fundamentals of C programming

Thread Starter

Ryan$

Joined Dec 14, 2018
178
Hi guys, I've read over the internet about structs in C and what's confusing me is:
lets assume I have a struct like this:
Code:
struct Book
{
int size;
char name[20];
}
Book b1;
what's actually the address of b1 look/visualize in the memory? b1 is a struct with properties of name and size ..
is it like this:(assuming the address of b1 is 1234)
Code:
1234: b1
   5678: name
   5699: size
?
I'm asking like this question because for example in type of int once we write int x, the first byte's address of 4 bytes(because it's int) is assigned to x, meaning lets assume the addresses of 4 bytes of int like this: 1 2 3 4 which all storing the data of x, so the address of x is 1 because it's by default the pc assigning the first address of the first block of 4 bytes to x.

what about the address of b1? is the pc assigning it to the address of the first property that we build in the struct(in my case &b1 is the same address of size) ?




secondly, in programming we most using names(variables) for expressing about memory location, which means there might be for instance memory location of 6 bytes which referred to specific name, but how actually 6 bytes entering that specific name? means 6 bytes having alot of addresses on it so how actually that specific name(variable) storing them all in one hit? to clear more, specific name (variable) at the end will have one "address" that can be stored in it, but 6 bytes having multiple addresses, so how that specific name storing them all in one hit? in other words, I'm not understanding or succeeding to visualize how several blocks of memory location are stored as one complement in a specific name?! it's look like several blocks of memory location converted to one complement block to be stored in a specific name which its entity space of storing is one block(not several blocks)... looks like several blocks compressed to one block with specific name ..

thanks guys alot
 

WBahn

Joined Mar 31, 2012
26,398
It would really help if you took the time to actually try your code and post code that doesn't have syntax errors in it.

Because you haven't done this, I'm left to guess what you intended to do, and I don't see any reason to pull out my crystal ball.

In general, the definition of a structure merely tells the compiler what one of those things will look like should it every actually be used. It doesn't actually allocate any memory at all.

In this case, you are saying that when and if we do ever allocate any of these, each one will consist of a block of memory that will contain two members, one variable of type int and one array of chars that can hold at least twenty elements. It is also guaranteeing that they will be stored in this order within the block of memory and that the first member will start at the base address of the corresponding block of memory. That's pretty much all that is guaranteed. The compiler is free to place padding between members or at the end, usually in order to align members on word boundaries.

I'm curious just how much you've actually "read over the internet" trying to answer this for yourself.

https://en.wikipedia.org/wiki/Struct_(C_programming_language)

Google something like "how are C structs stored in memory" for lots of links on this.
 

Thread Starter

Ryan$

Joined Dec 14, 2018
178
It would really help if you took the time to actually try your code and post code that doesn't have syntax errors in it.

Because you haven't done this, I'm left to guess what you intended to do, and I don't see any reason to pull out my crystal ball.

In general, the definition of a structure merely tells the compiler what one of those things will look like should it every actually be used. It doesn't actually allocate any memory at all.

In this case, you are saying that when and if we do ever allocate any of these, each one will consist of a block of memory that will contain two members, one variable of type int and one array of chars that can hold at least twenty elements. It is also guaranteeing that they will be stored in this order within the block of memory and that the first member will start at the base address of the corresponding block of memory. That's pretty much all that is guaranteed. The compiler is free to place padding between members or at the end, usually in order to align members on word boundaries.

I'm curious just how much you've actually "read over the internet" trying to answer this for yourself.

https://en.wikipedia.org/wiki/Struct_(C_programming_language)

Google something like "how are C structs stored in memory" for lots of links on this.
Sir your words 100% but how actually I code something that's I'm not convinced in?! meaning if theory isn't clearing out for me ..so you guess that I will succeed code?!
and I asked the questions which are not related to the code by the way, I need to understand the concept of the using ..why I need that? to code in convenient and not like parrot "this as like this"
I hope you understand me, and I hope you help me :) thanks alot
if you please read again my question you will figure out that I asked about how should I "visualize" the struct and its address on the memory
Moreover, I'm confused of how too many blocks of memory location stored in one name as implicitly "one complement block"
 
