~ubuntu-branches/ubuntu/wily/aspectc++/wily

« back to all changes in this revision

Viewing changes to Puma/gen-release/step2/src/Config.cc

  • Committer: Bazaar Package Importer
  • Author(s): Reinhard Tartler
  • Date: 2009-06-15 10:17:02 UTC
  • mfrom: (1.2.2 upstream)
  • Revision ID: james.westby@ubuntu.com-20090615101702-qsr30iptwbxylmo2
Tags: 1.0pre4~svn.20090615-1
* New upstream release.
* don't ignore errors in the postrm script
* avoid spurious creation of empty dir ./usr/sbin/
* improve short descriptions of libpuma-doc and libpuma-dev
* bump Standards-Version to 3.8.1
* bump debhelper compat level to level 7 (latest in stable)

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
// This file is part of PUMA.
2
2
// Copyright (C) 1999-2003  The PUMA developer team.
3
 
//                                                                
4
 
// This program is free software;  you can redistribute it and/or 
5
 
// modify it under the terms of the GNU General Public License as 
6
 
// published by the Free Software Foundation; either version 2 of 
7
 
// the License, or (at your option) any later version.            
8
 
//                                                                
 
3
//
 
4
// This program is free software;  you can redistribute it and/or
 
5
// modify it under the terms of the GNU General Public License as
 
6
// published by the Free Software Foundation; either version 2 of
 
7
// the License, or (at your option) any later version.
 
8
//
9
9
// This program is distributed in the hope that it will be useful,
10
 
// but WITHOUT ANY WARRANTY; without even the implied warranty of 
11
 
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the  
12
 
// GNU General Public License for more details.                   
13
 
//                                                                
14
 
// You should have received a copy of the GNU General Public      
15
 
// License along with this program; if not, write to the Free     
16
 
// Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, 
17
 
// MA  02111-1307  USA                                            
 
10
// but WITHOUT ANY WARRANTY; without even the implied warranty of
 
11
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
12
// GNU General Public License for more details.
 
13
//
 
14
// You should have received a copy of the GNU General Public
 
15
// License along with this program; if not, write to the Free
 
16
// Software Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 
17
// MA  02111-1307  USA
18
18
 
19
19
#include "Puma/Config.h"
20
20
#include "Puma/SysCall.h"
23
23
#include <stdlib.h>
24
24
#include <string.h>
25
25
#include <sstream>
 
26
#include <fstream>
26
27
 
27
28
 
28
29
namespace Puma {
37
38
   _err << sev_error << "at command line: "
38
39
 
39
40
#define ERROR_MSG(__mesg) \
40
 
