How do I put this struct into this dynamically allocated space? - c

I am working on a project that implements the buddy allocation algorithm in C. Using mmap(), I allocated a space of 1GB of continuous memory. It looks like this:
char * base = mmap(NULL, MAX_MEM, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANON, 0, 0);
I have a struct that I am trying to place into that space. The struct looks like this:
typedef struct Node {
unsigned char header;
struct Node *next;
struct Node *prev;
}node;
I am unsure how to get a node to go into that spot. I tried the code below because I didn't want to put the node at the very beginning, but when I print out the pointer they show much different spots
void *ptr = (struct Node *) base + 512;
printf("base: %p\n", base);
printf("ptr: %p\n", ptr);
My terminal window prints out this:
base: 0x102ef1000
ptr: 0x102ef4000
But this doesn't seem right because the pointers are 12288 spaces away from each other in memory instead of just 512. What am I doing wrong?

void *ptr = (struct Node *) base + 512;
means ((struct Node *) base) + 512.
What you want is
void *ptr = (struct Node *) (base + 512);
So you skip 512 bytes from the beginning of allocation.
According to the post, cast has higher precedence than addition.

Remember, as you cast base to a struct Node * adding to it will now add the size of a struct Node to the pointer, therefore you are adding sizeof(struct Node) * 512 to it. this is probably not what you want. Given it is a 24 byte struct this makes it 24 * 512 = 12288.
The reason it is 12 bytes is that is contains 2 8 byte pointers, a 1 byte char and 7 bytes of padding to ensure the pointers are aligned to 8 bytes.
To solve this simply omit the cast, it will leave base as a char * and increment it 512 bytes as wanted.
void *ptr = base + 512;

Related

malloc: get information from memory

I am currently doing a project to simulate loading and storing info like a computer Cache.
I used malloc to load a struct into memory but I don't know how to retrieve that information again.
For any line, I need to be able to call up a particular line in the cache and see if it causes a "hit or a miss" like a cache would.
struct cache {int s; int E; int b;}; //my struct
//creating a similated cache in memory.
struct cache** c1 = (struct cache**) malloc( pow(2,ssize) * Esize * sizeof(struct cache));`
Basically when you do
struct cache** c1 = (struct cache**) malloc( pow(2,ssize) * Esize * sizeof(struct cache)).
That is a pointer to pointer of struct cache. It is similar to an array of pointer to struct cache but it is not in your stack memory but in your heap memory. Nonetheless, you did it wrong. Each index of your struct cache ** suppose to be equal to the size of the pointer of struct cache. The code below probably explain everything.
After get space for struct cache **, each of its index you suppose to assign it with a pointer to struct * cache or malloc a pointer to struct cache with the size equal to the size struct cache. The code below, I created 10 index using malloc. So 0 - 9.
#include <stdlib.h>
#include <stdio.h>
struct cache {int s; int E; int b;}; //my struct
//creating a similated cache in memory.
int main(){
// Each index equal the size of a pointer to struct cache and there is 10 index
struct cache** c1 = (struct cache**) malloc( sizeof( struct cache* ) * 10 );
// Each index is a pointer to struct cache with the malloc size it pointing
// to equal to struct cache
c1[0] = (struct cache*) malloc( sizeof(struct cache) );
// Any later index would have to use malloc or assign a pointer to c1
c1[0]->s = 1;
c1[0]->E = 2;
c1[0]->b = 3;
printf("%d %d %d", c1[0]->s,
c1[0]->E,
c1[0]->b );
return 0;
}

What is the size of a structure pointer in C?

If the size of a structure pointer is 4 or say 8 bytes, how can it properly allocate the required memory for its data members in Dynamic Memory Allocation. This is my code:
#include<stdio.h>
typedef struct node{
char a[10];
char b[10];
char c[10];
int f;
struct node* next;
}node;
int main()
{
node* temp;
int d= sizeof(node *);
printf("Size of structure pointer = %d",d);
temp= (node*)malloc(sizeof(node*));
int c = sizeof(temp);
printf("Size of Temp = %d\n",c);
}
```````````````````
/*
Here both Temp and node* is having a size of 8 bytes.
But the size of the structure 'node' is 38 bytes(total size of the members).
So how can the pointer Temp allocate that much memory if its size is just 8 bytes ?
*/
Because you don't store data in pointers. Pointers point at data allocated elsewhere, hence the name "pointer". sizeof(node*) is wrong and the size of the pointer itself is irrelevant.
You should do
temp = malloc(sizeof *temp); // equivalent of sizeof(Node)
...
free(temp);
This is the pointer to the node struct, you don't need to allocate space for it. It can point to the node structure.
struct node *node_ptr;
If you want to store node structure at some pointer, you need to allocate space for the node structure NOT THE POINTER
node *node_data = malloc(sizeof(struct node));
You don't need to cast the result from the malloc, it is bad { see casting for malloc }
Pointer is just the pointer. It you are a tourist guide in the war museum and use the pointer to show the tank - what is the weight of the pointer in your hand? The weight of the wooden stick or the weight of the tank?
First lets understand about malloc:
Malloc is a function which allocates memory in a HEAP part of RAM. If we define a variable, usually it gets allocated in STACK part of RAM.
temp = (int*)malloc(n*sizeof(int));
this code allocates a memory in HEAP.
Now lets understand about ponters:
consider the following code.
int a;
int *p;
p=&a;
in the about line of code the pointer 'p' is storing the address of the variable 'a'.
Depending on the word length of your system(32bit or 64bit), the size of the pointer variable 'p' changes. It can be 2bytes or 4bytes or 8bytes. 8bytes is because in 64bit machine, "long int" can takes 8bytes.
Now lets understand about both pointers with structure:
struct value{
int a;
int b;
char c;
};
Since above code is a definition of structure, memory won't get allocated.
struct value s;
now the memory gets allocated in Stack.
struct value *s;
s = (struct value*)malloc(sizeof(struct value));
here the memory gets allocated in Heap.
Even though 's' is structure pointer it still stores the address of the whole structure 'value', it's size will be 4/8. It points to whole structure not the particular member of structure.
The general structure 's' will have the data part of all its members. So the size will be 5 or 9 depending of the machine and the padding.
struct s{
int a; /* 4 bytes */
char b; /* 1 byte */
/* 1 padding byte */
short c; /* 2 bytes */
};
Refer Data Structure Padding

