Путеводитель по Руководству Linux

  User  |  Syst  |  Libr  |  Device  |  Files  |  Other  |  Admin  |  Head  |



   execve    ( 2 )

выполнить программу (execute program)

  Name  |  Synopsis  |  Description  |  Return value  |  Error  |  Conforming to  |    Note    |  Examples  |  See also  |

Примечание (Note)

One sometimes sees execve() (and the related functions described in exec(3)) described as "executing a new process" (or similar). This is a highly misleading description: there is no new process; many attributes of the calling process remain unchanged (in particular, its PID). All that execve() does is arrange for an existing process (the calling process) to execute a new program.

Set-user-ID and set-group-ID processes can not be ptrace(2)d.

The result of mounting a filesystem nosuid varies across Linux kernel versions: some will refuse execution of set-user-ID and set-group-ID executables when this would give the user powers they did not have already (and return EPERM), some will just ignore the set-user-ID and set-group-ID bits and exec() successfully.

On Linux, argv and envp can be specified as NULL. In both cases, this has the same effect as specifying the argument as a pointer to a list containing a single null pointer. Do not take advantage of this nonstandard and nonportable misfeature! On many other UNIX systems, specifying argv as NULL will result in an error (EFAULT). Some other UNIX systems treat the envp==NULL case the same as Linux.

POSIX.1 says that values returned by sysconf(3) should be invariant over the lifetime of a process. However, since Linux 2.6.23, if the RLIMIT_STACK resource limit changes, then the value reported by _SC_ARG_MAX will also change, to reflect the fact that the limit on space for holding command-line arguments and environment variables has changed.

In most cases where execve() fails, control returns to the original executable image, and the caller of execve() can then handle the error. However, in (rare) cases (typically caused by resource exhaustion), failure may occur past the point of no return: the original executable image has been torn down, but the new image could not be completely built. In such cases, the kernel kills the process with a SIGSEGV (SIGKILL until Linux 3.17) signal.

Interpreter scripts The kernel imposes a maximum length on the text that follows the "#!" characters at the start of a script; characters beyond the limit are ignored. Before Linux 5.1, the limit is 127 characters. Since Linux 5.1, the limit is 255 characters.

The semantics of the optional-arg argument of an interpreter script vary across implementations. On Linux, the entire string following the interpreter name is passed as a single argument to the interpreter, and this string can include white space. However, behavior differs on some other systems. Some systems use the first white space to terminate optional-arg. On some systems, an interpreter script can have multiple arguments, and white spaces in optional-arg are used to delimit the arguments.

Linux (like most other modern UNIX systems) ignores the set-user- ID and set-group-ID bits on scripts.

execve() and EAGAIN A more detailed explanation of the EAGAIN error that can occur (since Linux 3.1) when calling execve() is as follows.

The EAGAIN error can occur when a preceding call to setuid(2), setreuid(2), or setresuid(2) caused the real user ID of the process to change, and that change caused the process to exceed its RLIMIT_NPROC resource limit (i.e., the number of processes belonging to the new real UID exceeds the resource limit). From Linux 2.6.0 to 3.0, this caused the set*uid() call to fail. (Prior to 2.6, the resource limit was not imposed on processes that changed their user IDs.)

Since Linux 3.1, the scenario just described no longer causes the set*uid() call to fail, because it too often led to security holes where buggy applications didn't check the return status and assumed that—if the caller had root privileges—the call would always succeed. Instead, the set*uid() calls now successfully change the real UID, but the kernel sets an internal flag, named PF_NPROC_EXCEEDED, to note that the RLIMIT_NPROC resource limit has been exceeded. If the PF_NPROC_EXCEEDED flag is set and the resource limit is still exceeded at the time of a subsequent execve() call, that call fails with the error EAGAIN. This kernel logic ensures that the RLIMIT_NPROC resource limit is still enforced for the common privileged daemon workflow—namely, fork(2) + set*uid() + execve().

If the resource limit was not still exceeded at the time of the execve() call (because other processes belonging to this real UID terminated between the set*uid() call and the execve() call), then the execve() call succeeds and the kernel clears the PF_NPROC_EXCEEDED process flag. The flag is also cleared if a subsequent call to fork(2) by this process succeeds.

Historical With UNIX V6, the argument list of an exec() call was ended by 0, while the argument list of main was ended by -1. Thus, this argument list was not directly usable in a further exec() call. Since UNIX V7, both are NULL.