Struct points as parameter to function C - c

I have a few months that i started programming in C, but I now find myself with a doubt, for example, let see the next example code:
typedef struct
{
char *var1;
}myFooStruct;
myFooStruct struct1 [ 200 ];
my doubt is what would I get for **struct1, &struct1, *struct1, struct1,
as I passed the struct to a function that takes a two-dimenssion pointer ( **myFooStruct ), I have basic knowledge about pointers 1-but I find myself confused with pointers to structs and 2-how can I modify the struct if I passed it as at parameter to a function
If there is another similar question post it here please, I could not find anything alike, if you know some lecture I could read is welcome too, thank you very much!!

* is a dereference operator - think of it as meaning "the value contained at location xyz".
& is a reference operator - think of it as meaning "the location in memory of variable xyz".
Accordingly:
myFooStruct struct1 is a physical structure - this is the actual object.
&struct1 is equivalent to the location in memory of struct1 - this is usually an address (like 0xf0004782). You'll usually see this used when passing by reference (see Wikipedia for more info) or when assigning to a pointer (which literally points to a location in memory - get it?).
*struct1 dereferences struct1 - that is, it returns the value contained at location struct1. In the example you give, this is invalid, as struct1 is not a pointer to a location in memory.
**struct1 is tricky - it returns the value contained at the location that is contained within struct1. In other words: struct1 points to a certain location in memory. At that location is the address of another location in memory! Think of it as a scavenger hunt - you go to a location, find a clue, and follow that to another location.
As to how to access structs: think of a struct as a box. When you have the box in front of you, you simply need to open it up and look at what's inside. In C, we do this using the . operator:
char *my_var = struct1.var1
When you don't have the box in front of you - that is, you have a pointer to the struct - you need to access the location the box is at before you can look at what's inside. In C, we have a shortcut for this - the -> operator:
myFooStruct *pointer_to_struct1 = &struct1
char *my_var = pointer_to_struct1->var1
//NOTE: the previous line is equivalent to:
// char *my_var = (*pointer_to_struct1).var1