Last edited:

WBahn

Joined Mar 31, 2012
26,398
Sir your words 100% but how actually I code something that's I'm not convinced in?! meaning if theory isn't clearing out for me ..so you guess that I will succeed code?!
Presenting syntactically correct code shouldn't be a big issue -- there's literally millions of code examples out on the Internet dealing with C structs. Pick a small program, compile and run it, and then use that as the code for discussion.

and I asked the questions which are not related to the code by the way, I need to understand the concept of the using ..why I need that? to code in convenient and not like parrot "this as like this"
There's nothing wrong with parroting when you are just starting to learn something. That's pretty much how we learn most things, whether it be karate, changing a flat tire on your car, learning to play the violin, or learning to write programs. Our knowledge of why we are doing what we are doing or how to do it truly properly is extremely limited. How we learn is to try to understand as much as we can, knowing that it won't be complete until we've done it many times.

I hope you understand me, and I hope you help me :) thanks alot
if you please read again my question you will figure out that I asked about how should I "visualize" the struct and its address on the memory
Moreover, I'm confused of how too many blocks of memory location stored in one name as implicitly "one complement block"
Think of a dresser with four drawers in it. Socks go in the top drawer, underwear in the next one down, scarves in the one below that, and tee shirts in the bottom one. They can all go into the same dresser and we can call that dresser by a single name, such as Bob's Dresser, with no problems.

Let's try to use the one you are trying to use.

C:
struct Book
{
   int size;
   char name[20];
};
Notice the semicolon at the end. That is NOT optional.

This declares a struct that contains a member that requires sizeof(int) bytes for 'size' and 20*sizeof(char) bytes for 'name'. It allocated NO memory for any actual instances of this struct, just tells the compiler what one will look like.

Let's assume that you are working on a 32-but platform and sizeof(int) is 4 bytes. The first member, 'size', will be stored at the beginning of the memory allocated for that instance of the structure -- known as at Offset 0. This is probably (but not guaranteed) to be the natural word size of the target hardware. But, for argument's sake, let's say that this compiler really wants to put things on 8-byte boundaries, so the next member, 'name', can't be stored starting at Offset 4 but rather will be stored at Offset 8. Since the 20 bytes for the char array is not divisible by 8, the compiler will add 4 bytes of padding to the end, making the entire structure take up 32 bytes.

So now you define a variable to be one of these stucts.

C:
struct Book b1;
Notice the keyword 'struct' there. It is NOT optional since Book is not a defined data type (which you could make it one by using a typedef statement).

So the compiler generates the code to allocate 32 bytes of memory and associates that with the identifier 'b1'.

When you do something like

b1.size = 42;

That generates the code to store the value 42 and an int starting at memory location (b1 + 0 bytes).

If you then do something like

strcpy(b1.name, "Fred");

That will generate the code to pass a pointer to (b1 + 8 bytes).

So if b1 was allocated memory at location 1000 (decimal), then it consists of memory locations 1000 through 1031. The member 'size' will be stored in locations 1000 through 1003. Locations 1003 through 1007 will not be used. The member 'name' will be stored at locations 1008 through 1027, and locations 1028 through 1031 will not be used.

One dresser, four drawers, two of which are always empty.

EDIT: Corrected 28 to 32 -- didn't update that sentence.
 
Last edited:

Thread Starter

Ryan$

Joined Dec 14, 2018
178
Presenting syntactically correct code shouldn't be a big issue -- there's literally millions of code examples out on the Internet dealing with C structs. Pick a small program, compile and run it, and then use that as the code for discussion.



There's nothing wrong with parroting when you are just starting to learn something. That's pretty much how we learn most things, whether it be karate, changing a flat tire on your car, learning to play the violin, or learning to write programs. Our knowledge of why we are doing what we are doing or how to do it truly properly is extremely limited. How we learn is to try to understand as much as we can, knowing that it won't be complete until we've done it many times.


