mirror of the now-defunct rocklinux.org
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

308 lines
7.3 KiB

  1. /*
  2. * Copyright (C) 1991, 92, 94, 97, 98, 99 Free Software Foundation, Inc.
  3. * This file is part of the GNU C Library.
  4. *
  5. * --- NO-ROCK-COPYRIGHT-NOTE ---
  6. *
  7. * glibc-2.2.5/posix/execl.c
  8. */
  9. /* Execute PATH with all arguments after PATH until
  10. a NULL pointer and environment from `environ'. */
  11. int
  12. execl (const char *path, const char *arg, ...)
  13. {
  14. size_t argv_max = 1024;
  15. const char **argv = alloca (argv_max * sizeof (const char *));
  16. unsigned int i;
  17. va_list args;
  18. argv[0] = arg;
  19. va_start (args, arg);
  20. i = 0;
  21. while (argv[i++] != NULL)
  22. {
  23. if (i == argv_max)
  24. {
  25. const char **nptr = alloca ((argv_max *= 2) * sizeof (const char *));
  26. #ifndef _STACK_GROWS_UP
  27. if ((char *) nptr + argv_max == (char *) argv)
  28. {
  29. /* Stack grows down. */
  30. argv = (const char **) memcpy (nptr, argv,
  31. i * sizeof (const char *));
  32. argv_max += i;
  33. }
  34. else
  35. #endif
  36. #ifndef _STACK_GROWS_DOWN
  37. if ((char *) argv + i == (char *) nptr)
  38. /* Stack grows up. */
  39. argv_max += i;
  40. else
  41. #endif
  42. /* We have a hole in the stack. */
  43. argv = (const char **) memcpy (nptr, argv,
  44. i * sizeof (const char *));
  45. }
  46. argv[i] = va_arg (args, const char *);
  47. }
  48. va_end (args);
  49. return execve (path, (char *const *) argv, __environ);
  50. }
  51. /*
  52. * Copyright (C) 1991, 92, 94, 97, 98, 99 Free Software Foundation, Inc.
  53. * This file is part of the GNU C Library.
  54. *
  55. * glibc-2.2.5/posix/execle.c
  56. */
  57. /* Execute PATH with all arguments after PATH until a NULL pointer,
  58. and the argument after that for environment. */
  59. int
  60. execle (const char *path, const char *arg, ...)
  61. {
  62. size_t argv_max = 1024;
  63. const char **argv = alloca (argv_max * sizeof (const char *));
  64. const char *const *envp;
  65. unsigned int i;
  66. va_list args;
  67. argv[0] = arg;
  68. va_start (args, arg);
  69. i = 0;
  70. while (argv[i++] != NULL)
  71. {
  72. if (i == argv_max)
  73. {
  74. const char **nptr = alloca ((argv_max *= 2) * sizeof (const char *));
  75. #ifndef _STACK_GROWS_UP
  76. if ((char *) nptr + argv_max == (char *) argv)
  77. {
  78. /* Stack grows down. */
  79. argv = (const char **) memcpy (nptr, argv,
  80. i * sizeof (const char *));
  81. argv_max += i;
  82. }
  83. else
  84. #endif
  85. #ifndef _STACK_GROWS_DOWN
  86. if ((char *) argv + i == (char *) nptr)
  87. /* Stack grows up. */
  88. argv_max += i;
  89. else
  90. #endif
  91. /* We have a hole in the stack. */
  92. argv = (const char **) memcpy (nptr, argv,
  93. i * sizeof (const char *));
  94. }
  95. argv[i] = va_arg (args, const char *);
  96. }
  97. envp = va_arg (args, const char *const *);
  98. va_end (args);
  99. return execve (path, (char *const *) argv, (char *const *) envp);
  100. }
  101. /*
  102. * Copyright (C) 1991, 92, 94, 97, 98, 99 Free Software Foundation, Inc.
  103. * This file is part of the GNU C Library.
  104. *
  105. * glibc-2.2.5/posix/execlp.c
  106. */
  107. /* Execute FILE, searching in the `PATH' environment variable if
  108. it contains no slashes, with all arguments after FILE until a
  109. NULL pointer and environment from `environ'. */
  110. int
  111. execlp (const char *file, const char *arg, ...)
  112. {
  113. size_t argv_max = 1024;
  114. const char **argv = alloca (argv_max * sizeof (const char *));
  115. unsigned int i;
  116. va_list args;
  117. argv[0] = arg;
  118. va_start (args, arg);
  119. i = 0;
  120. while (argv[i++] != NULL)
  121. {
  122. if (i == argv_max)
  123. {
  124. const char **nptr = alloca ((argv_max *= 2) * sizeof (const char *));
  125. #ifndef _STACK_GROWS_UP
  126. if ((char *) nptr + argv_max == (char *) argv)
  127. {
  128. /* Stack grows down. */
  129. argv = (const char **) memcpy (nptr, argv,
  130. i * sizeof (const char *));
  131. argv_max += i;
  132. }
  133. else
  134. #endif
  135. #ifndef _STACK_GROWS_DOWN
  136. if ((char *) argv + i == (char *) nptr)
  137. /* Stack grows up. */
  138. argv_max += i;
  139. else
  140. #endif
  141. /* We have a hole in the stack. */
  142. argv = (const char **) memcpy (nptr, argv,
  143. i * sizeof (const char *));
  144. }
  145. argv[i] = va_arg (args, const char *);
  146. }
  147. va_end (args);
  148. return execvp (file, (char *const *) argv);
  149. }
  150. /*
  151. * Copyright (C) 1991, 92, 94, 97, 98, 99 Free Software Foundation, Inc.
  152. * This file is part of the GNU C Library.
  153. *
  154. * glibc-2.2.5/posix/execvp.c
  155. */
  156. /* The file is accessible but it is not an executable file. Invoke
  157. the shell to interpret it as a script. */
  158. static void
  159. script_execute (const char *file, char *const argv[])
  160. {
  161. /* Count the arguments. */
  162. int argc = 0;
  163. while (argv[argc++])
  164. ;
  165. /* Construct an argument list for the shell. */
  166. {
  167. char *new_argv[argc + 1];
  168. new_argv[0] = (char *) "/bin/sh";
  169. new_argv[1] = (char *) file;
  170. while (argc > 1)
  171. {
  172. new_argv[argc] = argv[argc - 1];
  173. --argc;
  174. }
  175. /* Execute the shell. */
  176. execve (new_argv[0], new_argv, __environ);
  177. }
  178. }
  179. /* Execute FILE, searching in the `PATH' environment variable if it contains
  180. no slashes, with arguments ARGV and environment from `environ'. */
  181. int
  182. execvp (file, argv)
  183. const char *file;
  184. char *const argv[];
  185. {
  186. if (*file == '\0')
  187. {
  188. /* We check the simple case first. */
  189. errno = ENOENT;
  190. return -1;
  191. }
  192. if (strchr (file, '/') != NULL)
  193. {
  194. /* Don't search when it contains a slash. */
  195. execve (file, argv, __environ);
  196. if (errno == ENOEXEC)
  197. script_execute (file, argv);
  198. }
  199. else
  200. {
  201. int got_eacces = 0;
  202. char *path, *p, *name;
  203. size_t len;
  204. size_t pathlen;
  205. path = getenv ("PATH");
  206. if (path == NULL)
  207. {
  208. /* There is no `PATH' in the environment.
  209. The default search path is the current directory
  210. followed by the path `confstr' returns for `_CS_PATH'. */
  211. len = confstr (_CS_PATH, (char *) NULL, 0);
  212. path = (char *) alloca (1 + len);
  213. path[0] = ':';
  214. (void) confstr (_CS_PATH, path + 1, len);
  215. }
  216. len = strlen (file) + 1;
  217. pathlen = strlen (path);
  218. name = alloca (pathlen + len + 1);
  219. /* Copy the file name at the top. */
  220. name = (char *) memcpy (name + pathlen + 1, file, len);
  221. /* And add the slash. */
  222. *--name = '/';
  223. p = path;
  224. do
  225. {
  226. char *startp;
  227. path = p;
  228. p = strchrnul (path, ':');
  229. if (p == path)
  230. /* Two adjacent colons, or a colon at the beginning or the end
  231. of `PATH' means to search the current directory. */
  232. startp = name + 1;
  233. else
  234. startp = (char *) memcpy (name - (p - path), path, p - path);
  235. /* Try to execute this name. If it works, execv will not return. */
  236. execve (startp, argv, __environ);
  237. if (errno == ENOEXEC)
  238. script_execute (startp, argv);
  239. switch (errno)
  240. {
  241. case EACCES:
  242. /* Record the we got a `Permission denied' error. If we end
  243. up finding no executable we can use, we want to diagnose
  244. that we did find one but were denied access. */
  245. got_eacces = 1;
  246. case ENOENT:
  247. case ESTALE:
  248. case ENOTDIR:
  249. /* Those errors indicate the file is missing or not executable
  250. by us, in which case we want to just try the next path
  251. directory. */
  252. break;
  253. default:
  254. /* Some other error means we found an executable file, but
  255. something went wrong executing it; return the error to our
  256. caller. */
  257. return -1;
  258. }
  259. }
  260. while (*p++ != '\0');
  261. /* We tried every element and none of them worked. */
  262. if (got_eacces)
  263. /* At least one failure was due to permissions, so report that
  264. error. */
  265. errno = EACCES;
  266. }
  267. /* Return the error from the last attempt (probably ENOENT). */
  268. return -1;
  269. }