   _err << __mesg << endMessage 
 
41
   _err << __mesg << endMessage
41
42
 
42
43
#define ERROR__missing(__name) \
43
44
   COMMAND_LINE; \
47
48
   COMMAND_LINE; \
48
49
   ERROR_MSG ("no " << __what << " given for `" << __name << "'")
49
50
 
50
 
// options:
51
 
// -A<PREDICATE>(<ANSWER>)                      // Assert a preprocessor predicate.
52
 
// -D<NAME>[=<BODY>]                            // Define a preprocessor macro.
53
 
// -U<NAME>                                     // Undefine a preprocessor macro.
54
 
// -I<PATH>                                     // Add a new include path.
55
 
//OLD: -p|--path <SRC> [<DEST>]                 // Add a new source dest paths pair.
56
 
// -p|--path <SRC>                              // Add a new source path.
57
 
// -d|--dest <DEST>                             // Add a new dest path.
58
 
// -w|--write-protected <PATH_PATTERN>          // Add a new write protected path.
59
 
// -s|--suffix <SUFFIX>                         // Set the file save suffix.
60
 
// -e|--extension <EXTENSION>                   // Set the extension for source files.
61
 
// --save-overwrite|rename-old|new-suffix       // set the file save mode
62
 
// --lang-c|ec++|c++|ac++                       // set the source code language
63
 
// --skip-bodies-all                            // skip parsing function bodies
64
 
// --skip-bodies-tpl                            // skip parsing function bodies of templates
65
 
// --skip-bodies-non-prj                        // skip parsing non-project function bodies
66
 
// --skip-bodies-non-prim                       // skip parsing function bodies in non-primary files
67
 
// --match-expr                                 // parse match expressions
68
 
// --vc                                         // support MS Visual C++ extensions
69
 
// --gnu                                        // support gnu extensions
70
 
// --gnu-2.95
71
 
// --gnu-std-hack
72
 
// --gnu-nested-fct
73
 
// --gnu-condition-scope
74
 
// --gnu-param-decl
75
 
// --gnu-fct-decl
76
 
// --gnu-param-scope
77
 
// --gnu-default-args
78
 
// --gnu-extended-asm
79
 
// --gnu-extended-expr
80
 
// --gnu-long-long
81
 
// --gnu-name-scope
82
 
// --gnu-implicit-int
83
 
// --gnu-fct-attribute
84
 
// --gnu-if-then-expr
85
51
 
86
52
OptsParser::Option pumaOpts[] = {
87
53
   {Config::PRE_ASSERT, "A", NULL, "Assert a preprocessor predicate", OptsParser::AT_MANDATORY},
88
54
   {Config::PRE_DEFINE, "D", NULL, "Define a preprocessor macro", OptsParser::AT_MANDATORY},
89
55
   {Config::PRE_UNDEFINE, "U", NULL, "Undefine a preprocessor macro", OptsParser::AT_MANDATORY},
90
 
   {Config::PRE_LOCK_MACRO, 0, "lock-macro", "Define an unchangeable preprocessor macro", OptsParser::AT_MANDATORY},
91
 
   {Config::PRE_INCLUDE, "I", NULL, "Add new include path", OptsParser::AT_MANDATORY},
92
 
   {Config::PROJ_PATH, "p", "path", "Path to project source", OptsParser::AT_MANDATORY},
93
 
   {Config::PROJ_DESTINATION, "d", "dest", "Path to destination for modified sources", OptsParser::AT_MANDATORY},
94
 
   {Config::SET_SUFFIX, "s", "suffix", "Set file save suffix", OptsParser::AT_MANDATORY},
 
56
   {Config::PRE_LOCK_MACRO, NULL, "lock-macro", "Define an immutable preprocessor macro", OptsParser::AT_MANDATORY},
 
57
   {Config::SET_OPTION_ARG, NULL, "inhibit-macro", "Add the name of a macro whose definition will be ignored", OptsParser::AT_MANDATORY},
 
58
   {Config::PRE_INCLUDE, "I", NULL, "Add an include directory", OptsParser::AT_MANDATORY},
 
59
   {Config::PROJ_PATH, "p", "path", "Add a project source directory", OptsParser::AT_MANDATORY},
 
60
   {Config::PROJ_DESTINATION, "d", "dest", "Add a destination folder for modified sources", OptsParser::AT_MANDATORY},
 
61
   {Config::SET_SUFFIX, "s", "suffix", "Set the suffix for output files", OptsParser::AT_MANDATORY},
95
62
   {Config::SET_EXTENSION, "e", "extension", "Set the extension for source files", OptsParser::AT_MANDATORY},
96
 
   {Config::SET_WRITE_PROTECTED, "w", "write-protected", "Add a new write protected path", OptsParser::AT_MANDATORY},
97
 
   {Config::CFG_FILE, NULL, "config", "Full path to a config file", OptsParser::AT_MANDATORY},
98
 
   {Config::SET_OPTION, NULL, "save-overwrite", "Overwrite old files", OptsParser::AT_NONE},
99
 
   {Config::SET_OPTION, NULL, "rename-old", "Rename old files", OptsParser::AT_NONE},
100
 
   {Config::SET_OPTION, NULL, "new-suffix", "Append new suffix on old files", OptsParser::AT_NONE},
101
 
   {Config::SET_OPTION, NULL, "lang-c", "Input language is C", OptsParser::AT_NONE},
102
 
   {Config::SET_OPTION, NULL, "lang-ec++", "Input language is EC++", OptsParser::AT_NONE},
103
 
   {Config::SET_OPTION, NULL, "lang-c++", "Input language is C++", OptsParser::AT_NONE},
104
 
   {Config::SET_OPTION, NULL, "lang-ac++", "Input language is AC++", OptsParser::AT_NONE},
 
63
   {Config::SET_WRITE_PROTECTED, "w", "write-protected", "Add a write protected project directory", OptsParser::AT_MANDATORY},
 
64
   {Config::CFG_FILE, NULL, "config", "Load configuration options from a file", OptsParser::AT_MANDATORY},
 
65
   {Config::SET_OPTION, NULL, "save-overwrite", "Overwrite existing files when saving", OptsParser::AT_NONE},
 
66
   {Config::SET_OPTION, NULL, "rename-old", "Rename existing files when saving", OptsParser::AT_NONE},
 
67
   {Config::SET_OPTION, NULL, "new-suffix", "Append new suffix on existing files when saving", OptsParser::AT_NONE},
 
68
   {Config::SET_OPTION, NULL, "lang-c", "Set input language to C", OptsParser::AT_NONE},
 
69
   {Config::SET_OPTION, NULL, "lang-ec++", "Set input language to EC++", OptsParser::AT_NONE},
 
70
   {Config::SET_OPTION, NULL, "lang-c++", "Set input language to C++", OptsParser::AT_NONE},
 
71
   {Config::SET_OPTION, NULL, "lang-ac++", "Set input language to AC++", OptsParser::AT_NONE},
 
72
   {Config::SET_OPTION, NULL, "vc", "Enable Visual C++ extensions", OptsParser::AT_NONE},
 
73
   {Config::GNU, NULL, "gnu", "Enable GNU extensions", OptsParser::AT_OPTIONAL},
 
74
   {Config::SET_OPTION, NULL, "gnu-nested-fct", "Enable GNU nested functions extension", OptsParser::AT_NONE},
 
75
   {Config::SET_OPTION, NULL, "gnu-condition-scope", "Enable GNU condition scope extension", OptsParser::AT_NONE},
 
76
   {Config::SET_OPTION, NULL, "gnu-param-decl", "Enable GNU parameter declaration extension", OptsParser::AT_NONE},
 
77
   {Config::SET_OPTION, NULL, "gnu-fct-decl", "Enable GNU function declaration extension", OptsParser::AT_NONE},
 
78
   {Config::SET_OPTION, NULL, "gnu-param-scope", "Enable GNU parameter scope extension", OptsParser::AT_NONE},
 
79
   {Config::SET_OPTION, NULL, "gnu-default-args", "Enable GNU default arguments extension", OptsParser::AT_NONE},
 
80
   {Config::SET_OPTION, NULL, "gnu-extended-asm", "Enable GNU extended asm declaration extension", OptsParser::AT_NONE},
 
81
   {Config::SET_OPTION, NULL, "gnu-extended-expr", "Enable GNU extended expression extension", OptsParser::AT_NONE},
 
82
   {Config::SET_OPTION, NULL, "gnu-long-long", "Enable GNU type long long extension", OptsParser::AT_NONE},
 
83
   {Config::SET_OPTION, NULL, "gnu-name-scope", "Enable GNU name scope extension", OptsParser::AT_NONE},
 
84
   {Config::SET_OPTION, NULL, "gnu-implicit-int", "Enable GNU implicit int extension", OptsParser::AT_NONE},
 
85
   {Config::SET_OPTION, NULL, "gnu-fct-attribute", "Enable GNU function attributes extension", OptsParser::AT_NONE},
 
86
   {Config::SET_OPTION, NULL, "gnu-if-then-expr", "Enable GNU if-then expression extension", OptsParser::AT_NONE},
 
87
   {Config::SET_OPTION, NULL, "gnu-std-hack", "Enable GNU std namespace extension", OptsParser::AT_NONE},
 
88
   {Config::SET_OPTION, NULL, "gnu-friend-injection", "Enable GNU friend injection extension", OptsParser::AT_NONE},
 
89
   {Config::SET_OPTION, NULL, "builtin-type-traits", "Enable built-in type traits", OptsParser::AT_NONE},
105
90
   {Config::SET_OPTION, NULL, "skip-bodies-all", "Skip parsing function bodies", OptsParser::AT_NONE},
106
91
   {Config::SET_OPTION, NULL, "skip-bodies-tpl", "Skip parsing function bodies of templates", OptsParser::AT_NONE},
107
92
   {Config::SET_OPTION, NULL, "skip-bodies-non-prj", "Skip parsing non-project function bodies", OptsParser::AT_NONE},
108
93
   {Config::SET_OPTION, NULL, "skip-bodies-non-prim", "Skip parsing function bodies in non-primary files", OptsParser::AT_NONE},
109
 
   {Config::SET_OPTION, NULL, "real-instances", "Do real template instantiation", OptsParser::AT_NONE},
110
 
   {Config::SET_OPTION, NULL, "match-expr", "Parse match expression", OptsParser::AT_NONE},
111
 
   {Config::SET_OPTION, NULL, "gnu-nested-fct", "", OptsParser::AT_NONE},
112
 
   {Config::SET_OPTION, NULL, "gnu-condition-scope", "", OptsParser::AT_NONE},
113
 
   {Config::SET_OPTION, NULL, "gnu-param-decl", "", OptsParser::AT_NONE},
114
 
   {Config::SET_OPTION, NULL, "gnu-fct-decl", "", OptsParser::AT_NONE},
115
 
   {Config::SET_OPTION, NULL, "gnu-param-scope", "", OptsParser::AT_NONE},
116
 
   {Config::SET_OPTION, NULL, "gnu-default-args", "", OptsParser::AT_NONE},
117
 
   {Config::SET_OPTION, NULL, "gnu-extended-asm", "", OptsParser::AT_NONE},
118
 
   {Config::SET_OPTION, NULL, "gnu-extended-expr", "", OptsParser::AT_NONE},
119
 
   {Config::SET_OPTION, NULL, "gnu-long-long", "", OptsParser::AT_NONE},
120
 
   {Config::SET_OPTION, NULL, "gnu-name-scope", "", OptsParser::AT_NONE},
121
 
   {Config::SET_OPTION, NULL, "gnu-implicit-int", "", OptsParser::AT_NONE},
122
 
   {Config::SET_OPTION, NULL, "gnu-fct-attribute", "", OptsParser::AT_NONE},
123
 
   {Config::SET_OPTION, NULL, "gnu-if-then-expr", "", OptsParser::AT_NONE},
124
 
   {Config::SET_OPTION, NULL, "gnu-std-hack", "", OptsParser::AT_NONE},
125
 
   {Config::SET_OPTION, NULL, "gnu", "Support gnu extensions", OptsParser::AT_NONE},
126
 
   {Config::SET_OPTION, NULL, "gnu-2.95", "Support gnu extensions for g++ 2.95", OptsParser::AT_NONE},
127
 
   {Config::SET_OPTION, NULL, "vc", "Support Visual C++ extensions", OptsParser::AT_NONE},
128
 
   {Config::SET_OPTION_ARG, NULL, "import-handler", "Handler for #import directives", OptsParser::AT_MANDATORY},
129
 
   {Config::SET_OPTION_ARG, NULL, "include", "Always include file", OptsParser::AT_MANDATORY},
130
 
   {Config::SET_OPTION_ARG, NULL, "size-type", "Internal type for size_t", OptsParser::AT_MANDATORY},
131
 
   {Config::SET_OPTION_ARG, NULL, "ptrdiff-type", "Internal type for ptrdiff_t", OptsParser::AT_MANDATORY},
132
 
   {Config::SET_OPTION_ARG, NULL, "inhibit-macro", "Prevent a preprocessor macro for being defined", OptsParser::AT_MANDATORY},
 
94
   {Config::SET_OPTION, NULL, "real-instances", "Enable template instantiation", OptsParser::AT_NONE},
 
95
   {Config::SET_OPTION_ARG, NULL, "template-depth", "Set the maximum instantiation depth for templates", OptsParser::AT_MANDATORY},
 
96
   {Config::SET_OPTION, NULL, "match-expr", "Enable parsing match expressions", OptsParser::AT_NONE},
 
97
   {Config::SET_OPTION_ARG, NULL, "import-handler", "Set handler for Visual C++ #import directives", OptsParser::AT_MANDATORY},
 
98
   {Config::SET_OPTION_ARG, NULL, "include", "Add file to be included at the beginning of every source file", OptsParser::AT_MANDATORY},
 
99
   {Config::SET_OPTION_ARG, NULL, "size-type", "Set type for size_t", OptsParser::AT_MANDATORY},
 
100
   {Config::SET_OPTION_ARG, NULL, "ptrdiff-type", "Set type for ptrdiff_t", OptsParser::AT_MANDATORY},
133
101
   {0, 0, 0, 0, OptsParser::AT_NONE}
134
102
};
135
103
 
136
104
 
 
105
// print the options
 
106
void Config::PrintOptions(std::ostream& os) const {
 
107
  // first print short options with description
 
108
  for (int i = 0; pumaOpts[i].number > 0; i++) {
 
109
    if (pumaOpts[i].shortName && pumaOpts[i].desc && strlen(pumaOpts[i].desc)) {
 
110
      PrintOption(pumaOpts[i], os);
 
111
    }
 
112
  }
 
113
  // then print long options with description
 
114
  for (int i = 0; pumaOpts[i].number > 0; i++) {
 
115
    if (! pumaOpts[i].shortName && pumaOpts[i].desc && strlen(pumaOpts[i].desc)) {
 
116
      PrintOption(pumaOpts[i], os);
 
117
    }
 
118
  }
 
119
  // then print options without description
 
120
  for (int i = 0; pumaOpts[i].number > 0; i++) {
 
121
    if (! pumaOpts[i].desc || strlen(pumaOpts[i].desc)==0) {
 
122
      PrintOption(pumaOpts[i], os);
 
123
    }
 
124
  }
 
125
}
 
126
 
 
127
 
 
128
// print a single option
 
129
void Config::PrintOption(OptsParser::Option& o, std::ostream& os) const {
 
130
  if (o.shortName) {
 
131
    os << "  -" << o.shortName;
 
132
  }
 
133
  if (o.longName) {
 
134
    if (o.shortName) {
 
135
      os << "|";
 
136
    } else {
 
137
      os << "  ";
 
138
    }
 
139
    os << "--" << o.longName;
 
140
  }
 
141
  if (o.argType == OptsParser::AT_MANDATORY) {
 
142
    os << " <ARG>";
 
143
  }
 
144
  if (o.argType == OptsParser::AT_OPTIONAL) {
 
145
    os << " [ARG]";
 
146
  }
 
147
  if (o.desc) {
 
148
    os << "\033[35G" << o.desc;
 
149
  }
 
150
  os << std::endl;
 
151
}
 
152
 
 
153
 
137
154
void Config::Read (const char *file) {
138
 
  FileHandle fp;
139
 
  char buffer[4096];
140
 
  string optstr ("");
141
 
 
142
155
  // file not given, read from $PUMA_CONFIG or /etc/puma.config
 
156
  bool default_loc = false;
143
157
  if (! file)
144
 
    file = getenv ("PUMA_CONFIG");
145
 
    
146
 
  if (file) {
147
 
    if ((fp = SysCall::fopen (file, "r")) == NULL) {
148
 
      ERROR_MSG ("cannot open config file `" << file << "'");
149
 
      return;
150
 
    }
151
 
  } else {
 
158
    file = getenv("PUMA_CONFIG");
 
159
  if (! file) {
152
160
    file = "/etc/puma.config"; // default location
153
 
    if ((fp = SysCall::fopen (file, "r")) == NULL) {
154
 
      return;
155
 
    }
156
 
  }
157
 
  
158
 
  while (fgets (buffer, 4000, fp)) {
159
 
    // skip comments and newlines
160
 
    if (buffer[0] != '#' || buffer[0] != '\n') {
161
 
      optstr += " ";
162
 
      optstr += buffer;
163
 
    }
164
 
  }
165
 
 
166
 
  SysCall::fclose (fp, &_err);
167
 
 
168
 
  OptsParser optp (optstr, pumaOpts);
 
161
    default_loc = true;
 
162
  }
 
163
 
 
164
  std::ifstream in(file);
 
165
  if (! in) {
 
166
    if (! default_loc) {
 
167
      ERROR_MSG("cannot open config file `" << file << "'");
 
168
    }
 
169
    return;
 
170
  }
 
171
 
 
172
  std::ostringstream optstr;
 
173
  std::string line;
 
174
  while (! in.eof()) {
 
175
    std::getline(in, line);
 
176
    // skip comments and empty lines
 
177
    if (! line.empty() && line[0] != '#') {
 
178
      ReplaceEnvVars(line);
 
179
      optstr << " " << line;
 
180
    }
 
181
  }
 
182
  in.close();
 
183
 
 
184
  OptsParser optp(optstr.str(), pumaOpts);
169
185
 
170
186
  // process the given options
171
187
  while (optp.getOption () != OptsParser::FINISH) {
172
 
    Process (optp, true);
 
188
    Process(optp, true);
173
189
  }
174
190
}
175
191
 
179
195
  OptsParser optp (argc, argv, pumaOpts);
180
196
  char** newargv = new char*[argc];
181
197
  int    newargc = 1;
182
 
        
 
198
 
183
199
  // process the given options
184
200
  while (optp.getOption () != OptsParser::FINISH) {
185
201
    if (Process (optp) == false) {
186
202
      // this is not processed by PUMA - copy
187
203
      newargv[newargc++] = argv[optp.getCurrentArgNum ()];
188
 
      //cout << "add to newargv: " << argv[optp.getCurrentArgNum()] << endl;
189
204
    }
190
205
  }
191
 
        
 
206
 
192
207
  // make argv point to new argv and set argc to value of new argc
193
208
  argc = newargc;
194
209
  for (int i = 1; i < argc; i++)
197
212
}
198
213
 