Think of a dresser with four drawers in it. Socks go in the top drawer, underwear in the next one down, scarves in the one below that, and tee shirts in the bottom one. They can all go into the same dresser and we can call that dresser by a single name, such as Bob's Dresser, with no problems.

Let's try to use the one you are trying to use.

C:
struct Book
{
   int size;
   char name[20];
};
Notice the semicolon at the end. That is NOT optional.

This declares a struct that contains a member that requires sizeof(int) bytes for 'size' and 20*sizeof(char) bytes for 'name'. It allocated NO memory for any actual instances of this struct, just tells the compiler what one will look like.

Let's assume that you are working on a 32-but platform and sizeof(int) is 4 bytes. The first member, 'size', will be stored at the beginning of the memory allocated for that instance of the structure -- known as at Offset 0. This is probably (but not guaranteed) to be the natural word size of the target hardware. But, for argument's sake, let's say that this compiler really wants to put things on 8-byte boundaries, so the next member, 'name', can't be stored starting at Offset 4 but rather will be stored at Offset 8. Since the 20 bytes for the char array is not divisible by 8, the compiler will add 4 bytes of padding to the end, making the entire structure take up 32 bytes.

So now you define a variable to be one of these stucts.

C:
struct Book b1;
Notice the keyword 'struct' there. It is NOT optional since Book is not a defined data type (which you could make it one by using a typedef statement).

So the compiler generates the code to allocate 28 bytes of memory and associates that with the identifier 'b1'.

When you do something like

b1.size = 42;

That generates the code to store the value 42 and an int starting at memory location (b1 + 0 bytes).

If you then do something like

strcpy(b1.name, "Fred");

That will generate the code to pass a pointer to (b1 + 8 bytes).

So if b1 was allocated memory at location 1000 (decimal), then it consists of memory locations 1000 through 1031. The member 'size' will be stored in locations 1000 through 1003. Locations 1003 through 1007 will not be used. The member 'name' will be stored at locations 1008 through 1027, and locations 1028 through 1031 will not be used.

One dresser, four drawers, two of which are always empty.
Sir you're supurb helper, directed notions and all is on point !!
I've understood the idea, but last think you said "So the compiler generates the code to allocate 28 bytes of memory and associates that with the identifier 'b1'" which that's exactly what dramatically confusing me .... how exactly 28bytes in one complement associated to identifier b1, I mean b1 is something like variable, and 28bytes are too many variables, how actually too many variables stored in one variable? maybe I overthink it.
I didn't understand how actually the term "associate" done by the PC !

In our world to associate something it's like a symbol that implies about "something" that I associated, but in world of computing(computers) it's nonsense to say that PC makes a symbol ....

lets take an example of what confusing me.
lets assume I've five addresses which it allocates a BOOK struct, so five addresses is for BOOK struct, lets assume the five addresses are: 1 2 3 4 5 ; now I write BOOK b1; it's simple that b1 is now associated to a BOOK struct which have addresses 1 2 3 4 5 !
here ..all is fine, my question if I do &b1 so it means the addresses of the whole struct in other words that address is holding the five address(1 2 3 4 5) , is that address is one of the addresses of (1 2 3 4 5) ? or actually there's a different address at all that's denoting the five addresses of the struct?!

thanks really for your help
 
Last edited:

WBahn