Way 1 Using dynamic memory allocation. Generally used in linked list and all..
If you want to modify the struct in another function. first declare a pointer to a struct.
myFooStruct* struct1;
Allot memory for the struct
struct1 = malloc(sizeof(myFooStruct));
Send the address to the function
func1(struct1);
Receive it and access it to modify in the function.
void func(myFooStruct* struct1)
{
(*struct1).member1 = ...; // whatever you wanna do
...
Way 2
Declare a struct.
myFooStruct struct1;
Send the address of the struct to the function
func1(&struct1);
Receive it and access it to modify in the function.
void func(myFooStruct* struct1)
{
(*struct1).member1 = ...; // whatever you wanna do
...

If you need to access myFooStruct from function, you can define single pointer: fn( myFooStruct * st ). The you call the function with fn( struct1 ) and change values st[N].var1 = .... Double pointer may be necessary if your object is pointer with allocated memory, not static array as yours.

struct1 is just a table and to be speciffic it's just pointer to a place in the memory.
*struct1 would be thing, that is pointed by struct1, so it's a first struct in a table of structs.
But **struct1 won't be any string. First of all you do not allocate memory for string and second string is member of this struct not struct itself. **struct is undefined behavior, nothing more.
&struct is a pointer to the table, so it's a pointer to the pointer, that points first struct in a table.
You have to decide on your own, what you want. If you want to pass table of your structs then the cleanest way would be:
void function(myFooStruct structTab[]);

1. You should pass a struct pointer to function to access struct inside it .
Declare a struct pointer -
myFooStruct *struct1;
Allocate memory for struct
And pass it to function which is declared as -
type fn(myFooStruct *struct1){
.....
}
Call this function like this -
fn(struct1);
Access struct member like this -struct->member1
2. You can also pass what you have declared right now.
myFooStruct struct1[ 200 ];
define function as -
type fn(myFooStruct struct1[]){
.....
}
Access struct members like this - struct[i].member1.

Related

Accessing a struct given an unknown pointer to a memory address - C

Suppose I am given a (void*) ptr (my basic understanding is, it represents a pointer to a region of unknown data type) passed through the parameter of a function. I am trying to figure out how to access and check if a struct exists a few addresses behind.
To clarify, I am working with a big char array (not malloced) and the ptr passed into the function should point to an address of an unspecified data type within the array. Located before this data is a struct for which I am trying to access.
void function(void *ptr)
{
void *structPtr = (void*)((void*)ptr - sizeof(struct block));
}
Would this work to get me a pointer to the address of the struct located behind the initial "ptr"? And if so, how could I check if it is the block struct?
Apologizes in advance, I know this code is not specific as I am fairly new to the concepts entirely but also, I am in the process of coming up with an algorithm and not yet implementing it. Any references to possibly useful information are much appreciated.
what you are trying to do is risky as you must be sure that you address a correct place in memory. Usually, we add some magic number in struct block so that we can test here that we are not going anywhere.
This pattern is generally used in memory allocators,
have a look to https://sourceware.org/glibc/wiki/MallocInternals for an example.
The usual way of writing this is something like:
...function(void *ptr) {
struct block *hdr = (struct block *)ptr - 1;
relying on pointer arithmetic automatically scaling by the size of the pointed at type. As long as all the pointers passed in here were originally created by taking a pointer to a valid struct block and adding 1 to it (to get the memory after it), you should be fine.

C - passing elements from within structures to functions

I have a structure comprised of an array of pointers to other structures of a different type.
typedef struct{
NodeT* nodes[2];
int size;
}stackT;
with:
typedef struct{
char info;
}NodeT;
And I have a pointer to the above (first) structure:
stackT* stackPtr;
Assuming the memory is allocated for the stackT structure as well as both NodeT structures with associated assignments for the members of both NodeT structures, how would I pass to a function one of the pointers in stackT?
For example:
void setChar(NodeT* nodePtr, char setTo){
nodePtr->info = setTo;
}
called with line:
setChar(stackPtr->nodes[0], 'A');
Does not work. I figured it had something to do with the -> syntax dereferencing the pointer whereby I am actually passing in a structure. I do not get any compilation errors, but when I check for the assignment by printing whatever is stored in char info I do not get anything.
Is the notation incorrect or do I have issues elsewhere in the program perhaps? I just wanted to rule this out first (proper passing syntax).
If someone is looking for a solution to this problem, the above code was actually correct.
Assuming you have an array of pointer in some structure and you wish to pass such a pointer, the correct syntax would be:
someFunc( structPtr->ptrArray[0] )
The line:
structPtr->ptrArray[0]
Actually returns a pointer, and not whatever the pointer is pointer to.
(*structPtr).ptrArray[0]
Is also equivalent.
That being said, I either mistakenly interpreted the information before me, or I had underlying errors elsewhere in the my code.

pointer to structure and self pointers

What is the difference between self referential pointer in structure and pointer to structure?
struct abc
{
int data;
struct abc *next;
}
struct abc *pt;
What are the differences between *next and *pt??
How they differ in their use??
I am really in doubt between these two
I am a beginner
First example is used mainly for linked list
Are pointer to structure node and self referential pointer the same thing?
please see
see-programming.blogspot.in/2013/05/chain-hashing-separate-chaining-with.html here we have used struct hash *hashTable as an array ..how?? and can we do same with *pt
They are of the same type. They behave in the exact same way.
Some example usage:
// declare 2 structs
struct abc s1;
struct abc s2;
// point pt to s1
pt = &s1;
// point s1.next to s2
s1.next = &s2;
// access pt->data
int a = pt->data;
// access s1.next->data
int a = s1.next->data;
Differences in usage:
There's only one pt variable.
For every struct abc variable, there is a next variable.
In the context of a linked-list, there is only one head pointer, thus pt would be it.
But each node points to the next node, thus next should be used for this.
Using pointers as arrays?
Yes, this can be done with either pt or next.
A pointer just points to an address in memory. There can be any number of structs following on each other at that location.
If you want to use it as an array (or just using pointers in general), you just have to make sure you don't try to access elements that you didn't allocate memory for (with malloc for example) and free the memory after usage (if you used malloc).
Some example usage with array:
// declare a struct
struct abc s1;
// make an array of size 10
struct abc *a1 = malloc(10*sizeof(struct abc));
// give the 4th element a new value
a1[4] = s1;
// free the memory
free(a1);
I hope that helps a bit.
Conceptually, very little difference at all.
next is a member of the same structure it is pointing to. pt is not a member of the structure it is pointing to.
They are used in a similar way, except that to use next you have a have an existing struct abc, and pt can be used directly. Please consider:
myABC.next= &myOtherABC ;
pt= &myOtherABC ;
are pointer to structure node and self referential pointer same thing
They are and they are not. Depends on point of view. They are because they both point to a structure. They are not because a pointer to structure can point to any structure, and as a variable it can be a parameter, a local variable, a member of another struct, etc. But a self referential pointer is necessarily a member of a struct and points to the same struct it is a member of.
The only difference applies to people that write compilers. That is because a self-referential pointer refers to itself before itself is fully declared. So someone writing a compiler has to deal with this special case.
As a programmer (that means you), there is no difference, and the terms do not offer any additional meaning.
they are the same type but they do not contain the same value
from pt you can access next because pt point to a structure that contain next. but from next you can't access pt.
for linked list, you have to understand, that the list contain at the begining 1 element, and this element know how reach the next element of the list, it is the goal of the next pointer
There is no difference between those two pointers.
A possible difference in usage depends on the context but still does not apply to their nature of being both pointer to the same type of structure and therefore undergoing the same rules in terms of assignment, reading and arithmetics.

C - transferring information to a struct (specifically an array of strings)

This seems to be a very simple problem but I can't quite figure out which part is causing it. Basically, I have a struct that just contains an array of strings
struct command_stream{
char **tokens;
};
typedef struct command_stream *command_stream_t;
command_stream_t test;
Then later on, I parse some strings into shorter ones and end up with another array of strings
char **words = *array of strings*
words contains the correct information I want, I looped through and printed out each element to make sure I wasn't getting a faulty string. So now I just point tokens to words
test->tokens = words;
But it gives me a segmentation fault. I'm not sure why though. They're both pointers, so unless I'm missing something obvious...
EDIT: The function as a whole has to return a pointer, which is why it was set up like this, which I keep forgetting. But I think I've got it, if I just create a new typedef
typedef struct command_stream command_stream_s;
command_stream_s new_command_stream;
and just return
&new_command_stream;
That should work right? Even though new_command_stream itself isn't a pointer.
From your code excerpt, it seems that you have not declared the struct. You have successfully declared a pointer to the struct command_stream_t test; but this pointer does not point to anywhere yet.
You need to allocate memory for your struct in some way and make test reference it. For instance:
command_stream_t test =
(command_stream_t) malloc(sizeof(struct command_stream));
This way you can successfully use:
test->tokens = words;
as you intended.
Note that you don't need to use malloc to allocate the memory. The pointer can reference a local/global variable as long as it has memory associated to it (N.B. if you use a local var don't use the pointer outside the declaration scope of that var).
typedef struct command_stream *command_stream_t;
command_stream_t test;
This makes "test" a pointer. There is no memory allocated for the structure.
You need to allocate memory for the structure and make the test pointer point to the block of memory before you can dereference by saying -
test->tokens = words;
Do this:
typedef struct command_stream command_stream_t;
command_stream_t test;
test.tokens = words;
The difference is that, command_stream_t is no more a pointer type, it is the actual structure.

How to copy typedef struct into another one?

How to copy typedef struct into another one?
If I have a typedef struct called books and I have a struct variable called books first. Now I declare books second How can I pass the content of first to second? Is there a function to do that or I can do that just with second = first ?
If your structure does not contain any members that are pointers (or containing structs that do), then you can simply assign one to the other.
second = first;
If however your structs do contain pointers, then with a simple assignment you end up with two struct that contain pointers to the same memory, and changing one will affect the other. If that's not what you want then you need to do a deep copy.
For example:
struct book {
char *name;
int cost; // in cents, so you don't have to deal with floating point issues
};
struct book first;
first.name = strdup("title1");
first.cost = 500;
struct book second;
second.name = strdup(first.name);
second.cost = first.cost;
If both first and second have the same type, then you can just do second = first; . It does not matter whether the type is an built-in or user-defined. C will copy the contents of first over to second. Just try it.
In general, variables in C are just data with a name and a type.
If the types of 2 variables a and b match, you can assign one to the other: a = b;.
What happens is that the value of variable b is copied into variable a.
But beware of pointers: For C, pointers are just variables with a value (the fact that the value represents a memory address does not matter, C treats all data equal).
If the 2 variables happen to be pointers, like char *a; char *b; then you can assign a = b; just with any variable.
But since the value of the variable b is the memory address, the memory address is copied from b to a, not the content of the memory at the memory address.
If you want to have the memory copied over, you will have to do it on your own, e.g. via the help of memcpy() (see its man page for information).
That said, if your structs contain pointers, the pointers are the content, not the stuff the pointers point to. C would copy the pointer values, not the pointer targets.
If you got pointers in your structs and want some sort of deep-copy, you would have to implement the traversal of your structs on your own. See What is the difference between a deep copy and a shallow copy?

Resources