199
214
 
 
215
// replace environment variables of the form ${ENVVAR}
 
216
std::string& Config::ReplaceEnvVars(std::string& s) const {
 
217
  std::string::size_type varbegin = 0, varend = 0;
 
218
 
 
219
  // find first opening parenthesis
 
220
  varbegin = s.find("${", 0);
 
221
  while (varbegin != std::string::npos) {
 
222
 
 
223
    // find closing parenthesis
 
224
    varend = s.find("}", varbegin+2);
 
225
    if (varend != std::string::npos) {
 
226
 
 
227
      // check if '$' is protected by a backslash
 
228
      std::string::size_type pos = varbegin, even = 1;
 
229
      while (pos > 0 ? s.at(--pos)=='\\' : (even=0));
 
230
      if ((varbegin-pos)%2 != even) {
 
231
        // odd number of backslashes, do not replace, but remove last backslash
 
232
        s.erase(varbegin-1, 1);
 
233
        varend = varbegin;
 
234
      } else {
 
235
        // get the value of the environment variable
 
236
        const char* vstr = getenv(s.substr(varbegin+2, varend-varbegin-2).c_str());
 
237
        std::string value = vstr ? vstr : "";
 
238
        // replace the variable with its value
 
239
        s.replace(varbegin, varend-varbegin+1, value);
 
240
        varend = varbegin + value.length();
 
241
      }
 
242
      // find next variable
 
243
      varbegin = s.find("${", varend);
 
244
 
 
245
    } else {
 
246
      // end of string
 
247
      varbegin = std::string::npos;
 
248
    }
 
249
  }
 
250
  return s;
 
251
}
 
