Reputation: 8152
void print_hello_world() {
pid_t pid = getpid();
printf("Hello world %d\n", pid);
pthread_exit(0);
}
void main() {
pthread_t thread;
pthread_create(&thread, NULL, (void *) &print_hello_world, NULL);
print_hello_world();
}
I really couldn't understand what is the need of (void *) in pthread_create. And do we need "&print_hello_world" in the same or could drop "&" as I have read somewhere that while passing function pointers we don't need to place "&" before the function name.
Upvotes: 1
Views: 597
Reputation: 12263
Casting a function pointer to/from void *
is actually undefined behaviour. See 6.3.2.3, especially p1 and p8. Note that functions are no objects in C.
So the cast is wrong in fact and the addressof-operator &
is unnecessary. You can cast, however, one function pointer to another (see §8 of the reference). But here, you shoud definitively have a proper signature for your function, as there is a reason it takes a pointer and returns one, too. So: do not cast, but get the signature (and semantics) correct.
Note: An empty identifier-list in a function declaration which is part of the definition is an obsolescent feature. Using the prototype-style (void)
for an empty argument list is recommended. Also the minimal required signature for main
is int main(void)
(with respect to the above said).
Upvotes: 2
Reputation: 121387
Yes, there's no need for cast or &
operator there:
pthread_create(&thread, NULL, print_hello_world, NULL);
should suffice as a function name gets converted into a function pointer when passing as argument to function(s).
Note that the function pointer you pass to pthread_create()
takes a void*
as argument and returns a void *
. So your function should be:
void* print_hello_world(void *unused) {
...
}
It's the C way of implementing "generic" data type. For example, you can pass a int*
or struct args*
to the thread function and retrieve it back.
E.g.
int i=5;
pthread_create(&thread, NULL, print_hello_world, &i);
and in the function print_hello_world()
, you would do:
void *print_hello_world(void *value) {
int i = *(int*)value;
...
}
Basically void*
allows you to pass any data pointer to the thread function here. If pthread_create()
's thread function were to take int*
, you wouldn't be able to pass a struct args*
to it, for example.
I suggest you read the following posts for more information on void pointer and its usage in C:
Concept of void pointer in C programming and What does void* mean and how to use it?
Upvotes: 3