execl() no longer depends on CONFIG_MAX_TASK_ARGS

This commit is contained in:
Gregory Nutt 2014-11-12 18:44:11 -06:00
parent bb65701ccd
commit 597999400e

View File

@ -47,6 +47,11 @@
/****************************************************************************
* Pre-processor Definitions
****************************************************************************/
/* This is an artificial limit to detect error conditions where an argv[]
* list is not properly terminated.
*/
#define MAX_EXECL_ARGS 256
/****************************************************************************
* Global Variables
@ -119,28 +124,60 @@
int execl(FAR const char *path, ...)
{
FAR char *argv[CONFIG_MAX_TASK_ARGS+1];
FAR char **argv;
size_t nargs;
va_list ap;
int argc;
int ret;
/* Count the number of arguments */
va_start(ap, path);
for (nargs = 0, argc = 0; argv[argc]; argc++)
{
/* Increment the number of args. Here is a sanity check to prevent
* running away with an unterminated argv[] list. MAX_EXECL_ARGS
* should be sufficiently large that this never happens in normal
* usage.
*/
if (++nargs > MAX_EXECL_ARGS)
{
set_errno(E2BIG);
return ERROR;
}
}
va_end(ap);
/* Allocate a temporary argv[] array */
argv = (FAR char **)malloc((nargs + 1) * sizeof(FAR char *));
if (argv = (FAR char **)NULL)
{
set_errno(ENOMEM);
return ERROR;
}
/* Collect the arguments into the argv[] array */
va_start(ap, path);
for (argc = 0; argc < CONFIG_MAX_TASK_ARGS; argc++)
for (argc = 0; argc < nargs; argc++)
{
argv[argc] = va_arg(ap, FAR char *);
if (argv[argc] == NULL)
{
break;
}
}
argv[CONFIG_MAX_TASK_ARGS] = NULL;
argv[nargs] = NULL;
va_end(ap);
/* Then let execv() do the real work */
return execv(path, (char * const *)&argv);
ret = execv(path, (char * const *)&argv);
/* Free the allocated argv[] list */
free(argv);
return ret;
}
#endif /* CONFIG_LIBC_EXECFUNCS */