252
 
 
253
 
200
254
bool Config::Process (OptsParser &parser, bool unescape) {
201
 
  bool res=true;
202
 
  string arg;
203
 
  if (unescape) {
204
 
    arg = Unescape (parser.getArgument ());
205
 
  } else {
206
 
    arg = parser.getArgument ();
207
 
  }
208
 
        
 
255
  bool res = true;
 
256
  string arg = parser.getArgument ();
 
257
  if (! arg.empty () && unescape)
 
258
    arg = Unescape (arg);
 
259
 
209
260
  switch (parser.getResult ()) {
210
261
    case PRE_ASSERT:
211
262
      ProcessAssert (arg);
226
277
      ProcessPathArgument ("-p", arg);
227
278
      break;
228
279
    case PROJ_DESTINATION:
229
 
      ProcessPathArgument ("-d", arg);                        
 
280
      ProcessPathArgument ("-d", arg);
230
281
      break;
231
282
    case CFG_FILE:
232
283
      ProcessConfigFile ("--config", arg);
240
291
    case SET_WRITE_PROTECTED:
241
292
      ProcessArgument ("-w", arg);
242
293
      break;
 
294
    case GNU:
 
295
      ProcessOptionalArgument ("--gnu", arg);
 
296
      break;
243
297
    case SET_OPTION:
244
 
      //cout << "option: " << parser.getOptionName() << endl;
245
298
      Add (parser.getOptionName ().c_str ());
246
299
      break;
247
300
    case SET_OPTION_ARG:
248
 
      //cout << "option: " << parser.getOptionName() << endl;
249
301
      Add (parser.getOptionName ().c_str (), arg.c_str ());
250
302
      break;
251
303
    case OptsParser::UNKNOWN:
267
319
    Read (arg.c_str ());
268
320
    //cout << opt << " " << arg << endl;
269
321
    res = true;
270
 
  } else { 
271
 
    ERROR__empty ("file name", opt.c_str ()); 
 
322
  } else {
 
323
    ERROR__empty ("file name", opt.c_str ());
272
324
  }
273
 
        
 
325
 
274
326
  return res;
275
327
}
276
328
 