Joined Mar 31, 2012
26,398
Sir you're supurb helper, directed notions and all is on point !!
I've understood the idea, but last think you said "So the compiler generates the code to allocate 28 bytes of memory and associates that with the identifier 'b1'" which that's exactly what dramatically confusing me .... how exactly 28bytes in one complement associated to identifier b1, I mean b1 is something like variable, and 28bytes are too many variables, how actually too many variables stored in one variable? maybe I overthink it.
I didn't understand how actually the term "associate" done by the PC !
First, I had a typo (actually, a sentence didn't get updated) and it should have said 32 bytes.

In our world to associate something it's like a symbol that implies about "something" that I associated, but in world of computing(computers) it's nonsense to say that PC makes a symbol ....

lets take an example of what confusing me.
lets assume I've five addresses which it allocates a BOOK struct, so five addresses is for BOOK struct, lets assume the five addresses are: 1 2 3 4 5 ; now I write BOOK b1; it's simple that b1 is now associated to a BOOK struct which have addresses 1 2 3 4 5 !
here ..all is fine, my question if I do &b1 so it means the addresses of the whole struct in other words that address is holding the five address(1 2 3 4 5) , is that address is one of the addresses of (1 2 3 4 5) ? or actually there's a different address at all that's denoting the five addresses of the struct?!

thanks really for your help
The address of a struct is the address of the first byte in the memory allocated to the stuct. Just like for any other variable or array.

Do you understand how arrays work?

If I have

int fred[12];

and if an int requires 4 bytes, do you understand that the fred array has 48 bytes allocated for it and that it holds 12 different int variables, each in a different four-byte section of that 48-byte block?

If you understand that, then there really isn't anything different about a struct, except that in an array we require each element to be the same type -- and that's only so that we can calculate the offset of a given element based only on knowing its index and the type of data stored in that array. In a struct, we relax this and let it have members of different types, but that means that we can't use the simply array indexing approach to access the member elements. Instead, we use the period (structure access operator) to do this.

As for what "associate" means, think of the compiler simply maintaining a list of all the identifier names and what address they were assigned in memory (and also what type and perhaps some other things). This is known as a symbol table. When we need to know the address of a variable we look up the name of the variable in the table and then get the address from that row in our list. This 'associates', or 'links' or 'ties together' an address with a variable name.
 

danadak

Joined Mar 10, 2018
4,057
In general, the definition of a structure merely tells the compiler what one of those things will look like should it every actually be used. It doesn't actually allocate any memory at all.
WBhan, is that true of local variables, but statics do get allocated ?


Regards, Dana.
 

Thread Starter

Ryan$

Joined Dec 14, 2018
178
As for what "associate" means, think of the compiler simply maintaining a list of all the identifier names and what address they were assigned in memory (and also what type and perhaps some other things). This is known as a symbol table. When we need to know the address of a variable we look up the name of the variable in the table and then get the address from that row in our list. This 'associates', or 'links' or 'ties together' an address with a variable name.
here what's confusing me "what address they were assigned" ..but lets assume I have struct which spaces from 100 - 400 memory location, so what's the address that we assigned it to the variables? are we assigning the last address of the data blocks(in my case 400) that already allocated on the memory to the variable name in the table for describing the whole data?that's what actually confusing me what address we assign to the variable name in the table, the first address or the last address of the data location?

thanks!
 

Ian Rogers

Joined Dec 12, 2012
901
To address struct members you use the '.' operator.. The compiler works the rest out..

C:
struct somestruct{
   int twobytes;
   char tenbytes[10];
   long fourbytes;
};

struct somestruct b1;

b1.twobytes = (int)b1.fourbytes;
access is pretty straight forward... You don't need to know the actual address!!!
 

WBahn

Joined Mar 31, 2012
26,398
here what's confusing me "what address they were assigned" ..but lets assume I have struct which spaces from 100 - 400 memory location, so what's the address that we assigned it to the variables? are we assigning the last address of the data blocks(in my case 400) that already allocated on the memory to the variable name in the table for describing the whole data?that's what actually confusing me what address we assign to the variable name in the table, the first address or the last address of the data location?

thanks!
What did I say?

The address of a struct is the address of the first byte in the memory allocated to the stuct. Just like for any other variable or array.
If you have an instance of a struct that occupies the memory from 100 to 400 (inclusive), then you have a 301 byte structure located at address 100.
 

WBahn

Joined Mar 31, 2012
26,398
WBhan, is that true of local variables, but statics do get allocated ?


Regards, Dana.
Much of the details depends on the implementation, but generally static variables are allocated memory at compile time since they live for the entire life of the program, whether they are local or not. Nonstatic local variables, known as "automatic" variables, are usually allocated memory on the runtime stack when the function containing them is invoked and they live until the particular call to that function returns.
 
Top