Creating a child process WITHOUT fork()
Asked Answered
F

5

12

Is there a way to start a child process without fork(), using execvp() exclusively?

Ferreira answered 11/1, 2019 at 19:8 Comment(10)
Yes, if the process created by execvp is using fork or clone... This question makes no sense without rationale provided.Avertin
execvp replaces your process with another executable so hardly a child process. Why the resistance to fork?Minhminho
Unfortunately there is no rational behind the question because there is this specific restriction on my project.Ferreira
If you have a restriction on using fork then you are not supposed to create a child process, that's it. Or maybe they want you to use clone.Avertin
Creating a child process is a non negotiable demand according to the instructions given by the professor. execvp only!Ferreira
Could you please quote us the full statement of restrictions on your project? It's possible you are supposed to learn something subtle about Unix from discovering that you can't start a child process without fork, but it's also possible that you misunderstood the assignment.Genova
Then either you have misunderstood the assignment or the professor is asking for impossible.Avertin
execvp doesn't create a new process, it runs a new program in the context of your current process.Holliholliday
What is the operating system? There are plenty of operating systems that do not use fork() at all.Assert
man vfork(); or if you wanted to be even more disingenuous, system().Satsuma
G
10

The pedantic answer to your question is no. The only system call that creates a new process is fork. The system call underlying execvp (called execve) loads a new program into an existing process, which is a different thing.

Some species of Unix have additional system calls besides fork (e.g. vfork, rfork, clone) that create a new process, but they are only small variations on fork itself, and none of them are part of the POSIX standard that specifies the functionality you can count on on anything that calls itself a Unix.

The slightly more helpful answer is that you might be looking for posix_spawn, which is a library routine wrapping fork and exec into a single operation, but I find it more troublesome to use that correctly than to write my own fork+exec subroutine. YMMV.

Genova answered 11/1, 2019 at 19:16 Comment(5)
@DanO I don't think that makes enough of a difference to change my answer. Sure, posix_spawn might be using a newer fork-with-options primitive, whatever that's called, rather than the original fork(2), but it's still a library routine that wraps a fork operation and an exec operation. Its algorithm has not changed.Genova
@DanO please reread the second paragraph of the answer: clone has been mentioned since I originally wrote it. Since clone is just a small variation on fork, its existence doesn't invalidate my original point, no more than vfork does.Genova
Sorry, I just don't see it. As long as posix_spawn is implemented by doing a fork operation and an exec operation, I think what the answer currently says is accurate. The names of the system calls involved are not important.Genova
You're insisting on a distinction that, as far as I can tell, does not correspond to an actual difference. Clone performs a fork operation.Genova
I'll write my own answer.Gabionade
G
4

posix_spawn is the only posix compliant way to create a child process without calling fork directly. I say 'directly' because historically posix_spawn would itself just call fork, or vfork. However, that is no longer the case in GNU/linux. posix_spawn itself may be more efficient than fork, in addition to perhaps being a stronger fit conceptually when code is attempting to run a different executable.

If you aren't worried about portability, you can abandon posix and couple yourself directly to the kernel you are targeting. On linux the system call to create a child process is clone. At the time of this answer the manual page provides documentation for three variants, including the relatively new clone3.

I believe you can take the example from the manual page and add an execvp call to childFunc. I have not tried it yet, though!

Gabionade answered 9/7, 2020 at 23:21 Comment(1)
However, that is no longer the case in GNU/linux. posix_spawn itself may be more efficient than fork The reason is fork() is broken in glibc and glibc maintainers have been waging a decade-and-a-half effort to get fork() removed from the POSIX list of async-signal-safe functions.Intersidereal
C
3

Unlike Windows systems, where creating a new process and executing a new process image happen in a single step, Linux and other UNIX-like systems do them as two distinct steps.

The fork function makes an exact duplicate of the calling process and actually returns twice, once to the parent process and once to the child process. The execvp function (and other functions in the exec family) executes a new process image in the same process, overwriting the existing process image.

You can call execvp without calling fork first. If so, that just means the currently running program goes away and is replaced with the given program. However, fork is the way to create a new process.

Chap answered 11/1, 2019 at 19:14 Comment(1)
overwriting the existing process image going into implementation details I'd imagine it's done lazy and only the page tables are replaced at first with the registers.Holliholliday
L
1

As user zwol has already explained, execve() does not fork a new process. Rather, it replaces the address space and CPU state of current process, loads the new address space from the executable filename and starts it from main() with argument list argv and environment variable list envp. It keeps pid and open files.

int execve(const char *filename,char *const argv [],char *const envp[]);

filename: name of executable file to run
argv: Command line arguments
envp: environment variable settings (e.g., $PATH, $HOME, etc.)

Lazes answered 13/1, 2020 at 17:35 Comment(0)
W
0

posix_spawn. But it ignores failures of execvp() -- potentially because implementing this was regarded as too complicated.

Warrigal answered 8/8, 2022 at 16:58 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.