282
334
    Add (opt.c_str (), arg.c_str ());
283
335
    //cout << opt << " " << arg << endl;
284
336
    res = true;
285
 
  } else { 
286
 
    ERROR__empty ("argument", opt.c_str ()); 
287
 
  }
288
 
        
 
337
  }
 
338
  else {
 
339
    ERROR__empty ("argument", opt.c_str ());
 
340
  }
289
341
  return res;
290
342
}
291
343
 
292
344
 
 
345
bool Config::ProcessOptionalArgument (const string &opt, const string &arg) {
 
346
  if (arg.empty ()) {
 
347
    Add (opt.c_str ());
 
348
    //cout << opt << endl;
 
349
  }
 
350
  else {
 
351
    Add (opt.c_str (), arg.c_str ());
 
352
    // TODO: better check valid version string syntax here
 
353
    //cout << opt << " " << arg << endl;
 
354
  }
 
355
  return true;
 
356
}
 
357
 
 
358
 
293
359
bool Config::ProcessPathArgument (const string &opt, const string &arg) {
294
360
  bool res = false;
295
361
 
300
366
      SysCall::MakeUnixPath (tmp);
301
367
      Add (opt.c_str (), tmp);
302
368
      delete[] tmp;
303
 
    }                
 
369
    }
304
370
#else
305
371
    Add (opt.c_str (), arg.c_str ());
