ARTS  2.2.66
main.cc
Go to the documentation of this file.
1 /* Copyright (C) 2000-2012 Stefan Buehler <sbuehler@ltu.se>
2 
3  This program is free software; you can redistribute it and/or modify it
4  under the terms of the GNU General Public License as published by the
5  Free Software Foundation; either version 2, or (at your option) any
6  later version.
7 
8  This program is distributed in the hope that it will be useful,
9  but WITHOUT ANY WARRANTY; without even the implied warranty of
10  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  GNU General Public License for more details.
12 
13  You should have received a copy of the GNU General Public License
14  along with this program; if not, write to the Free Software
15  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
16  USA. */
17 
31 #include "arts.h"
32 
33 #ifdef ENABLE_GUI
34 #include "ag_main.h"
35 #endif
36 
37 #ifdef TIME_SUPPORT
38 #include <sys/types.h>
39 #include <unistd.h>
40 #include <sys/stat.h>
41 #include <ctime>
42 #include <sys/times.h>
43 #endif
44 #include <algorithm>
45 #include <map>
46 
47 #include "auto_version.h"
48 #include "parameters.h"
49 #include "messages.h"
50 #include "exceptions.h"
51 #include "file.h"
52 #include "methods.h"
53 #include "parser.h"
54 #include "auto_md.h"
55 #include "absorption.h"
56 #include "wsv_aux.h"
57 #include "agenda_record.h"
58 #include "mystring.h"
59 #include "workspace_ng.h"
60 #include "arts_omp.h"
61 #include "docserver.h"
62 #include "global_data.h"
63 
66 {
67  cerr << "Try `arts --help' for help.\n";
68  arts_exit ();
69 
70 }
71 
86 {
88 
89  if ( -1 == r )
90  {
91  // Reporting was not specified, set default. (No output from
92  // agendas (except main of course), only the important stuff to
93  // the screen, nothing to the file.)
94  verbosity_at_launch.set_agenda_verbosity(0);
95  verbosity_at_launch.set_screen_verbosity(1);
96  verbosity_at_launch.set_file_verbosity(0);
97  }
98  else
99  {
100  // Reporting was specified. Check consistency and set report
101  // level accordingly.
102 
103  // Separate the three digits:
104  verbosity_at_launch.set_agenda_verbosity(r/100);
105  verbosity_at_launch.set_screen_verbosity((r%100)/10);
106  verbosity_at_launch.set_file_verbosity(r%10);
107 
108  if ( !verbosity_at_launch.valid() )
109  {
110  cerr << "Illegal value specified for --reporting (-r).\n"
111  << "The specified value is " << r << ", which would be\n"
112  << "interpreted as:\n"
113  << "Verbosity for agendas: " << verbosity_at_launch.get_agenda_verbosity() << "\n"
114  << "Verbosity for screen: " << verbosity_at_launch.get_screen_verbosity() << "\n"
115  << "Verbosity for report file: " << verbosity_at_launch.get_file_verbosity() << "\n"
116  << "Only values of 0-3 are allowed for each verbosity.\n";
117  arts_exit ();
118  }
119  }
120 }
121 
122 
130 void option_methods(const String& methods)
131 {
132  Workspace workspace;
133  workspace.initialize();
134  // Make global data visible:
136  extern const Parameters parameters;
138 
139  // This is used to count the number of matches to a query, so
140  // that `none' can be output if necessary
141  Index hitcount;
142 
143  // First check if the user gave the special name `all':
144 
145  if ( "all" == methods )
146  {
147  if (!parameters.plain)
148  {
149  cout
150  << "\n*-------------------------------------------------------------------*\n"
151  << "Complete list of ARTS workspace methods:\n"
152  << "---------------------------------------------------------------------\n";
153  }
154  for ( Index i=0; i<md_data_raw.nelem(); ++i )
155  {
156  if (!parameters.plain) cout << "- ";
157  cout << md_data_raw[i].Name() << "\n";
158  }
159 
160  if (!parameters.plain)
161  cout << "*-------------------------------------------------------------------*\n\n";
162 
163  return;
164  }
165 
166  // Ok, so the user has probably specified a workspace variable or
167  // workspace variable group.
168 
169  // Check if the user gave the name of a specific variable.
170  map<String, Index>::const_iterator mi =
171  Workspace::WsvMap.find(methods);
172  if ( mi != Workspace::WsvMap.end() )
173  {
174  // If we are here, then the given name matches a variable.
175  Index wsv_key = mi->second;
176 
177  // List generic methods:
178  hitcount = 0;
179  cout
180  << "\n*-------------------------------------------------------------------*\n"
181  << "Generic and supergeneric methods that can generate " << Workspace::wsv_data[wsv_key].Name()
182  << ":\n"
183  << "---------------------------------------------------------------------\n";
184  for ( Index i=0; i<md_data_raw.nelem(); ++i )
185  {
186  // Get handle on method record:
187  const MdRecord& mdd = md_data_raw[i];
188 
189  // This if statement checks whether GOutType, the list
190  // of output variable types contains the group of the
191  // requested variable.
192  // The else clause picks up methods with supergeneric input.
193  if ( count( mdd.GOutType().begin(),
194  mdd.GOutType().end(),
195  Workspace::wsv_data[wsv_key].Group() ) )
196  {
197  cout << "- " << mdd.Name() << "\n";
198  ++hitcount;
199  }
200  else if ( count( mdd.GOutType().begin(),
201  mdd.GOutType().end(),
202  get_wsv_group_id("Any") ) )
203  {
204  for (Index j = 0; j < mdd.GOutType().nelem(); j++)
205  {
206  if (mdd.GOutType()[j] == get_wsv_group_id("Any"))
207  {
208  if (mdd.GOutSpecType()[j].nelem())
209  {
210  if (count( mdd.GOutSpecType()[j].begin(),
211  mdd.GOutSpecType()[j].end(),
212  Workspace::wsv_data[wsv_key].Group() ) )
213  {
214  cout << "- " << mdd.Name() << "\n";
215  ++hitcount;
216  }
217  }
218  else
219  {
220  cout << "- " << mdd.Name() << "\n";
221  ++hitcount;
222  }
223  }
224  }
225  }
226  }
227  if ( 0==hitcount )
228  cout << "none\n";
229 
230  // List specific methods:
231  hitcount = 0;
232  cout
233  << "\n---------------------------------------------------------------------\n"
234  << "Specific methods that can generate " << Workspace::wsv_data[wsv_key].Name()
235  << ":\n"
236  << "---------------------------------------------------------------------\n";
237  for ( Index i=0; i<md_data_raw.nelem(); ++i )
238  {
239  // Get handle on method record:
240  const MdRecord& mdd = md_data_raw[i];
241 
242  // This if statement checks whether Output, the list
243  // of output variables contains the workspace
244  // variable key.
245  if ( count( mdd.Out().begin(),
246  mdd.Out().end(),
247  wsv_key ) )
248  {
249  cout << "- " << mdd.Name() << "\n";
250  ++hitcount;
251  }
252  }
253  if ( 0==hitcount )
254  cout << "none\n";
255 
256  cout
257  << "*-------------------------------------------------------------------*\n\n";
258 
259  return;
260  }
261 
262  // Check if the user gave the name of a variable group.
263 
264  // We use the find algorithm from the STL to do this. It
265  // returns an iterator, so to get the index we take the
266  // difference to the begin() iterator.
267  Index group_key =
268  find( wsv_group_names.begin(),
269  wsv_group_names.end(),
270  methods ) - wsv_group_names.begin();
271 
272  // group_key == wsv_goup_names.nelem() indicates that a
273  // group with this name was not found.
274  if ( group_key != wsv_group_names.nelem() )
275  {
276  // List generic methods:
277  hitcount = 0;
278  cout
279  << "\n*-------------------------------------------------------------------*\n"
280  << "Generic and supergeneric methods that can generate variables of group "
281  << wsv_group_names[group_key] << ":\n"
282  << "---------------------------------------------------------------------\n";
283  for ( Index i=0; i<md_data_raw.nelem(); ++i )
284  {
285  // Get handle on method record:
286  const MdRecord& mdd = md_data_raw[i];
287 
288  // This if statement checks whether GOutType, the list
289  // of output variable types contains the
290  // requested group.
291  // The else clause picks up methods with supergeneric input.
292  if ( count( mdd.GOutType().begin(),
293  mdd.GOutType().end(),
294  group_key ) )
295  {
296  cout << "- " << mdd.Name() << "\n";
297  ++hitcount;
298  }
299  else if ( count( mdd.GOutType().begin(),
300  mdd.GOutType().end(),
301  get_wsv_group_id("Any") ) )
302  {
303  for (Index j = 0; j < mdd.GOutType().nelem(); j++)
304  {
305  if (mdd.GOutType()[j] == get_wsv_group_id("Any"))
306  {
307  if (mdd.GOutSpecType()[j].nelem())
308  {
309  if (count( mdd.GOutSpecType()[j].begin(),
310  mdd.GOutSpecType()[j].end(),
311  group_key ) )
312  {
313  cout << "- " << mdd.Name() << "\n";
314  ++hitcount;
315  }
316  }
317  else
318  {
319  cout << "- " << mdd.Name() << "\n";
320  ++hitcount;
321  }
322  }
323  }
324  }
325  }
326  if ( 0==hitcount )
327  cout << "none\n";
328 
329  cout
330  << "*-------------------------------------------------------------------*\n\n";
331 
332  return;
333  }
334 
335  // If we are here it means that what the user specified is neither
336  // `all', nor a variable, nor a variable group.
337  cerr << "The name " << methods << " matches neither `all',\n"
338  << "nor the name of a workspace variable, nor the name\n"
339  << "of a workspace variable group.\n";
340  arts_exit ();
341 }
342 
350 void option_input(const String& input)
351 {
352  // Make global data visible:
355 
356  // Ok, so the user has probably specified a workspace variable or
357  // workspace variable group.
358 
359  // Check if the user gave the name of a specific variable.
360  map<String, Index>::const_iterator mi =
361  Workspace::WsvMap.find(input);
362  if ( mi != Workspace::WsvMap.end() )
363  {
364  // This is used to count the number of matches to a query, so
365  // that `none' can be output if necessary
366  Index hitcount = 0;
367 
368  // If we are here, then the given name matches a variable.
369  Index wsv_key = mi->second;
370 
371  // List generic methods:
372  cout
373  << "\n*-------------------------------------------------------------------*\n"
374  << "Generic and supergeneric methods that can use " << Workspace::wsv_data[wsv_key].Name() << ":\n"
375  << "---------------------------------------------------------------------\n";
376  for ( Index i=0; i<md_data_raw.nelem(); ++i )
377  {
378  // Get handle on method record:
379  const MdRecord& mdd = md_data_raw[i];
380 
381  // This if statement checks whether GInType, the list
382  // of input variable types contains the group of the
383  // requested variable.
384  // The else clause picks up methods with supergeneric input.
385  if ( count( mdd.GInType().begin(),
386  mdd.GInType().end(),
387  Workspace::wsv_data[wsv_key].Group() ) )
388  {
389  cout << "- " << mdd.Name() << "\n";
390  ++hitcount;
391  }
392  else if ( count( mdd.GInType().begin(),
393  mdd.GInType().end(),
394  get_wsv_group_id("Any") ) )
395  {
396  for (Index j = 0; j < mdd.GInType().nelem(); j++)
397  {
398  if (mdd.GInType()[j] == get_wsv_group_id("Any"))
399  {
400  if (mdd.GInSpecType()[j].nelem())
401  {
402  if (count( mdd.GInSpecType()[j].begin(),
403  mdd.GInSpecType()[j].end(),
404  Workspace::wsv_data[wsv_key].Group() ) )
405  {
406  cout << "- " << mdd.Name() << "\n";
407  ++hitcount;
408  }
409  }
410  else
411  {
412  cout << "- " << mdd.Name() << "\n";
413  ++hitcount;
414  }
415  }
416  }
417  }
418  }
419  if ( 0==hitcount )
420  cout << "none\n";
421 
422  // List specific methods:
423  hitcount = 0;
424  cout
425  << "\n---------------------------------------------------------------------\n"
426  << "Specific methods that require " << Workspace::wsv_data[wsv_key].Name()
427  << ":\n"
428  << "---------------------------------------------------------------------\n";
429  for ( Index i=0; i<md_data_raw.nelem(); ++i )
430  {
431  // Get handle on method record:
432  const MdRecord& mdd = md_data_raw[i];
433 
434  // This if statement checks whether Output, the list
435  // of output variables contains the workspace
436  // variable key.
437  if ( count( mdd.In().begin(),
438  mdd.In().end(),
439  wsv_key ) )
440  {
441  cout << "- " << mdd.Name() << "\n";
442  ++hitcount;
443  }
444  }
445  if ( 0==hitcount )
446  cout << "none\n";
447 
448  cout
449  << "*-------------------------------------------------------------------*\n\n";
450 
451  return;
452  }
453 
454  // Check if the user gave the name of a variable group.
455 
456  // We use the find algorithm from the STL to do this. It
457  // returns an iterator, so to get the index we take the
458  // difference to the begin() iterator.
459  Index group_key =
460  find( wsv_group_names.begin(),
461  wsv_group_names.end(),
462  input ) - wsv_group_names.begin();
463 
464  // group_key == wsv_goup_names.nelem() indicates that a
465  // group with this name was not found.
466  if ( group_key != wsv_group_names.nelem() )
467  {
468  // This is used to count the number of matches to a query, so
469  // that `none' can be output if necessary
470  Index hitcount = 0;
471 
472  // List generic methods:
473  cout
474  << "\n*-------------------------------------------------------------------*\n"
475  << "Generic and supergeneric methods that require a variable of group "
476  << wsv_group_names[group_key] << ":\n"
477  << "---------------------------------------------------------------------\n";
478  for ( Index i=0; i<md_data_raw.nelem(); ++i )
479  {
480  // Get handle on method record:
481  const MdRecord& mdd = md_data_raw[i];
482 
483  // This if statement checks whether GOutType, the list
484  // of output variable types contains the
485  // requested group.
486  // The else clause picks up methods with supergeneric input.
487  if ( count( mdd.GInType().begin(),
488  mdd.GInType().end(),
489  group_key ) )
490  {
491  cout << "- " << mdd.Name() << "\n";
492  ++hitcount;
493  }
494  else if ( count( mdd.GInType().begin(),
495  mdd.GInType().end(),
496  get_wsv_group_id("Any") ) )
497  {
498  for (Index j = 0; j < mdd.GInType().nelem(); j++)
499  {
500  if (mdd.GInType()[j] == get_wsv_group_id("Any"))
501  {
502  if (mdd.GInSpecType()[j].nelem())
503  {
504  if (count( mdd.GInSpecType()[j].begin(),
505  mdd.GInSpecType()[j].end(),
506  group_key ) )
507  {
508  cout << "- " << mdd.Name() << "\n";
509  ++hitcount;
510  }
511  }
512  else
513  {
514  cout << "- " << mdd.Name() << "\n";
515  ++hitcount;
516  }
517  }
518  }
519  }
520  }
521  if ( 0==hitcount )
522  cout << "none\n";
523 
524  cout
525  << "*-------------------------------------------------------------------*\n\n";
526 
527  return;
528  }
529 
530  // If we are here it means that what the user specified is neither
531  // a variable nor a variable group.
532  cerr << "The name " << input << " matches neither the name of a\n"
533  << "workspace variable, nor the name of a workspace variable group.\n";
534  arts_exit ();
535 }
536 
537 
545 void option_workspacevariables(const String& workspacevariables)
546 {
547  // Make global data visible:
548  using global_data::md_data;
549  using global_data::MdMap;
550  extern const Parameters parameters;
552 
553  // This is used to count the number of matches to a query, so
554  // that `none' can be output if necessary
555  Index hitcount;
556 
557  // First check for `all':
558 
559  if ( "all" == workspacevariables )
560  {
561  if (!parameters.plain)
562  {
563  cout
564  << "\n*-------------------------------------------------------------------*\n"
565  << "Complete list of ARTS workspace variables:\n"
566  << "---------------------------------------------------------------------\n";
567  }
568 
569  for ( Index i=0; i<Workspace::wsv_data.nelem(); ++i )
570  {
571  if (!parameters.plain) cout << "- ";
572  cout << Workspace::wsv_data[i].Name() << "\n";
573  }
574 
575  if (!parameters.plain)
576  cout << "*-------------------------------------------------------------------*\n\n";
577  return;
578  }
579 
580 
581  // Now check if the user gave the name of a method.
582  map<String, Index>::const_iterator mi =
583  MdMap.find(workspacevariables);
584  if ( mi != MdMap.end() )
585  {
586  // If we are here, then the given name matches a method.
587  // Assign the data record for this method to a local
588  // variable for easier access:
589  const MdRecord& mdr = md_data[mi->second];
590 
591  // List generic variables required by this method.
592  hitcount = 0;
593  cout
594  << "\n*-------------------------------------------------------------------*\n"
595  << "Generic workspace variables required by " << mdr.Name()
596  << " are of type:\n"
597  << "---------------------------------------------------------------------\n";
598  for ( Index i=0; i<mdr.GInType().nelem(); ++i )
599  {
600  cout << "- " << wsv_group_names[mdr.GInType()[i]] << "\n";
601  ++hitcount;
602  }
603  if ( 0==hitcount )
604  cout << "none\n";
605 
606  // List specific variables required by this method.
607  hitcount = 0;
608  cout
609  << "\n---------------------------------------------------------------------\n"
610  << "Specific workspace variables required by " << mdr.Name() << ":\n"
611  << "---------------------------------------------------------------------\n";
612  for ( Index i=0; i<mdr.In().nelem(); ++i )
613  {
614  cout << "- " << Workspace::wsv_data[mdr.In()[i]].Name() << "\n";
615  ++hitcount;
616  }
617  if ( 0==hitcount )
618  cout << "none\n";
619 
620  cout
621  << "*-------------------------------------------------------------------*\n\n";
622 
623  return;
624  }
625 
626  // If we are here, then the user specified nothing that makes sense.
627  cerr << "The name " << workspacevariables << " matches neither `all',\n"
628  << "nor the name of a workspace method.\n";
629  arts_exit ();
630 }
631 
632 
639 {
640  // Make global data visible:
642  using global_data::MdRawMap;
643 
644  // Let's first assume it is a method that the user wants to have
645  // described.
646 
647  // Find method id:
648  map<String, Index>::const_iterator i =
649  MdRawMap.find(describe);
650  if ( i != MdRawMap.end() )
651  {
652  // If we are here, then the given name matches a method.
653  cout << md_data_raw[i->second] << "\n";
654  return;
655  }
656 
657  // Ok, let's now assume it is a variable that the user wants to have
658  // described.
659 
660  // Find wsv id:
661  i = Workspace::WsvMap.find(describe);
662  if ( i != Workspace::WsvMap.end() )
663  {
664  // If we are here, then the given name matches a workspace
665  // variable.
666  cout << Workspace::wsv_data[i->second] << "\n";
667  return;
668  }
669 
670  // If we are here, then the given name does not match anything.
671  cerr << "The name " << describe
672  << " matches neither method nor variable.\n";
673  arts_exit ();
674 }
675 
676 
681 #ifdef TIME_SUPPORT
682 String arts_mod_time (String filename)
683 {
684  struct stat buf;
685  if (stat (filename.c_str(), &buf) != -1)
686  {
687  String ts = ctime (&buf.st_mtime);
688  return String(" (compiled ") + ts.substr (0, ts.length()-1) + ")";
689  }
690  else
691  return String("");
692 }
693 #else
695 {
696  return String("");
697 }
698 #endif
699 
700 
715 int main (int argc, char **argv)
716 {
717  extern const Parameters parameters; // Global variable that holds
718  // all command line parameters.
719 
720 
721  //---------------< -1. Time the arts run if possible >---------------
722 #ifdef TIME_SUPPORT
723  struct tms arts_cputime_start;
724  clock_t arts_realtime_start;
725  arts_realtime_start = times (&arts_cputime_start);
726 #endif
727 
728 
729  //---------------< 1. Get command line parameters >---------------
730  if ( get_parameters(argc, argv) )
731  {
732  // Print an error message and exit:
733  polite_goodby();
734  }
735 
736  //----------< 2. Evaluate the command line parameters >----------
737  if (parameters.help)
738  {
739  // Just print a help message and then exit.
740  cout << "\n" << parameters.usage << "\n\n";
741  cout << parameters.helptext << "\n\n";
742  arts_exit (EXIT_SUCCESS);
743  }
744 
745  ostringstream osfeatures;
746  {
747  osfeatures
748  << "Compiler: " << String(COMPILER) << endl;
749 
750  if (String(COMPILER) != "Xcode")
751  osfeatures << "Compile flags: " << COMPILE_FLAGS << endl;
752 
753  osfeatures
754  << "Features in this build: " << endl
755  << " Numeric precision: "
756  << ((sizeof (Numeric) == sizeof (double)) ? "double" : "float") << endl
757  << " OpenMP support: "
758 #ifdef _OPENMP
759  << "enabled" << endl
760 #else
761  << "disabled" << endl
762 #endif
763  << " Documentation server: "
764 #ifdef ENABLE_DOCSERVER
765  << "enabled" << endl
766 #else
767  << "disabled" << endl
768 #endif
769  << " Zipped XML support: "
770 #ifdef ENABLE_ZLIB
771  << "enabled" << endl
772 #else
773  << "disabled" << endl
774 #endif
775  << " NetCDF support: "
776 #ifdef ENABLE_NETCDF
777  << "enabled" << endl
778 #else
779  << "disabled" << endl
780 #endif
781  << " Fortran support: "
782 #ifdef FORTRAN_COMPILER
783  << "enabled (" << FORTRAN_COMPILER << ")" << endl
784 #else
785  << "disabled" << endl
786 #endif
787  << " Refice support: "
788 #ifdef ENABLE_REFICE
789  << "enabled" << endl
790 #else
791  << "disabled" << endl
792 #endif
793  << " Tmatrix support: "
794 #ifdef ENABLE_TMATRIX
795  << "enabled" << endl
796 #else
797  << "disabled" << endl
798 #endif
799  << ""
800  << "Include search paths: " << endl;
801 
802  for (ArrayOfString::const_iterator it = parameters.includepath.begin();
803  it != parameters.includepath.end(); it++)
804  {
805  osfeatures << " " << (*it) << endl;
806  }
807  osfeatures << "Data search paths: " << endl;
808 
809  for (ArrayOfString::const_iterator it = parameters.datapath.begin();
810  it != parameters.datapath.end(); it++)
811  {
812  osfeatures << " " << (*it) << endl;
813  }
814  }
815 
816  if (parameters.version)
817  {
818  cout << ARTS_FULL_VERSION << arts_mod_time (argv[0]) << endl;
819  cout << osfeatures.str();
820  arts_exit (EXIT_SUCCESS);
821  }
822 
823  if (parameters.numthreads)
824  {
825 #ifdef _OPENMP
826  omp_set_num_threads ((int)parameters.numthreads);
827 #else
828  cerr << "Ignoring commandline option --numthreads/-n.\n"
829  << "This option only works with an OpenMP enabled ARTS build.\n";
830 #endif
831  }
832 
833 
834  // For the next couple of options we need to have the workspce and
835  // method lookup data.
836 
837  // Initialize the wsv group name array:
839 
840  // Initialize the wsv data:
842 
843  // Initialize WsvMap:
845 
846  // Initialize the md data:
848 
849  // Expand supergeneric methods:
851 
852  // Initialize MdMap:
853  define_md_map();
854 
855  // Initialize MdRawMap (needed by parser and online docu).
857 
858  // Initialize the agenda lookup data:
860 
861  // Initialize AgendaMap:
863 
864  // Check that agenda information in wsv_data and agenda_data is consistent:
865  assert( check_agenda_data() );
866 
867  // While we are at it, we can also initialize the molecular data and
868  // the coefficients of the partition function that we need for the
869  // absorption part, and check that the inputs are sorted the same way:
871 
872  // And also the species map:
874 
875  // And the lineshape lookup data:
878 
879  // Make all global data visible:
881 
882  // Now we are set to deal with the more interesting command line
883  // switches.
884 
885 
886  // React to option `methods'. If given the argument `all', it
887  // should simply prints a list of all methods. If given the name of
888  // a variable, it should print all methods that produce this
889  // variable as output.
890  if ( "" != parameters.methods )
891  {
892  option_methods(parameters.methods);
893  arts_exit (EXIT_SUCCESS);
894  }
895 
896  // React to option `input'. Given the name of a variable (or group)
897  // it should print all methods that need this variable (or group) as
898  // input.
899  if ( "" != parameters.input )
900  {
901  option_input(parameters.input);
902  arts_exit (EXIT_SUCCESS);
903  }
904 
905  // React to option `workspacevariables'. If given the argument `all',
906  // it should simply prints a list of all variables. If given the
907  // name of a method, it should print all variables that are needed
908  // by that method.
909  if ( "" != parameters.workspacevariables )
910  {
912  arts_exit (EXIT_SUCCESS);
913  }
914 
915  // React to option `describe'. This should print the description
916  // String of the given workspace variable or method.
917  if ( "" != parameters.describe )
918  {
919  option_describe(parameters.describe);
920  arts_exit (EXIT_SUCCESS);
921  }
922 
923 
924  // React to option `groups'. This should simply print a list of all
925  // workspace variable groups.
926  if ( parameters.groups )
927  {
928  if (!parameters.plain)
929  {
930  cout
931  << "\n*-------------------------------------------------------------------*\n"
932  << "Complete list of ARTS workspace variable groups:\n"
933  << "---------------------------------------------------------------------\n";
934  }
935 
936  for ( Index i=0; i<wsv_group_names.nelem(); ++i )
937  {
938  if (!parameters.plain) cout << "- ";
939  cout << wsv_group_names[i] << "\n";
940  }
941 
942  if (!parameters.plain)
943  cout << "*-------------------------------------------------------------------*\n\n";
944  arts_exit (EXIT_SUCCESS);
945  }
946 
947 #ifdef ENABLE_DOCSERVER
948  if ( 0 != parameters.docserver )
949  {
950  if (parameters.daemon) {
951  int pid = fork();
952  if (!pid)
953  {
954  Docserver docserver(parameters.docserver, parameters.baseurl);
955  docserver.launch(parameters.daemon);
956  arts_exit(0);
957  }
958  else
959  {
960  cout << "Docserver daemon started with PID: " << pid << endl;
961  arts_exit(0);
962  }
963  }
964  else
965  {
966  Docserver docserver(parameters.docserver, parameters.baseurl);
967  cout << "Starting the arts documentation server." << endl;
968  docserver.launch(parameters.daemon);
969  arts_exit(0);
970  }
971  }
972 #endif
973 
974  if (parameters.gui)
975  {
976 #ifdef ENABLE_GUI
977  ag_main(argc, argv);
978 #endif
979 
980  arts_exit();
981  }
982 
983  // Ok, we are past all the special options. This means the user
984  // wants to get serious and really do a calculation. Check if we
985  // have at least one control file:
986  if ( 0 == parameters.controlfiles.nelem() )
987  {
988  cerr << "You must specify at least one control file name.\n";
989  polite_goodby();
990  }
991 
992  // Set the basename according to the first control file, if not
993  // explicitly specified.
994  if ( "" == parameters.basename )
995  {
996  extern String out_basename;
997  ArrayOfString fileparts;
998  parameters.controlfiles[0].split(fileparts, "/");
999  out_basename = fileparts[fileparts.nelem()-1];
1000  // Find the last . in the name
1001  String::size_type p = out_basename.rfind(".arts");
1002 
1003  if (String::npos==p)
1004  {
1005  // This is an error handler for the case that somebody gives
1006  // a supposed file name that does not contain the extension
1007  // ".arts"
1008 
1009  cerr << "The controlfile must have the extension .arts.\n";
1010  polite_goodby();
1011  }
1012 
1013  // Kill everything starting from the `.'
1014  out_basename.erase(p);
1015  }
1016  else
1017  {
1018  extern String out_basename;
1019  out_basename = parameters.basename;
1020  }
1021 
1022  // Set the global reporting level, either from reporting command line
1023  // option or default.
1024  set_reporting_level(parameters.reporting);
1025 
1026  // Keep around a global copy of the verbosity levels at launch, so that
1027  // verbosityInit() can be used to reset them in the control file
1029  Verbosity verbosity;
1030  verbosity = verbosity_at_launch;
1031  verbosity.set_main_agenda(true);
1032 
1033  CREATE_OUTS;
1034 
1035  //--------------------< Open report file >--------------------
1036  // This one needs its own little try block, because we have to
1037  // write error messages to cerr directly since the report file
1038  // will not exist.
1039  try
1040  {
1041  extern String out_basename; // Basis for file name
1042  extern ofstream report_file; // Report file pointer
1043  ostringstream report_file_ext;
1044 
1045  report_file_ext << ".rep";
1046  open_output_file(report_file, out_basename + report_file_ext.str ());
1047  }
1048  catch (runtime_error x)
1049  {
1050  cerr << x.what() << "\n"
1051  << "I have to be able to write to my report file.\n";
1052  arts_exit ();
1053  }
1054 
1055  // Now comes the global try block. Exceptions caught after this
1056  // one are general stuff like file opening errors.
1057  try
1058  {
1059  out1 << "Executing ARTS.\n";
1060 
1061  // Output command line:
1062  out1 << "Command line:\n";
1063  for (Index i=0; i<argc; ++i) {
1064  out1 << argv[i] << " ";
1065  }
1066  out1 << "\n";
1067 
1068  // Output full program name (with version number):
1069  out1 << "Version: " << ARTS_FULL_VERSION << arts_mod_time (argv[0]) << "\n";
1070 
1071  // Output more details about the compilation:
1072  out2 << osfeatures.str() << "\n";
1073 
1074  // Output some OpenMP specific information on output level 2:
1075 #ifdef _OPENMP
1076  out2 << "Running with OpenMP, "
1077  << "maximum number of threads = "
1078  << arts_omp_get_max_threads() << ".\n";
1079 #else
1080  out2 << "Running without OpenMP.\n";
1081 #endif
1082 
1083 
1084  // Output a short hello from each thread to out3:
1085 #ifdef _OPENMP
1086 #pragma omp parallel \
1087  default(none) \
1088  shared(out3)
1089  {
1090  ostringstream os;
1091  int tn = arts_omp_get_thread_num();
1092  os << " Thread " << tn << ": ready.\n";
1093  out3 << os.str();
1094  }
1095 #endif
1096  out2 << "\n";
1097 
1098  time_t rawtime;
1099  struct tm * timeinfo;
1100 
1101  time ( &rawtime );
1102  timeinfo = localtime ( &rawtime );
1103  out2 << "Run started: " << asctime(timeinfo) << "\n";
1104 
1105 
1106  // Output verbosity settings. This is not too interesting, it
1107  // goes only to out3.
1108  out3 << "Verbosity settings: Agendas: " << verbosity.get_agenda_verbosity() << "\n"
1109  << " Screen: " << verbosity.get_screen_verbosity() << "\n"
1110  << " Report file: " << verbosity.get_file_verbosity() << "\n";
1111 
1112  out3 << "\nReading control files:\n";
1113  for ( Index i=0; i<parameters.controlfiles.nelem(); ++i )
1114  {
1115  try {
1116  out3 << "- " << parameters.controlfiles[i] << "\n";
1117 
1118  // The list of methods to execute and their keyword data from
1119  // the control file.
1120  Agenda tasklist;
1121 
1122  Workspace workspace;
1123 
1124  // Call the parser to parse the control text:
1125  ArtsParser arts_parser(tasklist, parameters.controlfiles[i], verbosity);
1126 
1127  arts_parser.parse_tasklist();
1128 
1129  tasklist.set_name("Arts");
1130 
1131  tasklist.set_main_agenda();
1132 
1133  //tasklist.find_unused_variables();
1134 
1135  workspace.initialize ();
1136 
1137  // Execute main agenda:
1138  Arts2(workspace, tasklist, verbosity);
1139  }
1140  catch (const runtime_error x)
1141  {
1142  ostringstream os;
1143  os << "Run-time error in controlfile: " << parameters.controlfiles[i] << '\n'
1144  << x.what();
1145  throw runtime_error(os.str());
1146  }
1147  }
1148  }
1149  catch (const runtime_error x)
1150  {
1151 #ifdef TIME_SUPPORT
1152  struct tms arts_cputime_end;
1153  clock_t arts_realtime_end;
1154  long clktck = 0;
1155 
1156  clktck = sysconf (_SC_CLK_TCK);
1157  arts_realtime_end = times (&arts_cputime_end);
1158  if (clktck > 0
1159  && arts_realtime_start != (clock_t)-1
1160  && arts_realtime_end != (clock_t)-1)
1161  {
1162  out1 << "This run took " << fixed << setprecision(2)
1163  << (Numeric)
1164  (arts_realtime_end - arts_realtime_start)
1165  / (Numeric)clktck
1166  << "s (" << fixed << setprecision(2) << (Numeric)
1167  ((arts_cputime_end.tms_stime - arts_cputime_start.tms_stime)
1168  + (arts_cputime_end.tms_utime - arts_cputime_start.tms_utime))
1169  / (Numeric)clktck << "s CPU time)\n";
1170  }
1171 #endif
1172 
1173  arts_exit_with_error_message(x.what(), out0);
1174  }
1175 
1176 #ifdef TIME_SUPPORT
1177  struct tms arts_cputime_end;
1178  clock_t arts_realtime_end;
1179  long clktck = 0;
1180 
1181  clktck = sysconf (_SC_CLK_TCK);
1182  arts_realtime_end = times (&arts_cputime_end);
1183  if (clktck > 0
1184  && arts_realtime_start != (clock_t)-1
1185  && arts_realtime_end != (clock_t)-1)
1186  {
1187  out1 << "This run took " << fixed << setprecision(2)
1188  << (Numeric)
1189  (arts_realtime_end - arts_realtime_start)
1190  / (Numeric)clktck
1191  << "s (" << fixed << setprecision(2) << (Numeric)
1192  ((arts_cputime_end.tms_stime - arts_cputime_start.tms_stime)
1193  + (arts_cputime_end.tms_utime - arts_cputime_start.tms_utime))
1194  / (Numeric)clktck << "s CPU time)\n";
1195  }
1196 #endif
1197 
1198  out1 << "Everything seems fine. Goodbye.\n";
1199  arts_exit (EXIT_SUCCESS);
1200 }
String arts_mod_time(String)
This function returns the modification time of the arts executable as a string.
Definition: main.cc:694
Index get_wsv_group_id(const String &name)
Returns the id of the given group.
Definition: groups.cc:205
INDEX Index
The type to use for all integer numbers and indices.
Definition: matpack.h:35
static Array< WsvRecord > wsv_data
Definition: workspace_ng.h:64
bool daemon
Flag to run the docserver in the background.
Definition: parameters.h:128
ArrayOfString controlfiles
The filenames of the controlfiles.
Definition: parameters.h:89
void define_md_map()
Define MdMap.
Definition: methods_aux.cc:472
void option_input(const String &input)
React to option `input&#39;.
Definition: main.cc:350
Parameters parameters
Holds the command line parameters.
Definition: parameters.cc:41
void polite_goodby()
Remind the user of –help and exit return value 1.
Definition: main.cc:65
Index get_agenda_verbosity() const
Definition: messages.h:64
#define COMPILE_FLAGS
Definition: config.h:6
The Agenda class.
Definition: agenda_class.h:44
Index nelem() const
Number of elements.
Definition: array.h:176
#define ARTS_FULL_VERSION
Definition: auto_version.h:1
void arts_exit(int status)
This is the exit function of ARTS.
Definition: arts.cc:42
String baseurl
Baseurl for the docserver.
Definition: parameters.h:126
void option_methods(const String &methods)
React to option `methods&#39;.
Definition: main.cc:130
Declarations having to do with the four output streams.
void define_lineshape_data()
Definition: lineshapes.cc:1928
String basename
If this is specified (with the -b –basename option), it is used as the base name for the report file...
Definition: parameters.h:81
String describe(ConstTensor7View x)
Describe Tensor7.
Definition: describe.cc:39
Declarations for the arts documentation server.
#define FORTRAN_COMPILER
Definition: config.h:12
void initialize()
int arts_omp_get_thread_num()
Wrapper for omp_get_thread_num.
Definition: arts_omp.cc:83
bool groups
Print a list of all workspace variable groups.
Definition: parameters.h:120
void parse_tasklist()
Public interface to the main function of the parser.
Definition: parser.cc:48
int arts_omp_get_max_threads()
Wrapper for omp_get_max_threads.
Definition: arts_omp.cc:47
const ArrayOfIndex & Out() const
Definition: methods.h:92
void option_describe(const String &describe)
React to option `describe&#39;.
Definition: main.cc:638
void set_agenda_verbosity(Index v)
Definition: messages.h:69
const map< String, Index > MdRawMap
The map associated with md_data_raw.
Definition: methods_aux.cc:41
This file contains basic functions to handle ASCII files.
Structure to hold all command line Parameters.
Definition: parameters.h:42
String methods
If this is given the argument `all&#39;, it simply prints a list of all methods.
Definition: parameters.h:101
All information for one workspace method.
Definition: methods.h:42
void set_reporting_level(Index r)
Set the reporting level.
Definition: main.cc:85
void define_lineshape_norm_data()
Definition: lineshapes.cc:2033
String input
This is complementary to the methods switch.
Definition: parameters.h:111
String out_basename
The basename for the report file and for all other output files.
Definition: messages.cc:42
const String & Name() const
Definition: methods.h:89
ArrayOfString includepath
List of paths to search for include files.
Definition: parameters.h:105
void define_agenda_map()
void define_agenda_data()
Definition: agendas.cc:44
const map< String, Index > MdMap
The map associated with md_data.
Definition: methods_aux.cc:39
This file contains the declaration and partly the implementation of the workspace class...
ArrayOfString datapath
List of paths to search for data files.
Definition: parameters.h:107
The implementation for String, the ARTS string class.
Definition: mystring.h:63
void expand_md_data_raw_to_md_data()
Expand supergeneric methods.
Definition: methods_aux.cc:396
Index numthreads
The maximum number of threads to use.
Definition: parameters.h:103
The global header file for ARTS.
bool help
Only display the help text.
Definition: parameters.h:75
static void define_wsv_data()
Definition: workspace.cc:50
#define CREATE_OUTS
Definition: messages.h:216
const ArrayOfIndex & In() const
Definition: methods.h:97
void set_file_verbosity(Index v)
Definition: messages.h:71
void set_main_agenda(bool main_agenda)
Definition: messages.h:72
The declarations of all the exception classes.
Index reporting
This should be a two digit integer.
Definition: parameters.h:97
bool check_agenda_data()
Check that agendas.cc and workspace.cc are consistent.
#define COMPILER
Definition: config.h:9
ofstream report_file
The report file.
Definition: messages.cc:45
const ArrayOfArrayOfIndex & GInSpecType() const
Definition: methods.h:100
void option_workspacevariables(const String &workspacevariables)
React to option `workspacevariables&#39;.
Definition: main.cc:545
NUMERIC Numeric
The type to use for all floating point numbers.
Definition: matpack.h:29
Index docserver
Port to use for the docserver.
Definition: parameters.h:124
Declarations required for the calculation of absorption coefficients.
int main(int argc, char **argv)
This is the main function of ARTS.
Definition: main.cc:715
String usage
Short message how to call the program.
Definition: parameters.h:71
bool gui
Flag to run with graphical user interface.
Definition: parameters.h:130
void define_species_data()
void arts_exit_with_error_message(const String &m, ArtsOut &out)
Print error message and exit.
Definition: arts.cc:64
void define_md_raw_map()
Define MdRawMap.
Definition: methods_aux.cc:514
This can be used to make arrays out of anything.
Definition: array.h:40
void open_output_file(ofstream &file, const String &name)
Open a file for writing.
Definition: file.cc:103
const ArrayOfIndex & GOutType() const
Definition: methods.h:94
void define_wsv_group_names()
Define the array of workspace variable group names.
Definition: groups.cc:84
const ArrayOfString wsv_group_names
The names associated with Wsv groups as Strings.
Definition: global_data.h:94
void set_name(const String &nname)
Set agenda name.
static map< String, Index > WsvMap
Definition: workspace_ng.h:67
Index get_file_verbosity() const
Definition: messages.h:66
bool get_parameters(int argc, char **argv)
Get the command line parameters.
Definition: parameters.cc:76
void define_md_data_raw()
Definition: methods.cc:126
void set_main_agenda()
Definition: agenda_class.h:81
String workspacevariables
If this is given the argument `all&#39;, it simply prints a list of all workspace variables.
Definition: parameters.h:115
Workspace class.
Definition: workspace_ng.h:47
const ArrayOfArrayOfIndex & GOutSpecType() const
Definition: methods.h:95
const Array< MdRecord > md_data
Lookup information for workspace methods.
Definition: methods_aux.cc:48
bool version
Display version information.
Definition: parameters.h:77
static void define_wsv_map()
Definition: workspace_ng.cc:53
const ArrayOfIndex & GInType() const
Definition: methods.h:99
static const Index npos
Define npos:
Definition: mystring.h:105
Verbosity verbosity_at_launch
Definition: messages.cc:34
Index get_screen_verbosity() const
Definition: messages.h:65
Header file for helper functions for OpenMP.
This file contains header information for the dealing with command line parameters.
bool valid() const
Check if artsmessages contains valid message levels.
Definition: messages.h:61
void define_species_map()
Define the species data map.
Definition: absorption.cc:322
bool plain
Generate plain help out suitable for script processing.
Definition: parameters.h:122
Declaration of the class MdRecord.
my_basic_string< char > String
The String type for ARTS.
Definition: mystring.h:318
Declarations for AgRecord, storing lookup information for one agenda.
This file contains the definition of String, the ARTS string class.
void Arts2(Workspace &ws, const Agenda &input_agenda, const Verbosity &verbosity)
WORKSPACE METHOD: Arts2.
Definition: m_agenda.cc:121
const Array< MdRecord > md_data_raw
Lookup information for workspace methods.
Definition: methods.cc:39
void set_screen_verbosity(Index v)
Definition: messages.h:70
String describe
Print the description String of the given workspace variable or method.
Definition: parameters.h:118
Auxiliary header stuff related to workspace variable groups.
String helptext
Longer message explaining the options.
Definition: parameters.h:73