Final size of a structure variable of data structure "stack" (implementation through structure and its creation through function)

So I am learning about data structure stack in my college, howsoever I have some doubts in its implementation and the memory it occupies.
Below is a small code which I have written for it: -
# include <stdio.h>
# include <stdlib.h>
# include <string.h>
# include <stdbool.h>
struct stack
{
int *array;
int top;
int max_size;
};
struct stack createStack(int size)
{
struct stack *Stack = malloc(sizeof(struct stack)); //line 1
Stack -> max_size = size; //line 2
Stack -> top = -1; //line 3
Stack -> array = calloc(Stack -> max_size, sizeof(int)); //line 4
return *Stack;
}
int main()
{
int size; //Here lets say that size = 5
scanf("%d", &size);
printf("%ld", sizeof(createStack(size)));
return 0;
}
Here I have defined Stack through struct stack as seen below in this portion of the code: -
struct stack
{
int *array;
int top;
int max_size;
};
Now the memory which would be occupied by the above struct stack should be: -
8 bytes for int *array
4 bytes for int top
4 bytes for int max_size
Therefore total memory occupied\allocated should be 16 bytes.
Now lets come to the second portion of code which helps in creation of stack: -
struct stack createStack(int size)
{
struct stack *Stack = malloc(sizeof(struct stack)); //line 1
Stack -> max_size = size; //line 2
Stack -> top = -1; //line 3
Stack -> array = calloc(Stack -> max_size, sizeof(int)); //line 4
return *Stack;
}
Here in line 1 we have allocated the sizeof struct stack(16 bytes) in structure variable *Stack. Hence size of * Stack is 16 bytes.
In line 2 and in line 3 values are initialised.
Now my question come from line 4
In line 4 we allocated 20 bytes to int *array (considering max_size = 5)
Now shouldn't the size of structure variable *Stack be 28 bytes considering that int *array now occupies 20 bytes instead of 8 bytes ?
When I run the above code, it still mentions that the sizeof structure variable *Stack is 16 bytes. What am i missing here?
Now shouldn't the size of structure variable *Stack be 28 bytes considering that int *array now occupies 20 bytes instead of 8 bytes?
No. The size of array is still 8 bytes. It just contains the memory address of a separate chunk of memory that is 20 bytes in size. That separate chunk is not part of *Stack and does not contribute to its size.
In fact, sizeof(createStack(size)) does not call your function, so no memory is ever allocated. sizeof only cares about the type of its operand expression. Since createStack is declared as returning a struct stack, sizeof createStack(...) is equivalent to sizeof (struct stack). All of this is resolved at compile time.
Similarly, if you do
char arr[1000];
char *ptr = &arr[0];
then sizeof ptr is still 8 because ptr is declared as char * and sizeof (char *) is 8. That's all that matters.
By the way, if you were to actually call createStack, it would leak memory:
struct stack *Stack = malloc(sizeof(struct stack));
...
return *Stack;
The first line allocates memory and stores the address in Stack. However, this address does not leave the function. Only a copy of the struct itself is returned (via return *Stack). The program has now lost track of the pointer returned by malloc and can never free it.
Fix:
struct stack Stack;
Stack.max_size = size;
Stack.top = -1;
Stack.array = calloc(Stack -> max_size, sizeof(int));
return Stack;
The size of a structure is just the amount of memory used for the structure itself, not the memory for any things pointed to be members of the structure.
The fact that array is given a value that points to more memory does not change the structure or its size.
sizeof reports only the memory required for a particular object. It does not report all memory you have associated or linked to in some way.

