Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include <config_features.h>
21 :
22 : #if HAVE_FEATURE_MACOSX_SANDBOX
23 : #include <premac.h>
24 : #include <Foundation/Foundation.h>
25 : #include <postmac.h>
26 : #endif
27 :
28 : #include "cmdlineargs.hxx"
29 : #include <vcl/svapp.hxx>
30 : #include <rtl/uri.hxx>
31 : #include <rtl/ustring.hxx>
32 : #include <rtl/process.h>
33 : #include <comphelper/processfactory.hxx>
34 : #include <com/sun/star/uri/ExternalUriReferenceTranslator.hpp>
35 : #include <tools/getprocessworkingdir.hxx>
36 :
37 : #include <svl/documentlockfile.hxx>
38 :
39 : #include <cstdio>
40 :
41 : using namespace com::sun::star::lang;
42 : using namespace com::sun::star::uri;
43 : using namespace com::sun::star::uno;
44 :
45 :
46 : namespace desktop
47 : {
48 :
49 : namespace {
50 :
51 96 : OUString translateExternalUris(OUString const & input) {
52 : OUString t(
53 : com::sun::star::uri::ExternalUriReferenceTranslator::create(
54 288 : comphelper::getProcessComponentContext())->
55 192 : translateToInternal(input));
56 96 : return t.isEmpty() ? input : t;
57 : }
58 :
59 768 : std::vector< OUString > translateExternalUris(
60 : std::vector< OUString > const & input)
61 : {
62 768 : std::vector< OUString > t;
63 2304 : for (std::vector< OUString >::const_iterator i(input.begin());
64 1536 : i != input.end(); ++i)
65 : {
66 0 : t.push_back(translateExternalUris(*i));
67 : }
68 768 : return t;
69 : }
70 :
71 : class ExtCommandLineSupplier: public CommandLineArgs::Supplier {
72 : public:
73 160 : explicit ExtCommandLineSupplier():
74 160 : m_count(rtl_getAppCommandArgCount()),
75 320 : m_index(0)
76 : {
77 160 : OUString url;
78 160 : if (tools::getProcessWorkingDir(url)) {
79 160 : m_cwdUrl.reset(url);
80 160 : }
81 160 : }
82 :
83 160 : virtual ~ExtCommandLineSupplier() {}
84 :
85 160 : virtual boost::optional< OUString > getCwdUrl() SAL_OVERRIDE { return m_cwdUrl; }
86 :
87 1120 : virtual bool next(OUString * argument) SAL_OVERRIDE {
88 : OSL_ASSERT(argument != NULL);
89 1120 : if (m_index < m_count) {
90 960 : rtl_getAppCommandArg(m_index++, &argument->pData);
91 960 : return true;
92 : } else {
93 160 : return false;
94 : }
95 : }
96 :
97 : private:
98 : boost::optional< OUString > m_cwdUrl;
99 : sal_uInt32 m_count;
100 : sal_uInt32 m_index;
101 : };
102 :
103 : }
104 :
105 0 : CommandLineArgs::Supplier::Exception::Exception() {}
106 :
107 0 : CommandLineArgs::Supplier::Exception::Exception(Exception const &) {}
108 :
109 0 : CommandLineArgs::Supplier::Exception::~Exception() {}
110 :
111 : CommandLineArgs::Supplier::Exception &
112 0 : CommandLineArgs::Supplier::Exception::operator =(Exception const &)
113 0 : { return *this; }
114 :
115 160 : CommandLineArgs::Supplier::~Supplier() {}
116 :
117 : // intialize class with command line parameters from process environment
118 160 : CommandLineArgs::CommandLineArgs()
119 : {
120 160 : InitParamValues();
121 160 : ExtCommandLineSupplier s;
122 160 : ParseCommandLine_Impl( s );
123 160 : }
124 :
125 0 : CommandLineArgs::CommandLineArgs( Supplier& supplier )
126 : {
127 0 : InitParamValues();
128 0 : ParseCommandLine_Impl( supplier );
129 0 : }
130 :
131 :
132 :
133 160 : void CommandLineArgs::ParseCommandLine_Impl( Supplier& supplier )
134 : {
135 160 : m_cwdUrl = supplier.getCwdUrl();
136 :
137 : // parse command line arguments
138 160 : bool bOpenEvent(true);
139 160 : bool bPrintEvent(false);
140 160 : bool bViewEvent(false);
141 160 : bool bStartEvent(false);
142 160 : bool bPrintToEvent(false);
143 160 : bool bPrinterName(false);
144 160 : bool bForceOpenEvent(false);
145 160 : bool bForceNewEvent(false);
146 160 : bool bDisplaySpec(false);
147 160 : bool bOpenDoc(false);
148 160 : bool bConversionEvent(false);
149 160 : bool bConversionParamsEvent(false);
150 160 : bool bBatchPrintEvent(false);
151 160 : bool bBatchPrinterNameEvent(false);
152 160 : bool bConversionOutEvent(false);
153 :
154 : for (;;)
155 : {
156 1120 : OUString aArg;
157 1120 : if ( !supplier.next( &aArg ) )
158 : {
159 160 : break;
160 : }
161 :
162 960 : if ( !aArg.isEmpty() )
163 : {
164 960 : m_bEmpty = false;
165 960 : OUString oArg;
166 960 : bool bDeprecated = !aArg.startsWith("--", &oArg)
167 960 : && aArg.startsWith("-", &oArg) && aArg.getLength() > 2;
168 : // -h, -?, -n, -o, -p are still valid
169 :
170 1920 : OUString rest;
171 960 : if ( oArg == "minimized" )
172 : {
173 0 : m_minimized = true;
174 : }
175 960 : else if ( oArg == "invisible" )
176 : {
177 0 : m_invisible = true;
178 : }
179 960 : else if ( oArg == "norestore" )
180 : {
181 160 : m_norestore = true;
182 : }
183 800 : else if ( oArg == "nodefault" )
184 : {
185 0 : m_nodefault = true;
186 : }
187 800 : else if ( oArg == "headless" )
188 : {
189 : // Headless means also invisibile, so set this parameter to true!
190 160 : m_headless = true;
191 160 : m_invisible = true;
192 : }
193 640 : else if ( oArg == "cat" )
194 : {
195 0 : m_textcat = true;
196 0 : m_conversionparams = "txt:Text";
197 0 : bOpenEvent = false;
198 0 : bConversionEvent = true;
199 : }
200 640 : else if ( oArg == "quickstart" )
201 : {
202 : #if defined(ENABLE_QUICKSTART_APPLET)
203 0 : m_quickstart = true;
204 : #endif
205 0 : m_noquickstart = false;
206 : }
207 640 : else if ( oArg == "quickstart=no" )
208 : {
209 160 : m_noquickstart = true;
210 160 : m_quickstart = false;
211 : }
212 480 : else if ( oArg == "terminate_after_init" )
213 : {
214 0 : m_terminateafterinit = true;
215 : }
216 480 : else if ( oArg == "nofirststartwizard" )
217 : {
218 160 : m_nofirststartwizard = true;
219 : }
220 320 : else if ( oArg == "nologo" )
221 : {
222 160 : m_nologo = true;
223 : }
224 : #if HAVE_FEATURE_MULTIUSER_ENVIRONMENT
225 160 : else if ( oArg == "nolockcheck" )
226 : {
227 0 : m_nolockcheck = true;
228 : }
229 : #endif
230 160 : else if ( oArg == "help" || aArg == "-h" || aArg == "-?" )
231 : {
232 0 : m_help = true;
233 : }
234 160 : else if ( oArg == "helpwriter" )
235 : {
236 0 : m_helpwriter = true;
237 : }
238 160 : else if ( oArg == "helpcalc" )
239 : {
240 0 : m_helpcalc = true;
241 : }
242 160 : else if ( oArg == "helpdraw" )
243 : {
244 0 : m_helpdraw = true;
245 : }
246 160 : else if ( oArg == "helpimpress" )
247 : {
248 0 : m_helpimpress = true;
249 : }
250 160 : else if ( oArg == "helpbase" )
251 : {
252 0 : m_helpbase = true;
253 : }
254 160 : else if ( oArg == "helpbasic" )
255 : {
256 0 : m_helpbasic = true;
257 : }
258 160 : else if ( oArg == "helpmath" )
259 : {
260 0 : m_helpmath = true;
261 : }
262 160 : else if ( oArg == "version" )
263 : {
264 0 : m_version = true;
265 : }
266 160 : else if ( oArg.startsWith("splash-pipe=") )
267 : {
268 0 : m_splashpipe = true;
269 : }
270 : #ifdef MACOSX
271 : /* #i84053# ignore -psn on Mac
272 : Platform dependent #ifdef here is ugly, however this is currently
273 : the only platform dependent parameter. Should more appear
274 : we should find a better solution
275 : */
276 : else if ( aArg.startsWith("-psn") )
277 : {
278 : bDeprecated = false;
279 : }
280 : #endif
281 : #if HAVE_FEATURE_MACOSX_SANDBOX
282 : else if ( oArg == "nstemporarydirectory" )
283 : {
284 : printf("%s\n", [NSTemporaryDirectory() UTF8String]);
285 : exit(0);
286 : }
287 : #endif
288 : #ifdef WIN32
289 : /* fdo#57203 ignore -Embedding on Windows
290 : when LibreOffice is launched by COM+
291 : */
292 : else if ( oArg == "Embedding" )
293 : {
294 : bDeprecated = false;
295 : }
296 : #endif
297 160 : else if ( oArg.startsWith("infilter=", &rest))
298 : {
299 0 : m_infilter.push_back(rest);
300 : }
301 160 : else if ( oArg.startsWith("accept=", &rest))
302 : {
303 160 : m_accept.push_back(rest);
304 : }
305 0 : else if ( oArg.startsWith("unaccept=", &rest))
306 : {
307 0 : m_unaccept.push_back(rest);
308 : }
309 0 : else if ( oArg.startsWith("language=", &rest))
310 : {
311 0 : m_language = rest;
312 : }
313 0 : else if ( oArg.startsWith("pidfile=", &rest))
314 : {
315 0 : m_pidfile = rest;
316 : }
317 0 : else if ( oArg == "writer" )
318 : {
319 0 : m_writer = true;
320 0 : m_bDocumentArgs = true;
321 : }
322 0 : else if ( oArg == "calc" )
323 : {
324 0 : m_calc = true;
325 0 : m_bDocumentArgs = true;
326 : }
327 0 : else if ( oArg == "draw" )
328 : {
329 0 : m_draw = true;
330 0 : m_bDocumentArgs = true;
331 : }
332 0 : else if ( oArg == "impress" )
333 : {
334 0 : m_impress = true;
335 0 : m_bDocumentArgs = true;
336 : }
337 0 : else if ( oArg == "base" )
338 : {
339 0 : m_base = true;
340 0 : m_bDocumentArgs = true;
341 : }
342 0 : else if ( oArg == "global" )
343 : {
344 0 : m_global = true;
345 0 : m_bDocumentArgs = true;
346 : }
347 0 : else if ( oArg == "math" )
348 : {
349 0 : m_math = true;
350 0 : m_bDocumentArgs = true;
351 : }
352 0 : else if ( oArg == "web" )
353 : {
354 0 : m_web = true;
355 0 : m_bDocumentArgs = true;
356 : }
357 0 : else if ( aArg == "-n" )
358 : {
359 : // force new documents based on the following documents
360 0 : bForceNewEvent = true;
361 0 : bOpenEvent = false;
362 0 : bForceOpenEvent = false;
363 0 : bPrintToEvent = false;
364 0 : bPrintEvent = false;
365 0 : bViewEvent = false;
366 0 : bStartEvent = false;
367 0 : bDisplaySpec = false;
368 : }
369 0 : else if ( aArg == "-o" )
370 : {
371 : // force open documents regardless if they are templates or not
372 0 : bForceOpenEvent = true;
373 0 : bOpenEvent = false;
374 0 : bForceNewEvent = false;
375 0 : bPrintToEvent = false;
376 0 : bPrintEvent = false;
377 0 : bViewEvent = false;
378 0 : bStartEvent = false;
379 0 : bDisplaySpec = false;
380 : }
381 0 : else if ( oArg == "pt" )
382 : {
383 : // Print to special printer
384 0 : bPrintToEvent = true;
385 0 : bPrinterName = true;
386 0 : bPrintEvent = false;
387 0 : bOpenEvent = false;
388 0 : bForceNewEvent = false;
389 0 : bViewEvent = false;
390 0 : bStartEvent = false;
391 0 : bDisplaySpec = false;
392 0 : bForceOpenEvent = false;
393 : }
394 0 : else if ( aArg == "-p" )
395 : {
396 : // Print to default printer
397 0 : bPrintEvent = true;
398 0 : bPrintToEvent = false;
399 0 : bOpenEvent = false;
400 0 : bForceNewEvent = false;
401 0 : bForceOpenEvent = false;
402 0 : bViewEvent = false;
403 0 : bStartEvent = false;
404 0 : bDisplaySpec = false;
405 : }
406 0 : else if ( oArg == "view")
407 : {
408 : // open in viewmode
409 0 : bOpenEvent = false;
410 0 : bPrintEvent = false;
411 0 : bPrintToEvent = false;
412 0 : bForceNewEvent = false;
413 0 : bForceOpenEvent = false;
414 0 : bViewEvent = true;
415 0 : bStartEvent = false;
416 0 : bDisplaySpec = false;
417 : }
418 0 : else if ( oArg == "show" )
419 : {
420 : // open in viewmode
421 0 : bOpenEvent = false;
422 0 : bViewEvent = false;
423 0 : bStartEvent = true;
424 0 : bPrintEvent = false;
425 0 : bPrintToEvent = false;
426 0 : bForceNewEvent = false;
427 0 : bForceOpenEvent = false;
428 0 : bDisplaySpec = false;
429 : }
430 0 : else if ( oArg == "display" )
431 : {
432 : // set display
433 0 : bOpenEvent = false;
434 0 : bPrintEvent = false;
435 0 : bForceOpenEvent = false;
436 0 : bPrintToEvent = false;
437 0 : bForceNewEvent = false;
438 0 : bViewEvent = false;
439 0 : bStartEvent = false;
440 0 : bDisplaySpec = true;
441 : }
442 0 : else if ( oArg == "language" )
443 : {
444 0 : bOpenEvent = false;
445 0 : bPrintEvent = false;
446 0 : bForceOpenEvent = false;
447 0 : bPrintToEvent = false;
448 0 : bForceNewEvent = false;
449 0 : bViewEvent = false;
450 0 : bStartEvent = false;
451 0 : bDisplaySpec = false;
452 : }
453 0 : else if ( oArg == "convert-to" )
454 : {
455 0 : bOpenEvent = false;
456 0 : bConversionEvent = true;
457 0 : bConversionParamsEvent = true;
458 : }
459 0 : else if ( oArg == "print-to-file" )
460 : {
461 0 : bOpenEvent = false;
462 0 : bBatchPrintEvent = true;
463 : }
464 0 : else if ( oArg == "printer-name" && bBatchPrintEvent )
465 : {
466 0 : bBatchPrinterNameEvent = true;
467 : }
468 0 : else if ( oArg == "outdir" &&
469 0 : (bConversionEvent || bBatchPrintEvent) )
470 : {
471 0 : bConversionOutEvent = true;
472 : }
473 0 : else if ( aArg.startsWith("-") )
474 : {
475 : // because it's impossible to filter these options that
476 : // are handled in the soffice shell script with the
477 : // primitive tools that /bin/sh offers, ignore them here
478 0 : if (
479 : #if defined UNX
480 0 : oArg != "backtrace" &&
481 0 : oArg != "strace" &&
482 0 : oArg != "valgrind" &&
483 : // for X Session Management, handled in
484 : // vcl/unx/generic/app/sm.cxx:
485 0 : oArg != "session=" &&
486 : #endif
487 : //ignore additional legacy options that don't do anything anymore
488 0 : oArg != "nocrashreport" &&
489 0 : m_unknown.isEmpty())
490 : {
491 0 : m_unknown = aArg;
492 : }
493 0 : bDeprecated = false;
494 : }
495 : else
496 : {
497 0 : if ( bPrinterName && bPrintToEvent )
498 : {
499 : // first argument after "-pt" this must be the printer name
500 0 : m_printername = aArg;
501 0 : bPrinterName = false;
502 : }
503 0 : else if ( bConversionParamsEvent && bConversionEvent )
504 : {
505 : // first argument must be the params
506 0 : m_conversionparams = aArg;
507 0 : bConversionParamsEvent = false;
508 : }
509 0 : else if ( bBatchPrinterNameEvent && bBatchPrintEvent )
510 : {
511 : // first argument is the printer name
512 0 : m_printername = aArg;
513 0 : bBatchPrinterNameEvent = false;
514 : }
515 0 : else if ( (bConversionEvent || bBatchPrintEvent) && bConversionOutEvent )
516 : {
517 0 : m_conversionout = aArg;
518 0 : bConversionOutEvent = false;
519 : }
520 : else
521 : {
522 : // handle this argument as a filename
523 0 : if ( bOpenEvent )
524 : {
525 0 : m_openlist.push_back(aArg);
526 0 : bOpenDoc = true;
527 : }
528 0 : else if ( bViewEvent )
529 : {
530 0 : m_viewlist.push_back(aArg);
531 0 : bOpenDoc = true;
532 : }
533 0 : else if ( bStartEvent )
534 : {
535 0 : m_startlist.push_back(aArg);
536 0 : bOpenDoc = true;
537 : }
538 0 : else if ( bPrintEvent )
539 : {
540 0 : m_printlist.push_back(aArg);
541 0 : bOpenDoc = true;
542 : }
543 0 : else if ( bPrintToEvent )
544 : {
545 0 : m_printtolist.push_back(aArg);
546 0 : bOpenDoc = true;
547 : }
548 0 : else if ( bForceNewEvent )
549 : {
550 0 : m_forcenewlist.push_back(aArg);
551 0 : bOpenDoc = true;
552 : }
553 0 : else if ( bForceOpenEvent )
554 : {
555 0 : m_forceopenlist.push_back(aArg);
556 0 : bOpenDoc = true;
557 : }
558 0 : else if ( bDisplaySpec )
559 : {
560 0 : bDisplaySpec = false; // only one display, not a lsit
561 0 : bOpenEvent = true; // set back to standard
562 : }
563 0 : else if ( bConversionEvent || bBatchPrintEvent )
564 0 : m_conversionlist.push_back(aArg);
565 : }
566 : }
567 :
568 960 : if (bDeprecated)
569 : {
570 0 : OString sArg(OUStringToOString(aArg, osl_getThreadTextEncoding()));
571 0 : fprintf(stderr, "Warning: %s is deprecated. Use -%s instead.\n", sArg.getStr(), sArg.getStr());
572 960 : }
573 : }
574 960 : }
575 :
576 160 : if ( bOpenDoc )
577 0 : m_bDocumentArgs = true;
578 160 : }
579 :
580 160 : void CommandLineArgs::InitParamValues()
581 : {
582 160 : m_minimized = false;
583 160 : m_norestore = false;
584 : #ifdef LIBO_HEADLESS
585 : m_invisible = true;
586 : m_headless = true;
587 : #else
588 160 : m_invisible = false;
589 160 : m_headless = false;
590 : #endif
591 160 : m_quickstart = false;
592 160 : m_noquickstart = false;
593 160 : m_terminateafterinit = false;
594 160 : m_nofirststartwizard = false;
595 160 : m_nologo = false;
596 160 : m_nolockcheck = false;
597 160 : m_nodefault = false;
598 160 : m_help = false;
599 160 : m_writer = false;
600 160 : m_calc = false;
601 160 : m_draw = false;
602 160 : m_impress = false;
603 160 : m_global = false;
604 160 : m_math = false;
605 160 : m_web = false;
606 160 : m_base = false;
607 160 : m_helpwriter = false;
608 160 : m_helpcalc = false;
609 160 : m_helpdraw = false;
610 160 : m_helpbasic = false;
611 160 : m_helpmath = false;
612 160 : m_helpimpress = false;
613 160 : m_helpbase = false;
614 160 : m_version = false;
615 160 : m_splashpipe = false;
616 160 : m_bEmpty = true;
617 160 : m_bDocumentArgs = false;
618 160 : m_textcat = false;
619 160 : }
620 :
621 :
622 :
623 :
624 :
625 :
626 :
627 :
628 :
629 :
630 :
631 :
632 :
633 :
634 :
635 :
636 :
637 :
638 :
639 :
640 :
641 :
642 :
643 :
644 :
645 :
646 0 : bool CommandLineArgs::HasModuleParam() const
647 : {
648 0 : return m_writer || m_calc || m_draw || m_impress || m_global || m_math
649 0 : || m_web || m_base;
650 : }
651 :
652 :
653 :
654 :
655 96 : std::vector< OUString > CommandLineArgs::GetOpenList() const
656 : {
657 96 : return translateExternalUris(m_openlist);
658 : }
659 :
660 96 : std::vector< OUString > CommandLineArgs::GetViewList() const
661 : {
662 96 : return translateExternalUris(m_viewlist);
663 : }
664 :
665 96 : std::vector< OUString > CommandLineArgs::GetStartList() const
666 : {
667 96 : return translateExternalUris(m_startlist);
668 : }
669 :
670 96 : std::vector< OUString > CommandLineArgs::GetForceOpenList() const
671 : {
672 96 : return translateExternalUris(m_forceopenlist);
673 : }
674 :
675 96 : std::vector< OUString > CommandLineArgs::GetForceNewList() const
676 : {
677 96 : return translateExternalUris(m_forcenewlist);
678 : }
679 :
680 96 : std::vector< OUString > CommandLineArgs::GetPrintList() const
681 : {
682 96 : return translateExternalUris(m_printlist);
683 : }
684 :
685 96 : std::vector< OUString > CommandLineArgs::GetPrintToList() const
686 : {
687 96 : return translateExternalUris(m_printtolist);
688 : }
689 :
690 :
691 :
692 :
693 96 : std::vector< OUString > CommandLineArgs::GetConversionList() const
694 : {
695 96 : return translateExternalUris(m_conversionlist);
696 : }
697 :
698 96 : OUString CommandLineArgs::GetConversionOut() const
699 : {
700 96 : return translateExternalUris(m_conversionout);
701 : }
702 :
703 :
704 :
705 :
706 480 : } // namespace desktop
707 :
708 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|