1 #include "configuration_manager.hh"
7 * This constructor makes a new configuration_manager ready to use.
8 *\arg name Name of the application as mentioned in the
9 * "Use: <appname> ..." help message.
11 configuration_manager::configuration_manager(string name
){
17 *\brief Add a new configuration value to be searched for.
18 *\param shortname A character for the short form.
19 * For example the h in -h
20 *\param longname The double dash longname. For example
21 * input_file in --input_file= or
22 *\param description A detailed description of the value.
23 *\param status Pointer to an integer. Will be set to 1 if arg found.
24 *\target Pointer to to string to put the value in.
25 *\placeholder A placeholder for the documentation.
26 * For example <filename> in -f<filename>
28 void configuration_manager::add_option_value (string shortname
, string longname
,
33 string
* target
, string placeholder
){
35 if(status
!=NULL
) option_values
.insert(opt_v
.end(),
36 opt_value_t(shortname
,longname
, description
,
37 status
,target
,placeholder
)
43 *\brief Add an accepted argument to the argument reader.
44 *\param placeholder Something like "<input-file>".
45 *\param description Text describing the argument.
46 *\param status A pointer to a status variable. Will be set to 0 immediately.
47 * If the argument is filled in, it will be set to 1.
48 *\param target A pointer to a c++ string where the argument goes to.
50 *\note Arguments are filled in the order of adding them to the
52 * There would be no other way to determine the order.
54 void configuration_manager::add_argument(string placeholder
, string description
, int * status
, string
* target
){
55 if (target
!=NULL
) if(status
!=NULL
)
56 arg_v
.insert(arg_v
.end(),arg_t(placeholder
,description
,status
,target
));
61 *\Read in the args passed to main().
62 *\returns empty vector on success or the error messages to be output.
64 vector
<string
> configuration_manager::read_args(int argc
, char ** args
){
65 vector
<string
> result
;
67 for (char ** akt
=args
; *akt
;akt
++) argv
.insert(argv
.end(),string(*akt
));
69 unsigned int free_parms_count
=0;
70 for (vector
<string
>::iterator akt_p
=argv
.begin()+1;akt_p
<argv
.end();akt_p
++){ //Argument loop
72 // Look for long argument
73 if ((akt_p
->substr(0,2)=="--")&&(free_parms_count
==0)){
75 for (vector
<opt_t
>::iterator parm_p
=opt_v
.begin();parm_p
<opt_v
.end();parm_p
++){
76 if (akt_p
->substr(2,parm_p
->longname
.length())==parm_p
->longname
){
80 if (akt_p
->length()>2+parm_p
->longname
.length()){
81 *(parm_p
->target
)=akt_p
->substr(2+parm_p
->longname
.length());
83 } else // Word not long enough
84 if (akt_p
+1<argv
.end()) { // If next word existend
86 *(parm_p
->target
)=*(++akt_p
);
87 } else { // No next word :-(
88 result
.insert(result
.end(),
89 "Parameter --"+parm_p
->longname
+parm_p
->placeholder
+" needs an Argument!");
94 if (!found
) result
.insert(result
.end(),"Unknown parameter: "+*akt_p
);
95 } else { // No -- param, now look for switches
96 if (((*akt_p
)[0]=='-')&&(free_parms_count
==0)){
98 for (unsigned int pos
=1; pos
<akt_p
->length()&& !stop_char_loop
;pos
++){
100 for (vector
<opt_t
>::iterator parm_p
=opt_v
.begin();parm_p
<opt_v
.end();parm_p
++){
101 if (parm_p
->shortname
[0]==(*akt_p
)[pos
]){
104 if (parm_p
->target
){ // Need argument
105 if (akt_p
->length()>pos
+1){
106 *(parm_p
->target
)=akt_p
->substr(pos
+1);
108 } else { // Word not long enough
109 if (akt_p
+1<argv
.end()) { // If next word existend
110 *(parm_p
->target
)=*(++akt_p
);
112 } else { // No next word :-(
113 result
.insert(result
.end(),
114 "Parameter --"+parm_p
->longname
+parm_p
->placeholder
+" needs an Argument!");
120 if (!found
) result
.insert(result
.end(),"Unknown switch: "+akt_p
->substr(pos
,1));
123 else{ // no switch found
124 if (free_parms_count
<arg_v
.size()){
125 *(arg_v
[free_parms_count
].target
)=*akt_p
;
126 *(arg_v
[free_parms_count
].status
)=1;
130 } //looking for not -- args
132 if (free_parms_count
>arg_v
.size()) result
.insert(result
.begin(),"Too many arguments!");
133 if (!result
.empty()){
134 result
.insert(result
.begin(),"Error!");
135 result
.insert(result
.begin(),"");
141 *\brief Generate help.
142 *\arg target Reference to a vector<string> to which lots of helpful
143 * strings are appended.
145 void configuration_manager::get_help(vector
<string
> & target
){
146 target
.insert(target
.end(),"");
147 string line
="Usage: "+app_name
;
148 for (vector
<opt_t
>::iterator parm_p
=opt_v
.begin();parm_p
<opt_v
.end();parm_p
++){
149 string addstr
=" [-"+parm_p
->shortname
;
150 if (parm_p
->target
!=0) addstr
+=parm_p
->placeholder
;
152 if (line
.length()+addstr
.length()>79){
153 target
.insert(target
.end(),line
);
154 line
=string(7+app_name
.length(),' ');
159 for (vector
<arg_t
>::iterator parm_p
=arg_v
.begin();parm_p
<arg_v
.end();parm_p
++){
160 if (line
.length()+parm_p
->placeholder
.length()>79){
161 target
.insert(target
.end(),line
);
162 line
=string(7+app_name
.length(),' ');
164 line
+=" ["+parm_p
->placeholder
+"]";
166 target
.insert(target
.end(),line
);
168 /*******************************/
170 vector
<string
> left
,right
;
171 for (vector
<opt_t
>::iterator parm_p
=opt_v
.begin();parm_p
<opt_v
.end();parm_p
++){
172 line
=parm_p
->description
;
173 string st2
=" -"+parm_p
->shortname
;
174 if (parm_p
->target
)st2
+=" "+parm_p
->placeholder
;
175 st2
+=", --"+parm_p
->longname
;
176 if (parm_p
->target
)st2
+=parm_p
->placeholder
;
177 left
.insert(left
.end(),st2
);
178 right
.insert(right
.end(),line
);
181 for (vector
<arg_t
>::iterator parm_p
=arg_v
.begin();parm_p
<arg_v
.end();parm_p
++){
183 line
=parm_p
->description
;
184 st2
+=" "+parm_p
->placeholder
;
185 left
.insert(left
.end(),st2
);
186 right
.insert(right
.end(),line
);
190 target
.insert(target
.end(),"");
191 target
.insert(target
.end(),"Options:");
194 unsigned int max_width
=0;
195 for (unsigned int c
=0; c
<opt_v
.size();c
++)
196 if(left
[c
].length()>max_width
) max_width
=left
[c
].length();
197 for (unsigned int c
=0; c
<opt_v
.size();c
++){
198 string
nl(max_width
,' ');
199 nl
.replace(0,left
[c
].length(),left
[c
]);
201 while (nl
.length()>80){ // Too long???
202 int limit
=nl
.find_last_of(' ',80);
203 target
.insert(target
.end(),nl
.substr(0,limit
));
204 nl
=string(max_width
+2,' ')+nl
.substr(limit
+1);
206 target
.insert(target
.end(),nl
);
210 target
.insert(target
.end(),"");
211 target
.insert(target
.end(),"Arguments:");
215 for (unsigned int c
=opt_v
.size(); c
<opt_v
.size()+arg_v
.size();c
++)
216 if(left
[c
].length()>max_width
) max_width
=left
[c
].length();
217 for (unsigned int c
=opt_v
.size(); c
<opt_v
.size()+arg_v
.size();c
++){
218 string
nl(max_width
,' ');
219 nl
.replace(0,left
[c
].length(),left
[c
]);
222 while (nl
.length()>80){ // Too long???
223 int limit
=nl
.find_last_of(' ',80);
224 printf("limit:%i\n",limit
);
225 target
.insert(target
.end(),nl
.substr(0,limit
));
226 nl
=string(max_width
+2,' ')+nl
.substr(limit
+1);
229 target
.insert(target
.end(),nl
);
231 target
.insert(target
.end(),"");
235 *\brief Generate help.
236 *\return A vector containing many helpful strings for the user.
238 vector
<string
> configuration_manager::get_help(){
239 vector
<string
> result
;
245 /**************************************************/
247 configuration_manager::opt_t::opt_t(string n_shortname
, string n_longname
,string n_description
, int * n_status
,
248 string
* n_target
, string n_placeholder
){
249 shortname
=n_shortname
;
251 description
=n_description
;
254 placeholder
=n_placeholder
;
255 if (status
) *status
=0;
258 configuration_manager::arg_t::arg_t( string n_placeholder
, string n_description
,
259 int * n_status
, string
* n_target
){
260 description
=n_description
;
263 placeholder
=n_placeholder
;
264 if (status
) *status
=0;