Can any one explain me how the size get allocated in the following case? [duplicate]

This question already has answers here:
Structure padding and packing
(11 answers)
Closed 3 years ago.
I got confused with the size allocation with my gcc compiler, can any one help me how the size get allocated for the following code.
struct node
{
int data;
struct node *next;
};
sizeof(struct node) it gives an output as 16.
struct node
{
int data;
};
sizeof(struct node) it gives an output as 4.
struct node
{
struct node *next;
};
sizeof(struct node) it gives an output as 8.
struct node
{
int data;
struct node *next;
}*link;
sizeof(link) is always 8, even if i add few more elements to structure.
On your specific platform, it looks like an int has size 4 and a pointer has size 8. It also looks like it wants to align pointers on an 8-byte boundary.
So if struct node just contains an int, then the its size is 4. If it just contains a pointer, its size is 8. If it contains both an int and a pointer, then it needs 12 bytes, but in order to maintain the alignment of the pointer, it pads the structure to a multiple of 8, resulting in a size of 16.
In your final example, you have link defined as a pointer to a struct node. In this case, it doesn't matter what a struct node contains. Since link is just a pointer, its size will always be 8.
Again, note that this is just a best guess for your platform. None of this is guaranteed, and it can vary from one platform to another.
sizeof return size in bytes
int have 32 bits = 4 bytes
Any pointer char*, struct any* has const sizeof depends memory structure, in your case is 8.
Because of memory alligment your first example has sizeof = 16, more here: https://en.wikipedia.org/wiki/Data_structure_alignment , you can add #pragma pack(1) and see diffrents, should be 4 + 8 = 12
sizeof(link) will always return 8 bytes because that's the size of a pointer in a 64 bits computer.
If you want the size of the structure you need to do sizeof(struct node) as it will give you the size of the actual struct.
And for a linked list type struct I would recomend you something like this
typedef struct node Node, *pnode;
struct node{
//some vars
pnode next;
}
Then you'll just need to declare it your main or anywhere you as
pnode list = NULL;
sizeof(Node) //for memory allocation

C program - Structure variable data packing and alignment

What will be the output of the program on a 32-bit machine (using GCC)? Explain.
#include<stdio.h>
int main() {
struct node {
int data;
struct node *link;
};
struct node *p, *q;
p = (struct node *) malloc(sizeof(struct node));
q = (struct node *) malloc(sizeof(struct node));
printf("%d, %d\n", sizeof(p), sizeof(q));
return 0;
}
The output shows
4, 4.
Is the above program related to structure member alignment padding and data packing?
No, you are just printing the size of the pointers. It's not related to the internal member layout of structures.
On a 32-bit system the stored addresses are always 32 bits big. If you're printing the size of a pointer you're basically just printing the size of the address it points to (32 Bit -> 4 Byte).
If you want to know the size of the struct do something like this:
struct node p;
struct node q = {4, &p};
printf("%zu, %zu\n", sizeof(p), sizeof(q));
Point 1 Use %zu format specifier to print the output of sizeof of type size_t .
Point 2 Note the type of p, it is struct node *, same as q.
So, essentially, sizeof(p) and sizeof(q) are exactly same as sizeof(struct node *), which, on your platform are 32 bit wide. As you're not considering a variable here, so the alignment and padding for the structure and members are neither relevant nor involved in this case.
That said, please see why not to cast the return value of malloc() and family in C.
No, it is not related to the structure member alignment padding and data packing.
Since it is a 32-bit machine the size of any pointer will be 4 bytes. Since p and q are of type struct node * i.e. pointer to struct node the result prints size of pointers p and q.

Resources