306
372
    //cout << opt << " " << arg << endl;
307
373
    res = true;
308
374
#endif
309
 
  } else { 
310
 
    ERROR__empty ("argument", opt.c_str ()); 
 
375
  } else {
 
376
    ERROR__empty ("argument", opt.c_str ());
311
377
  }
312
 
        
 
378
 
313
379
  return res;
314
380
}
315
381
 
321
387
    Add ("-U", arg.c_str ());
322
388
    //cout << "-U " << arg << endl;
323
389
    res = true;
324
 
  } else { 
325
 
    ERROR_MSG ("invalid name for -U"); 
 
390
  } else {
 
391
    ERROR_MSG ("invalid name for -U");
326
392
  }
327
 
        
 
393
 
328
394
  return res;
329
395
}
330
396
 
341
407
    body = "1";
342
408
    name = arg;
343
409
  }
344
 
        
 
410
 
345
411
  if (Valid (name.c_str ())) {
346
412
    Add ("-D", name.c_str (), body.c_str ());
347
413
    //cout << "-D " << name << "=" << body << endl;
348
414
    res = true;
349
 
  } else { 
350
 
    ERROR_MSG ("invalid name for -D"); 
 
415
  } else {
 
416
    ERROR_MSG ("invalid name for -D");
351
417
  }
