Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-02-23 09:22:03

0001 //
0002 // ********************************************************************
0003 // * License and Disclaimer                                           *
0004 // *                                                                  *
0005 // * The  Geant4 software  is  copyright of the Copyright Holders  of *
0006 // * the Geant4 Collaboration.  It is provided  under  the terms  and *
0007 // * conditions of the Geant4 Software License,  included in the file *
0008 // * LICENSE and available at  http://cern.ch/geant4/license .  These *
0009 // * include a list of copyright holders.                             *
0010 // *                                                                  *
0011 // * Neither the authors of this software system, nor their employing *
0012 // * institutes,nor the agencies providing financial support for this *
0013 // * work  make  any representation or  warranty, express or implied, *
0014 // * regarding  this  software system or assume any liability for its *
0015 // * use.  Please see the license in the file  LICENSE  and URL above *
0016 // * for the full disclaimer and the limitation of liability.         *
0017 // *                                                                  *
0018 // * This  code  implementation is the result of  the  scientific and *
0019 // * technical work of the GEANT4 collaboration.                      *
0020 // * By using,  copying,  modifying or  distributing the software (or *
0021 // * any work based  on the software)  you  agree  to acknowledge its *
0022 // * use  in  resulting  scientific  publications,  and indicate your *
0023 // * acceptance of all terms of the Geant4 Software license.          *
0024 // ********************************************************************
0025 //
0026 // This example is provided by the Geant4-DNA collaboration
0027 // Any report or published results obtained using the Geant4-DNA software
0028 // shall cite the following Geant4-DNA collaboration publication:
0029 // Med. Phys. 37 (2010) 4692-4708
0030 // J. Comput. Phys. 274 (2014) 841-882
0031 // The Geant4-DNA web site is available at http://geant4-dna.org
0032 //
0033 // Author: Mathieu Karamitros
0034 //
0035 //
0036 /// \file CommandLineParser.cc
0037 /// \brief Implementation of the CommandLineParser class
0038 
0039 #include "CommandLineParser.hh"
0040 
0041 #include <iomanip>
0042 
0043 using namespace std;
0044 using namespace G4DNAPARSER;
0045 
0046 CommandLineParser* CommandLineParser::fpInstance(0);
0047 G4String Command::fNoOption = "NoOption";
0048 
0049 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0050 
0051 inline bool MATCH(const char* a, const char* b)
0052 {
0053   return strcmp(a, b) == 0;
0054 }
0055 
0056 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0057 
0058 CommandLineParser::CommandLineParser()
0059 {
0060   // G4cout << "############ NEW PARSE ##########" << G4endl;
0061   fpInstance = this;
0062   fOptionsWereSetup = false;
0063   fMaxMarkerLength = 0;
0064   fMaxOptionNameLength = 0;
0065   AddCommand("--help", Command::WithoutOption, "Print this help");
0066   AddCommand("-h", Command::WithoutOption, "Print this help");
0067   AddCommand("&", Command::WithoutOption);
0068 
0069   fVerbose = 0;
0070 }
0071 
0072 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0073 
0074 CommandLineParser* CommandLineParser::GetParser()
0075 {
0076   if (!fpInstance) new CommandLineParser;
0077   return fpInstance;
0078 }
0079 
0080 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0081 
0082 CommandLineParser::~CommandLineParser()
0083 {
0084   std::map<G4String, Command*>::iterator it = fCommandMap.begin();
0085   for (; it != fCommandMap.end(); it++) {
0086     if (it->second) delete it->second;
0087   }
0088 }
0089 
0090 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0091 
0092 void CommandLineParser::DeleteInstance()
0093 {
0094   if (fpInstance) {
0095     delete fpInstance;
0096     fpInstance = 0;
0097   }
0098 }
0099 
0100 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0101 
0102 Command::Command(Command::Type commandType, const G4String& description)
0103 {
0104   fType = commandType;
0105   fDescription = description;
0106   fActive = false;
0107 }
0108 
0109 CommandWithOption::CommandWithOption(Command::Type commandType, const G4String& description,
0110                                      const G4String& defaultOption, const G4String& optionName)
0111   : Command(commandType, description)
0112 {
0113   fDefaultOption = defaultOption;
0114   fOptionName = optionName;
0115   fOption = "";
0116 }
0117 
0118 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0119 
0120 int CommandLineParser::Parse(int& argc, char** argv)
0121 {
0122   //    G4cout << "Parse " << G4endl;
0123   static char null[1] = {""};
0124   int firstArgc = argc;
0125 
0126   for (int i = 1; i < firstArgc; i++) {
0127     Command* command = FindCommand(argv[i]);
0128     if (command == 0) continue;
0129 
0130     if (fVerbose) G4cout << "Command : " << argv[i] << G4endl;
0131 
0132     fOptionsWereSetup = true;
0133     command->fActive = true;
0134 
0135     G4String marker(argv[i]);
0136 
0137     if (strcmp(argv[i], "-h") != 0 && strcmp(argv[i], "--help") != 0) {
0138       argv[i] = null;
0139     }
0140 
0141     if (command->fType == Command::WithOption) {
0142       if (fVerbose) G4cout << "WithOption" << G4endl;
0143 
0144       if (i + 1 > firstArgc || argv[i + 1] == 0 || argv[i + 1][0] == '-') {
0145         G4cerr << "An command line option is missing for " << marker << G4endl;
0146         abort();
0147       }
0148 
0149       command->SetOption((const char*)strdup(argv[i + 1]));
0150       argv[i + 1] = null;
0151       i++;
0152     }
0153     else if (command->fType == Command::OptionNotCompulsory) {
0154       if (fVerbose) G4cout << "OptionNotCompulsory" << G4endl;
0155 
0156       if (i + 1 < firstArgc) {
0157         G4String buffer = (const char*)strdup(argv[i + 1]);
0158 
0159         if (buffer.empty() == false) {
0160           if (buffer.at(0) != '-' && buffer.at(0) != '&' && buffer.at(0) != '>'
0161               && buffer.at(0) != '|')
0162           {
0163             if (fVerbose) {
0164               G4cout << "facultative option is : " << buffer << G4endl;
0165             }
0166 
0167             command->SetOption((const char*)strdup(argv[i + 1]));
0168             argv[i + 1] = null;
0169             i++;
0170             continue;
0171           }
0172         }
0173       }
0174 
0175       if (fVerbose) G4cout << "Option not set" << G4endl;
0176 
0177       command->SetOption("");
0178     }
0179   }
0180   CorrectRemainingOptions(argc, argv);
0181 
0182   Command* commandLine(0);
0183   if ((commandLine = GetCommandIfActive("--help")) || (commandLine = GetCommandIfActive("-h"))) {
0184     G4cout << "Usage : " << argv[0] << " [OPTIONS]" << G4endl;
0185     PrintHelp();
0186     return 1;
0187   }
0188 
0189   return 0;
0190 }
0191 
0192 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0193 
0194 void CommandLineParser::PrintHelp()
0195 {
0196   std::map<G4String, Command*>::iterator it;
0197 
0198   int maxFieldLength = fMaxMarkerLength + fMaxOptionNameLength + 4;
0199 
0200   G4cout << "Options: " << G4endl;
0201 
0202   for (it = fCommandMap.begin(); it != fCommandMap.end(); it++) {
0203     Command* command = it->second;
0204     if (command) {
0205       G4cout << setw(maxFieldLength) << left;
0206 
0207       G4String toPrint = it->first;
0208 
0209       if (toPrint == "&") {
0210         continue;
0211       }
0212       else if (toPrint == "-h")
0213         continue;
0214       else if (toPrint == "--help") {
0215         toPrint += ", -h";
0216       }
0217 
0218       if (command->GetDefaultOption() != "") {
0219         toPrint += " \"" + command->GetDefaultOption() + "\"";
0220       }
0221 
0222       G4cout << toPrint;
0223 
0224       G4cout << command->GetDescription() << G4endl;
0225     }
0226   }
0227 }
0228 
0229 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0230 
0231 void CommandLineParser::CorrectRemainingOptions(int& argc, char** argv)
0232 {
0233   // remove handled arguments from argument array
0234   int j = 0;
0235   for (int i = 0; i < argc; i++) {
0236     if (strcmp(argv[i], "")) {
0237       argv[j] = argv[i];
0238       j++;
0239     }
0240   }
0241   argc = j;
0242 }
0243 
0244 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0245 
0246 void CommandLineParser::AddCommand(const G4String& marker, Command::Type type,
0247                                    const G4String& description, const G4String& defaultOption,
0248                                    const G4String& optionName)
0249 {
0250   // G4cout << "Add command : "<< marker << G4endl;
0251 
0252   Command* command = 0;
0253   switch (type) {
0254     case Command::WithoutOption:
0255       command = new Command(type, description);
0256       break;
0257 
0258     default:
0259       command = new CommandWithOption(type, description, defaultOption, optionName);
0260       if ((int)defaultOption.length() > fMaxOptionNameLength)
0261         fMaxOptionNameLength = defaultOption.length();
0262       break;
0263   }
0264 
0265   if ((int)marker.length() > fMaxMarkerLength) fMaxMarkerLength = marker.length();
0266   fCommandMap.insert(make_pair(marker, command));
0267 }
0268 
0269 /*
0270 // Add one command but multiple markers
0271 void Parser::AddCommand(vector<G4String> markers,
0272                         CommandType type,
0273                         const G4String& description,
0274                         const G4String& optionName)
0275 {
0276   // G4cout << "Add command : "<< marker << G4endl;
0277   Command* command = new Command(type, description, optionName);
0278 
0279   for (size_t i = 0; i < markers.size; i++)
0280   {
0281     G4String marker = markers[i];
0282     if ((int) marker.length() > fMaxMarkerLength)
0283     {
0284       fMaxMarkerLength = marker.length();
0285     }
0286     if ((int) optionName.length() > fMaxOptionNameLength)
0287     {
0288       fMaxOptionNameLength = optionName.length();
0289     }
0290     fCommandMap.insert(make_pair(marker, command));
0291   }
0292 }
0293 */
0294 
0295 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0296 
0297 Command* CommandLineParser::FindCommand(const G4String& marker)
0298 {
0299   std::map<G4String, Command*>::iterator it = fCommandMap.find(marker);
0300   if (it == fCommandMap.end()) {
0301     // G4cerr << "command not found" << G4endl;
0302     return 0;
0303   }
0304   return it->second;
0305 }
0306 
0307 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0308 
0309 Command* CommandLineParser::GetCommandIfActive(const G4String& marker)
0310 {
0311   Command* command = FindCommand(marker);
0312   if (command) {
0313     // G4cout << "Command found : "<< marker << G4endl;
0314 
0315     if (command->fActive) {
0316       // G4cout << "Command Active" << G4endl;
0317       return command;
0318     }
0319     // else
0320     //  G4cout <<"Command not active" << G4endl;
0321   }
0322   else {
0323     G4ExceptionDescription description;
0324     description << "You try to retrieve a command that was not registered : " << marker << G4endl;
0325     G4Exception("CommandLineParser::GetCommandIfActive", "COMMAND LINE NOT DEFINED", FatalException,
0326                 description, "");
0327     // If you are using this class outside of Geant4, use exit(-1) instead
0328     // exit(-1);
0329   }
0330   return 0;
0331 }
0332 
0333 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0334 
0335 bool CommandLineParser::CheckIfNotHandledOptionsExists(int& argc, char** argv)
0336 {
0337   if (argc > 0) {
0338     G4bool kill = false;
0339     for (G4int i = 1; i < argc; i++) {
0340       if (strcmp(argv[i], "")) {
0341         kill = true;
0342         G4cerr << "Unknown argument : " << argv[i] << "\n";
0343       }
0344     }
0345     if (kill) {
0346       G4cerr << "The option " << argv[0] << " is not handled this programme." << G4endl;
0347       G4cout << "Usage : " << argv[0] << " [OPTIONS]" << G4endl;
0348       PrintHelp();
0349       return true;  // KILL APPLICATION
0350     }
0351   }
0352   return false;
0353 }