sbsv2/raptor/util/talon/talon.c
branchfix
changeset 251 64208ed747d4
parent 237 dd11681bd6f3
child 252 6846d05399b6
equal deleted inserted replaced
238:bd7f12067a47 251:64208ed747d4
   220 		return NULL;
   220 		return NULL;
   221 	}
   221 	}
   222 	return recipe;
   222 	return recipe;
   223 }
   223 }
   224 
   224 
       
   225 #ifdef HAS_GETCOMMANDLINE
       
   226 /*
       
   227    Get rid of the path to talon from a commandline string on windows find the 
       
   228    -c (if it's there) and step past it to after the quote on the first command:
       
   229 
       
   230    "g:\program files\talon\talon.exe" -c "gcc -c . . ."
       
   231                                           ^------ Returns a pointer to here
       
   232 
       
   233    Take care of the possibilty that there might be spaces in the command
       
   234    if it is quoted.
       
   235 
       
   236    A state-machine is flexible but not all that easy to write.  Should investigate
       
   237    the possiblity of using the Ragel state machine generator perhaps.
       
   238 
       
   239 */
       
   240 #define CH_START 0
       
   241 #define CH_PRE 1
       
   242 #define CH_EXQUOTE 2
       
   243 #define CH_INQUOTE 3
       
   244 #define CH_POST 4
       
   245 #define CH_MINUS 5
       
   246 #define CH_C 6
       
   247 #define CH_PRECOMMAND 7
       
   248 #define CH_COMMAND 8
       
   249 #define CH_ERR 9
       
   250 
       
   251 char * chompCommand(char command[])
       
   252 {
       
   253 	char *result = command;
       
   254 	int state = CH_START;
       
   255 
       
   256 	while (state != CH_COMMAND && state != CH_ERR)
       
   257 	{
       
   258 		DEBUG(("startstate: %d, char %c ",state, *result));
       
   259 		switch (*result)
       
   260 		{
       
   261 			case ' ':
       
   262 				switch (state)
       
   263 				{
       
   264 					case CH_START:
       
   265 					case CH_PRE:
       
   266 						state = CH_PRE;
       
   267 						break;
       
   268 					case CH_EXQUOTE:
       
   269 						state = CH_POST;
       
   270 						break;
       
   271 					case CH_INQUOTE:
       
   272 						break;
       
   273 					case CH_POST:
       
   274 						break;
       
   275 					case CH_MINUS:
       
   276 						state = CH_C;
       
   277 						break;
       
   278 					case CH_C:
       
   279 						state = CH_PRECOMMAND;
       
   280 						break;
       
   281 					case CH_PRECOMMAND:
       
   282 						break;
       
   283 					default:
       
   284 						state = CH_ERR;
       
   285 						break;
       
   286 				}
       
   287 			break;
       
   288 			case 'c':
       
   289 				switch (state)
       
   290 				{
       
   291 					case CH_START:
       
   292 					case CH_PRE:
       
   293 						state = CH_EXQUOTE;
       
   294 						break;
       
   295 					case CH_EXQUOTE:
       
   296 					case CH_INQUOTE:
       
   297 						break;
       
   298 					case CH_POST:
       
   299 						state = CH_ERR;
       
   300 						break;
       
   301 					case CH_MINUS:
       
   302 						state = CH_C;
       
   303 						break;
       
   304 					case CH_C:
       
   305 					case CH_PRECOMMAND:
       
   306 					default:
       
   307 						state = CH_ERR;
       
   308 						break;
       
   309 				}
       
   310 			break;
       
   311 			case '-':
       
   312 				switch (state)
       
   313 				{
       
   314 					case CH_START:
       
   315 					case CH_PRE:
       
   316 						state = CH_EXQUOTE;
       
   317 						break;
       
   318 					case CH_EXQUOTE:
       
   319 					case CH_INQUOTE:
       
   320 						break;
       
   321 					case CH_POST:
       
   322 						state = CH_MINUS;
       
   323 						break;
       
   324 					case CH_MINUS:
       
   325 					case CH_C:
       
   326 					case CH_PRECOMMAND:
       
   327 					default:
       
   328 						state = CH_ERR;
       
   329 						break;
       
   330 				}
       
   331 			break;
       
   332 			case '"':
       
   333 				switch (state)
       
   334 				{
       
   335 					case CH_START:
       
   336 					case CH_PRE:
       
   337 					case CH_EXQUOTE:
       
   338 						state = CH_INQUOTE;
       
   339 						break;
       
   340 					case CH_INQUOTE:
       
   341 						state = CH_EXQUOTE;
       
   342 						break;
       
   343 					case CH_POST:
       
   344 					case CH_MINUS:
       
   345 					case CH_C:
       
   346 						state = CH_ERR;
       
   347 						break;
       
   348 					case CH_PRECOMMAND:
       
   349 						state = CH_COMMAND;
       
   350 						break;
       
   351 					default:
       
   352 						state = CH_ERR;
       
   353 						break;
       
   354 				}
       
   355 
       
   356 			break;
       
   357 			default:
       
   358 				switch (state)
       
   359 				{
       
   360 					case CH_START:
       
   361 					case CH_PRE:
       
   362 						state = CH_EXQUOTE;
       
   363 						break;
       
   364 					case CH_INQUOTE:
       
   365 					case CH_EXQUOTE:
       
   366 						break;
       
   367 					default:
       
   368 						state = CH_ERR;
       
   369 						break;
       
   370 				}
       
   371 			break;
       
   372 		}
       
   373 		DEBUG((stderr,"endstate: %d\n",state));
       
   374 		result ++;
       
   375 		
       
   376 	}
       
   377 
       
   378 	if (state == CH_ERR)
       
   379 		return NULL;
       
   380 
       
   381 	return result;
       
   382 }
       
   383 #endif
       
   384 
   225 int main(int argc, char *argv[])
   385 int main(int argc, char *argv[])
   226 {
   386 {
   227 	/* find the argument to -c then strip the talon related front section */
   387 	/* find the argument to -c then strip the talon related front section */
   228 
   388 
   229 	char *recipe = NULL;
   389 	char *recipe = NULL;
   230 	int talon_returncode = 0;
   390 	int talon_returncode = 0;
   231 
   391 
   232 #ifdef HAS_GETCOMMANDLINE
   392 #ifdef HAS_GETCOMMANDLINE
   233 	char *commandline= GetCommandLine();
   393 	char *commandline= GetCommandLine();
   234 	DEBUG(("talon: commandline: %s\n", commandline));
       
   235 	/*
   394 	/*
   236 	 * The command line should be either,
   395 	 * The command line should be either,
   237 	 * talon -c "some shell commands"
   396 	 * talon -c "some shell commands"
   238 	 * or
   397 	 * or
   239 	 * talon shell_script_file
   398 	 * talon shell_script_file
   240 	 *
   399 	 *
   241 	 * talon could be an absolute path and may have a .exe extension.
   400 	 * talon could be an absolute path and may have a .exe extension.
   242 	 */
   401 	 */
   243 	recipe = strstr(commandline, "-c");
   402 
       
   403 	
       
   404 	recipe = chompCommand(commandline);
       
   405 	if (recipe == NULL)
       
   406 	{
       
   407 		error("talon: error: unable to locate argument start in '%s'\n", commandline);
       
   408 		return 1;
       
   409 	}
   244 	if (recipe)
   410 	if (recipe)
   245 	{
   411 	{
   246 		/* there was a -c so extract the quoted commands */
   412 		/* there was a -c so extract the quoted commands */
   247 
   413 
   248 		while (*recipe != '"' && *recipe != '\0')
       
   249 			recipe++;
       
   250 
       
   251 		if (*recipe != '"')    /* we found -c but no following quote */
       
   252 		{
       
   253 			error("talon: error: unquoted recipe in shell call '%s'\n", commandline);
       
   254 			return 1;
       
   255 		}
       
   256 		recipe++;
       
   257 		
       
   258 		int recipelen = strlen(recipe);
   414 		int recipelen = strlen(recipe);
   259 		if (recipelen > 0 && recipe[recipelen - 1] == '"')
   415 		if (recipelen > 0 && recipe[recipelen - 1] == '"')
   260 			recipe[recipelen - 1] = '\0'; /* remove trailing quote */
   416 			recipe[recipelen - 1] = '\0'; /* remove trailing quote */
   261 	}
   417 	}
   262 	else
   418 	else