352
 
        
 
418
 
353
419
  return res;
354
420
}
355
421
 
366
432
    body = "1";
367
433
    name = arg;
368
434
  }
369
 
        
 
435
 
370
436
  if (Valid (name.c_str ())) {
371
437
    Add ("--lock-macro", name.c_str (), body.c_str ());
372
438
    //cout << "--lock-macro " << name << "=" << body << endl;
373
439
    res = true;
374
 
  } else { 
375
 
    ERROR_MSG ("invalid name for --lock-macro"); 
 
440
  } else {
 
441
    ERROR_MSG ("invalid name for --lock-macro");
376
442
  }
377
 
        
 
443
 
378
444
  return res;
379
445
}
380
446
 
383
449
  bool res = false;
384
450
  string::size_type pos, end;
385
451
  string name, body;
386
 
        
 
452
 
387
453
  if ((pos = arg.find_first_of ('(',0)) != string::npos) {
388
454
    if ((end = arg.find_first_of (')',pos)) != string::npos) {
389
455
      name = arg.substr (0, pos);
393
459
          Add ("-A", name.c_str (), body.c_str ());
394
460
          //cout << "-A " << name << "(" << body << ")" << endl;
395
461
          res = true;
396
 
        } else { 
397
 
          ERROR_MSG  ("invalid name for -A"); 
 
462
        } else {
 
463
          ERROR_MSG  ("invalid name for -A");
398
464
        }
399
 
      } else { 
400
 
        ERROR__empty ("answer text", "-A"); 
 
465
      } else {
 
466
        ERROR__empty ("answer text", "-A");
401
467
      }
