Reputation: 19551
Are there any libraries/pthread wrappers/clone
arguments that would allow me to have a tfork
--something that, just like fork()
, allows you to continue code execution in context, as opposed to pointing to a new function to execute under a new thread.
If not, is there any simple way to write this myself?
Usage would be ideally just like fork but the meaning would be threadlike, so as a contrived example:
int main() {
int ival = 0;
if(tfork() == 0) {
sleep(10);
ival = 5;
_exit(); // or exit or return or whatever
} else {
while(1) {
printf("ival=%d\n", ival);
if(ival != 0) {
printf("ival changed. done.\n");
return 0;
}
sleep(1);
}
}
}
Should output:
ival=0
ival=0
ival=0
ival=0
ival=0
ival=0
ival=0
ival=0
ival=0
ival=0
ival=5
ival changed. done.
Upvotes: 3
Views: 1433
Reputation: 15218
In Linux, fork() and pthread_create() are just a wrapper over clone(). You call call clone() directly yourself to get the desired effect. For example (not actual code but very close):
pid = syscall(SYS_clone, (CLONE_VM | CLONE_FS | CLONE_FILES | CLONE_SYSVSEM | CLONE_PARENT), NULL, NULL, NULL );
if(-1 == pid) {
return -1;
}
if(pid) {
return pid;
} else {
// Your new thread code goes here
}
More details here: http://linux.die.net/man/2/clone
Upvotes: 1
Reputation: 63538
You can't do that, because threads share the same address-space. Continuing from the same execution context (like fork() does) would mean that their stacks were in the same memory.
Of course two threads needs to have their own stacks otherwise trouble would happen.
This is why you need to specify a function to start a new thread - because the new thread has a new stack.
Upvotes: 5
Reputation: 43688
Uh, this is almost what vfork()
does on Linux, it shares the memory of the parent (but doesn't share the rest of the things that threads are supposed to share).
Since sharing the memory of the parent leads to the problems that have been talked about in the comments to your question (snd some other problems), a vfork()
parent is actually suspended until the child drops all references to that memory, usually via execve()
or _exit()
(Note the underscore, exit()
is not safe on a vfork()
child).
The only things a vfork()
child is guaranteed to be able to do safely are calling exec*()
or _exit()
. With a lot of knowledge and black voodoo magic, some people can do more things on a vfork()
child on Linux, but this involves a lot of attention to detail.
So, as you can see, there are a lot of limitations to the things you can do when sharing memory and returning a la fork()
: there is a very good reason why thread creation usually is done by calling a function.
Upvotes: 1