Reputation: 14103
I've done alot of looking around, but still can't get my head around it, lets say I have struct:
struct some_struct {
int x;
int y;
char *some_string;
};
Lets say we have the above struct, how would you allocate some memory for the above struct? One can simply do:
struct some_struct *test_struct;
test_struct = malloc(sizeof(struct some_struct));
But is this enough? Don't you need to allocate some memory for some_string
? Or if the struct contains more pointers, do you not need to allocate memory for them as well?
Edit: One more thing... assuming my struct some_struct
already has data in it e.g.
struct some_struct *test_struct = malloc(sizeof(some_string);
test_struct->x = 2;
test_struct->y = 3;
test_struct->some_string = "sadlfkajsdflk";
Will the following code suffice in freeing allocated memory?
free(test_struct);
or do I have to go in and free the char* some_string as well?
Thanks
Upvotes: 3
Views: 288
Reputation: 1214
Ok, this bit of code is not doing what you want:
struct some_struct *test_struct = malloc(sizeof(some_string);
test_struct->x = 2;
test_struct->y = 3;
test_struct->some_string = "sadlfkajsdflk";
in this case, your *test_struct
is now pointing to a 'memory zone' with the typeof some_sring
size(I think your some_string is char*
).
Malloc(X)
gives you X
space from your program (or process) virtual memory.
When you do:
struct some_struct *test_struct;
You get enough space to store a pointer to some_struct
.
If you do:
malloc(sizeof(struct some_struct));
You have now reserved struct some_struct
space from the virtual memory. But you want to know 'where' that memory is. Thats why you assign it to the pointer:
test_struct = malloc (sizeof(struct some_struct));
[EDIT]I'd write this:" To make your compiler happier you should also include a cast in there to tell the compiler that that space allocated by malloc is gonna be used to store a struct some_struct
:", giving an example right after. But, in fact, that's not true. As you can see in the comments below, @chutsu corrected this, and to convince yourself, check this question.
The 'main' reason is that you're taking a lot of risks in doing it for no advantages at all.
The rest of the code is now corrected: No cast.
A cleaner way to do this would've been typedefing the struct. Then, your code would look like this:
typedef struct some_struct {
int x;
int y;
char *some_string;
}SomeStruct;
SomeStruct *test_struct;
test_struct = malloc(sizeof(SomeStruct));
About the string allocation. You can think like this: Everything created with malloc(and its brothers calloc, realloc...) needs to be free'd! This happens because all the other variables are local to functions, even the main is a function, and this ones are cleaned when the function terminates.
So, after allocating your struct, if you want space for your string, you'll have to allocate space for it.
test_struct->some_string = malloc((YOUR_STRING_SIZE+SPACE_FOR_THE_STRING_TERMINATOR)*sizeof(char));
with - SPACE_FOR_THE_STRING_TERMINATOR=1
, the \0
character.
Then, if you want to free test_struct
you'll have to free the string first and the struct later, in the reverse order you would lost the pointer to the string and that would leak.
It looks like this:
free(test_struct->some_string);
free(test_struct);
And that's it, you're done.
Hope this helps.
Upvotes: 1
Reputation: 53289
Calling malloc(sizeof(struct some_struct));
gives you memory for your struct, which includes space for two integer fields and a pointer field.
The pointer field however cannot be used until it points to a valid location in memory. To do this, you need to point it to a valid memory location, by e.g. allocating memory for it with malloc
or pointing it to a pre-existing valid memory location:
e.g.:
test_struct->some_string = malloc(100); // Allocate 100 bytes for the string
Upvotes: 6
Reputation: 9821
After running these two lines of code:
struct some_struct *test_struct;
test_struct = malloc(sizeof(struct some_struct));
You've done enough to start working with test_struct
. A pointer's value is just a memory address so the malloc
allocates enough for two int
s and one char*
. If you'd like to point test_struct->some_string
at an already existing char*
you may do so:
test_struct->some_string = some_other_char_pointer;
Otherwise, you'll need to allocate memory for it as well:
test_struct->some_string = malloc(...);
Upvotes: 2
Reputation: 182763
You may or may not need to allocate some memory for the string, depending on context. But the code you present allocate all the memory needed to hold that structure.
Basically, write code that does whatever it is you need to do. Whether you need memory for the string depends on what you're going to do.
With just the code you've shown, the pointer you allocated doesn't point to anything specific, just like the integers you allocated don't hold any specific values. Address allocation for the string, if needed, when you set the value of some_string
to something useful, probably at the same time you set x
and y
to something useful.
Upvotes: 1