402
 
    } else { 
403
 
      ERROR__missing (")"); 
 
468
    } else {
 
469
      ERROR__missing (")");
404
470
    }
405
 
  } else { 
406
 
    ERROR__missing ("("); 
 
471
  } else {
 
472
    ERROR__missing ("(");
407
473
  }
408
474
 
409
475
  return res;
417
483
        ! (*name >= '0' && *name <= '9'))
418
484
      return true;
419
485
  }
420
 
  if (file) 
 
486
  if (file)
421
487
    CONFIG_FILE;
422
 
  else 
 
488
  else
423
489
    COMMAND_LINE;
424
490
  ERROR_MSG ("`" << name << "' is not a valid C identifier");
425
491
  return false;
434
500
 
435
501
 
436
502
const ConfOption *Config::Option (const char *name) const {
 
503
  const ConfOption* co = 0;
437
504
  if (name) {
438
 
    for (unsigned i = Options (); i > 0; i--) {
439
 
      const ConfOption *o = Option (i-1);
440
 
      if (! strcmp (o->Name (), name))
441
 
        return o;
 
505
    OptionMap::const_iterator idx = _optnamemap.find(name);
 
506
    if (idx != _optnamemap.end()) {
 
507
      co = idx->second;
442
508
    }
443
509
  }
444
 
  return (const ConfOption*)0;
 
510
  return co;
445
511
}
446
512
 
447
513
 
448
514
string Config::Unescape (const string& arg) {
449
515
  // Replacement rules:
450
516
  // 1. '\' '"' => '"'
451
 
  // 2. '\' '\' => '\' 
 
517
  // 2. '\' '\' => '\'
452
518
  // 3. '"'     => ''
453
519
  ostringstream res;
454
520
  bool escaped = false;
458
524
      if (escaped) {
459
525
        escaped = false;
460
526
        res << c;
461
 
      } 
 
527
      }
462
528
    } else if (c == '\\') {
463
529
      if (escaped) {
464
530
        escaped = false;