llvm.org GIT mirror llvm / c48ef2a
lib/Support/CommandLine.cpp: Many changes suggested by Chris. It's okay, I'll recover from the emotional damage...maybe someday. :-) Collapse ParseCStringVector into ParseStringVector. Comment it. Make it take a const input. Use std::string::npos instead of -1 (what a mouthful!) Make ParseEnvironmentOptions take const inputs. Check its args at the very beginning. Strdup all the contents of newArgv and free them all at the end. include/Support/CommandLine.h: Constify progName and envVar arguments to ParseEnvironmentOptions(). git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@7905 91177308-0d34-0410-b5e6-96231b3b80d8 Brian Gaeke 17 years ago
4 changed file(s) with 110 addition(s) and 100 deletion(s). Raw diff Collapse all Expand all
3434 // ParseEnvironmentOptions - Environment variable option processing alternate
3535 // entry point.
3636 //
37 void ParseEnvironmentOptions(char *progName, char *envvar,
37 void ParseEnvironmentOptions(const char *progName, const char *envvar,
3838 const char *Overview = 0);
3939
4040 //===----------------------------------------------------------------------===//
3434 // ParseEnvironmentOptions - Environment variable option processing alternate
3535 // entry point.
3636 //
37 void ParseEnvironmentOptions(char *progName, char *envvar,
37 void ParseEnvironmentOptions(const char *progName, const char *envvar,
3838 const char *Overview = 0);
3939
4040 //===----------------------------------------------------------------------===//
151151 O->getNumOccurrencesFlag() == cl::OneOrMore;
152152 }
153153
154 /// ParseStringVector - Break INPUT up wherever one or more characters
155 /// from DELIMS are found, and store the resulting tokens in OUTPUT.
154 /// ParseCStringVector - Break INPUT up wherever one or more
155 /// whitespace characters are found, and store the resulting tokens in
156 /// OUTPUT. The tokens stored in OUTPUT are dynamically allocated
157 /// using strdup (), so it is the caller's responsibility to free ()
158 /// them later.
156159 ///
157 static void ParseStringVector (std::vector &output,
158 std::string &input, const char *delims) {
160 static void ParseCStringVector (std::vector &output,
161 const char *input) {
162 // Characters which will be treated as token separators:
163 static const char *delims = " \v\f\t\r\n";
164
159165 std::string work (input);
160 int pos = work.find_first_not_of (delims);
161 if (pos == -1) return;
166 // Skip past any delims at head of input string.
167 size_t pos = work.find_first_not_of (delims);
168 // If the string consists entirely of delims, then exit early.
169 if (pos == std::string::npos) return;
170 // Otherwise, jump forward to beginning of first word.
162171 work = work.substr (pos);
172 // Find position of first delimiter.
163173 pos = work.find_first_of (delims);
164 while (!work.empty() && pos != -1) {
165 if (pos == -1) break;
166 output.push_back (work.substr (0,pos));
167 int nextpos = work.find_first_not_of (delims, pos + 1);
168 if (nextpos != -1) {
174
175 while (!work.empty() && pos != std::string::npos) {
176 // Everything from 0 to POS is the next word to copy.
177 output.push_back (strdup (work.substr (0,pos).c_str ()));
178 // Is there another word in the string?
179 size_t nextpos = work.find_first_not_of (delims, pos + 1);
180 if (nextpos != std::string::npos) {
181 // Yes? Then remove delims from beginning ...
169182 work = work.substr (work.find_first_not_of (delims, pos + 1));
183 // and find the end of the word.
170184 pos = work.find_first_of (delims);
171185 } else {
186 // No? (Remainder of string is delims.) End the loop.
172187 work = "";
173 pos = -1;
174 }
175 }
188 pos = std::string::npos;
189 }
190 }
191
192 // If `input' ended with non-delim char, then we'll get here with
193 // the last word of `input' in `work'; copy it now.
176194 if (!work.empty ()) {
177 output.push_back (work);
178 }
179 }
180
181 /// ParseCStringVector - Same effect as ParseStringVector, but the
182 /// resulting output vector contains dynamically-allocated pointers to
183 /// char, instead of standard C++ strings.
184 ///
185 static void ParseCStringVector (std::vector &output,
186 std::string &input, const char *delims) {
187 std::vector work;
188 ParseStringVector (work, input, delims);
189 for (std::vector::iterator i = work.begin(), e = work.end();
190 i != e; ++i) {
191 output.push_back (strdup (i->c_str ()));
195 output.push_back (strdup (work.c_str ()));
192196 }
193197 }
194198
197201 /// from the caller (as PROGNAME) and its command-line arguments from
198202 /// an environment variable (whose name is given in ENVVAR).
199203 ///
200 void cl::ParseEnvironmentOptions (char *progName, char *envvar,
204 void cl::ParseEnvironmentOptions (const char *progName, const char *envVar,
201205 const char *Overview) {
206 // Check args.
207 assert (progName && "Program name not specified");
208 assert (envVar && "Environment variable name missing");
209
210 // Get the environment variable they want us to parse options out of.
211 const char *envValue = getenv (envVar);
212 if (!envValue)
213 return;
214
202215 // Get program's "name", which we wouldn't know without the caller
203216 // telling us.
204 assert (progName && "Program name not specified");
205 static std::vector newargv; // Maybe making it "static" is a hack.
206 int newargc;
207 newargv.push_back (progName);
208
209 // Get the environment variable they want us to parse options out of.
210 assert (envvar && "Environment variable name missing");
211 char *envvalue = getenv (envvar);
212 if (envvalue == NULL) {
213 // Env var not set --> act like there are no more command line
214 // arguments.
215 newargc = newargv.size ();
216 ParseCommandLineOptions (newargc, &newargv[0], Overview);
217 return;
218 }
219 std::string envvaluestr (envvalue);
217 std::vector newArgv;
218 newArgv.push_back (strdup (progName));
220219
221220 // Parse the value of the environment variable into a "command line"
222221 // and hand it off to ParseCommandLineOptions().
223 ParseCStringVector (newargv, envvaluestr, " \v\f\t\r\n");
224 newargc = newargv.size ();
225 ParseCommandLineOptions (newargc, &newargv[0], Overview);
222 ParseCStringVector (newArgv, envValue);
223 int newArgc = newArgv.size ();
224 ParseCommandLineOptions (newArgc, &newArgv[0], Overview);
225
226 // Free all the strdup()ed strings.
227 for (std::vector::iterator i = newArgv.begin (), e = newArgv.end ();
228 i != e; ++i) {
229 free (*i);
230 }
226231 }
227232
228233 void cl::ParseCommandLineOptions(int &argc, char **argv,
151151 O->getNumOccurrencesFlag() == cl::OneOrMore;
152152 }
153153
154 /// ParseStringVector - Break INPUT up wherever one or more characters
155 /// from DELIMS are found, and store the resulting tokens in OUTPUT.
154 /// ParseCStringVector - Break INPUT up wherever one or more
155 /// whitespace characters are found, and store the resulting tokens in
156 /// OUTPUT. The tokens stored in OUTPUT are dynamically allocated
157 /// using strdup (), so it is the caller's responsibility to free ()
158 /// them later.
156159 ///
157 static void ParseStringVector (std::vector &output,
158 std::string &input, const char *delims) {
160 static void ParseCStringVector (std::vector &output,
161 const char *input) {
162 // Characters which will be treated as token separators:
163 static const char *delims = " \v\f\t\r\n";
164
159165 std::string work (input);
160 int pos = work.find_first_not_of (delims);
161 if (pos == -1) return;
166 // Skip past any delims at head of input string.
167 size_t pos = work.find_first_not_of (delims);
168 // If the string consists entirely of delims, then exit early.
169 if (pos == std::string::npos) return;
170 // Otherwise, jump forward to beginning of first word.
162171 work = work.substr (pos);
172 // Find position of first delimiter.
163173 pos = work.find_first_of (delims);
164 while (!work.empty() && pos != -1) {
165 if (pos == -1) break;
166 output.push_back (work.substr (0,pos));
167 int nextpos = work.find_first_not_of (delims, pos + 1);
168 if (nextpos != -1) {
174
175 while (!work.empty() && pos != std::string::npos) {
176 // Everything from 0 to POS is the next word to copy.
177 output.push_back (strdup (work.substr (0,pos).c_str ()));
178 // Is there another word in the string?
179 size_t nextpos = work.find_first_not_of (delims, pos + 1);
180 if (nextpos != std::string::npos) {
181 // Yes? Then remove delims from beginning ...
169182 work = work.substr (work.find_first_not_of (delims, pos + 1));
183 // and find the end of the word.
170184 pos = work.find_first_of (delims);
171185 } else {
186 // No? (Remainder of string is delims.) End the loop.
172187 work = "";
173 pos = -1;
174 }
175 }
188 pos = std::string::npos;
189 }
190 }
191
192 // If `input' ended with non-delim char, then we'll get here with
193 // the last word of `input' in `work'; copy it now.
176194 if (!work.empty ()) {
177 output.push_back (work);
178 }
179 }
180
181 /// ParseCStringVector - Same effect as ParseStringVector, but the
182 /// resulting output vector contains dynamically-allocated pointers to
183 /// char, instead of standard C++ strings.
184 ///
185 static void ParseCStringVector (std::vector &output,
186 std::string &input, const char *delims) {
187 std::vector work;
188 ParseStringVector (work, input, delims);
189 for (std::vector::iterator i = work.begin(), e = work.end();
190 i != e; ++i) {
191 output.push_back (strdup (i->c_str ()));
195 output.push_back (strdup (work.c_str ()));
192196 }
193197 }
194198
197201 /// from the caller (as PROGNAME) and its command-line arguments from
198202 /// an environment variable (whose name is given in ENVVAR).
199203 ///
200 void cl::ParseEnvironmentOptions (char *progName, char *envvar,
204 void cl::ParseEnvironmentOptions (const char *progName, const char *envVar,
201205 const char *Overview) {
206 // Check args.
207 assert (progName && "Program name not specified");
208 assert (envVar && "Environment variable name missing");
209
210 // Get the environment variable they want us to parse options out of.
211 const char *envValue = getenv (envVar);
212 if (!envValue)
213 return;
214
202215 // Get program's "name", which we wouldn't know without the caller
203216 // telling us.
204 assert (progName && "Program name not specified");
205 static std::vector newargv; // Maybe making it "static" is a hack.
206 int newargc;
207 newargv.push_back (progName);
208
209 // Get the environment variable they want us to parse options out of.
210 assert (envvar && "Environment variable name missing");
211 char *envvalue = getenv (envvar);
212 if (envvalue == NULL) {
213 // Env var not set --> act like there are no more command line
214 // arguments.
215 newargc = newargv.size ();
216 ParseCommandLineOptions (newargc, &newargv[0], Overview);
217 return;
218 }
219 std::string envvaluestr (envvalue);
217 std::vector newArgv;
218 newArgv.push_back (strdup (progName));
220219
221220 // Parse the value of the environment variable into a "command line"
222221 // and hand it off to ParseCommandLineOptions().
223 ParseCStringVector (newargv, envvaluestr, " \v\f\t\r\n");
224 newargc = newargv.size ();
225 ParseCommandLineOptions (newargc, &newargv[0], Overview);
222 ParseCStringVector (newArgv, envValue);
223 int newArgc = newArgv.size ();
224 ParseCommandLineOptions (newArgc, &newArgv[0], Overview);
225
226 // Free all the strdup()ed strings.
227 for (std::vector::iterator i = newArgv.begin (), e = newArgv.end ();
228 i != e; ++i) {
229 free (*i);
230 }
226231 }
227232
228233 void cl::ParseCommandLineOptions(int &argc, char **argv,