I've been confused with what I see on most C programs that has unfamiliar function declaration for me.
void *func_name(void *param){
...
}
What does * imply for the function? My understanding about (*) in a variable type is that it creates a pointer to another variable thus it can be able to track what address at which the latter variable is stored in the memory. But in this case of a function, I don't know what this * asterisk implies.
The asterisk belongs to the return type, and not to the function name, i.e.:
void* func_name(void *param) { . . . . . }
It means that the function returns a void pointer.
The * refers to the return type of the function, which is void *.
When you declare a pointer variable, it is the same thing to put the * close to the variable name or the variable type:
int *a;
int* a;
I personally consider the first choice more clear because if you want to define multiple pointers using the , separator, you will have to repeat the * each time:
int *a, *b;
Using the "close to type syntax" can be misleading in this case, because if you write:
int* a, b;
You are declaring a pointer to int (a) and an int (b).
So, you'll find that syntax in function return types too!
The * belongs to the return type. This function returns void *, a pointer to some memory location of unspecified type.
A pointer is a variable type by itself that has the address of some memory location as its value. The different pointer types in C represent the different types that you expect to reside at the memory location the pointer variable refers to. So a int * is expected to refer to a location that can be interpreted as a int. But a void * is a pointer type that refers to a memory location of unspecified type. You will have to cast such a void pointer to be able to access the data at the memory location it refers to.
It means that the function returns a void*.
Related
I have 2 questions about pointers in c.
1) from my understanding the & returns the memory address of a variable. For example:
int x=10;
int *p=&x;
So I think that the & will return the memory address of x and that memory address is type int* because the variable type of x is int.
Also because the type of the address is int* I believe that is the reason that only an int* (and void *) pointer can point in the address (they are the same type).
Any thoughts about that? comments? I don't know if I am correct.
2) It's about the void pointer. I know that the void* pointer can point to any type of variable. For example
int x=10;
void *ptr=&x;
Now I have a function:
void * foo(some parameters)
{
// just for this example let's say that I return the address of a local variable
// I know that is wrong to do so because when the foo ends
// the local variables deallocate
int k=10;
void *ptr=&k;
return ptr;
}
So my pointer is type void but it points to int* memory address. So ptr will save the address of k and when I return ptr the address of k is returned which is type int* . But my function is type void*.
What is happening here?
According to the C Standard (6.3.2.3 Pointers)
1 A pointer to void may be converted to or from a pointer to any
object type. A pointer to any object type may be converted to a
pointer to void and back again; the result shall compare equal to the
original pointer.
So for example in this code snippet
int x = 10;
void *p = &x;
the expression &x in the right side of the assignment has the type int *. According to the quote it may be converted to pointer of the type void * in the left side of the assignment.
1) Yes all of that is correct.
2) The type of the pointed-at data remains int no matter what kind of pointer that points at it. (This is known as effective type in formal C.) In your example you return a void pointer so that's the type the caller gets. The information of what type it pointed at is lost, from the point you do void *ptr=&k; and onward. This is why void pointers are problematic to use.
1) You are correct
2) It is simply returning a void * that is pointing to k - a local variable. (Any pointers can be cast to void pointers).
You are correct in saying that you should not use the returned value as k no longer exists
I have seen void * explained as a pointer to an unused chunk of memory. I have also seen void * described as a pointer to any type, or a pointer to any type can be cast to void *.
From what I know, int * means a pointer to type int. So keeping this in mind, what does void * mean literally? Is it a pointer to type void? This doesn't seem right because I did not know that void could be a type.
void * is a pointer to void.
C11: 6.3.2.3 Pointers:
A pointer to void may be converted to or from a pointer to any object type. A pointer to
any object type may be converted to a pointer to void and back again; the result shall
compare equal to the original pointer.
The compiler will not let you dereference a void* pointer because it does not know the size of the object pointed to but you need to cast void * type pointer to the right type before you dereference it.
Let's begin with this example:
int a = 65;
int *q = &a;
void *p = q;
char *c = p;
(source: qiniudn.com)
we define an int variable a, and an int pointer q pointing to it. p in the void * pointer.
The beginning address of a is 0x8400(just for simplicity).
A pointer is an address, no more.
No matter what type of pointer, they have the same memory size, and their value is an address.
So,
printf("%p, %p", *p, *q);
will display:
0x8400, 0x8400
Type: how you interpret the date
As you see in the graph, the data in memory is 65000000(this is little endian). If we want to use it, we have to specify what it is! And type does that.
printf("%d %c", *p, *q);
If we print it as integer, we get 65. If we print them as char, we get A(asciicode).
And p + 1 pointer to 0x8401, q + 1 points to 0x8404.
void *: a universal type
According to wikipedia:
A program can probably convert a pointer to any type of data (except a function pointer) to a pointer to void and back to the original type without losing information, which makes these pointers useful for polymorphic functions.
Yes, void * define a trivial unit of pointer, it can be converted to any pointer and vise versa. But you can't dereference it, because it doesn't specify a type.
If you want to manipulator on bytes, you should always use void *.
Isn't char * the same as void *
Not exactly.
The C language standard does not explicitly guarantee that the different pointer types have the same size.
You can't always hope char * have the same size on different platforms.
And converting char * to int * can be confusing, and mistakes can be made.
It means: a pointer to some memory, but this pointer does not contain any information about the type of data that may be stored in that memory.
This is why it's not possible to dereference a void *: the operation of dereferencing (and obtaining an rvalue, or writing through an lvalue) requires that the bits in the memory location be interpreted as a particular type, but we don't know which type to interpret the memory as.
The onus is on the programmer to make sure that data read in matches the type of data read out. The programmer might help himself in this by converting the void * to a pointer to an object type.
It's useful if you want to have a common interface for dealing with memory of multiple possible types, without requiring the user to do a lot of casting. for example free() takes a void * because the type information isn't necessary when doing the free operation.
void * is a pointer to data of unspecified type. As such, it can't be used directly; it must be cast to a usable datatype before it can be dereferenced.
I have a situation where in the address inside the void pointer to be copied to a another pointer. Doing this without a type cast gives no warnings or errors. The pseudo code looks like
structA A;
void * p = &A;
structA * B = p;// Would like to conform this step
I don't foresee any problems with this.
But since this operation is used over a lot of places, I would like to conform whether it can have any replications. Also is there any compiler dependency?
No, this is fine and 100% standard.
A void * can be converted to and from any other data/object pointer without problems.
Note that data/object restriction: function pointers do not convert to/from void *.
This is the reason why you shouldn't cast the return value of malloc(), which returns a void *.
In C a void * is implicitly compatible with any pointer. That why you don't need to cast when e.g. passing pointers of any type to functions taking void * arguments, or when assigning to pointer (still of any type) from function returning void * (here malloc is a good example).
I need to know what it means when a function has a void * parameter. For example:
function(void * param){}
It is a function that receives a void*. This may be used to pass any kind of pointer in C.
A good example is the pthread_create function, and the pthread start routine.
Note, however, that if no return type is specified, it defaults to return an int, which it does not in your example.
param is a void pointer means pointer to any data type . You may call generic type pointer.
e.g.
func(void *param)
{
// body
}
call like this :
char* cptr;
int* iptr;
float* fptr;
func(cptr);
func(iptr);
func(fptr);
A void * is a pointer to any data, i.e. to data of an unknown or unspecified type.
param has type void *, which in C serves as a "generic" pointer type; any object pointer type can be converted to void * and vice versa without need for an explicit cast (some implementations allow function pointer types to be converted to void *, but that's not universal and not guaranteed by the language standard).
Note that a void pointer may not be dereferenced, so you can't do something like x = *param in the body of the function. You'd have to convert the pointer to a different type such as int * or double * or whatever to get what it points to. And that depends on what function is supposed to do with it.
It means the param of type void* (reference to a void), which is the size of a memory location . You can reference any memory location with this, which in practice anything.
I found this function definition
void *func(void *param) {
}
Actually, I have a certain confusion regarding this function definition. What does void * mean in the return type of the function as well as the argument. I am a beginner in C. So please don't mind. Thank you
void *func(void *param) {
int s = (int)param;
....
}
Well looking at the above program which I found. I think it should have been
int *s = (int *)param;
isn't it? I am confused
void * means it's a pointer of no specific type, think of it as a generic pointer, unlike say int * an int pointer.
You can cast it into a different type if need be (for instance if you are going to do pointer arithmetic with the pointer).
You might find this SO question of use: Concept of void pointer in C programming
It simply means that the function func takes one parameter which is a pointer (to anything) and returns a pointer (to anything). When you use a void *, you are telling the compiler "this is a pointer, but it doesn't matter at this point what it's a pointer to".
When you want to actually use the data it's pointing to, you need to cast it to a pointer to some other type. For example, if it points to an int, you can create an int * variable and dereference that:
int *int_ptr = (int *)param;
// now (*int_ptr) is the value param is pointing to
you can think of it as a raw pointer, nothing more than an address, think about it, pointers are nothing more than address right, so they should all be of equal size, either 32 or 64 bits in most modern systems but if thats the case why do we say int * or char * or so on if they are all the same size, well thats because we need of a way to interpret the type we are pointing to, int * means when we dereference go to that address and interpret the 4 bytes as an int or char * means when we dereference go to that address and get a byte, so what happens when you dereference a void * well you get warning: dereferencing ‘void *’ pointer basically we really can't and if you do its affects are compiler dependent, the same applies when we do arithmetics on it.
So why bother using them? well I personally don't and some groups dont particularly like them, fundamentally they allow you to create fairly generic subroutines, a good example would be memset which sets a block of memory to a certain byte value, its first argument is a void * so it won't complain whether giving a char * or int * due note that it works on a per byte basis, and you need to properly calculate the total size of the array.
void *func(void *param) {
}
param is a void pointer means it is a pointer of any reference type. since a void pointer has no object type,it cannot be dereferenced unless it is case.
so void *param;
int *s=(int*)param;
here since param is an pointer variable so you will have to cast it as a pointer variable.not to a int type as you did there.
e.g.
int x;
float r;
void *p=&x;
int main()
{
*(int *)p=2;
p=&r;
*(float*)p=1.1;
}
in this example p is a void pointer. now in main method I have cast the p as a int pointer and then as a float pointer so that it can reference to first a integer and then a float.
Returning a pointer of any type. It can be of any datatype.