Solved

# memory allocation in structures

Posted on 2004-04-24
517 Views
Hello all,
I am experiencing trouble with memory allocation and de-allocation to the following C structure. I might be wrong, but I would like to know the correct procedure to do it.

//globally declared variables
int num_steps = 0;
int num_parts = 0;
struct TIMESTEP
{
float *x;
float *y;
float *z;
};
TIMESTEP *timestep;

//right now, I dont know how many timestep structures I will need and how many x,y & z would be needed in the structure. I would know that info in the run time. Later, in the run time, I would know for example:
num_steps = 10;
num_parts = 25;

//Then, in some function blaw_blaw():

void blaw_blaw(int num_steps, int num_parts)
{
free(timestep->x);
free(timestep->y);
free(timestep->z);
free(timestep);

timestep = (struct TIMESTEP *)malloc(num_steps*sizeof(struct TIMESTEP));
for(int i=0; i<num_steps; i++)
{
timestep[i].x = (float *)malloc(num_steps*sizeof(float));
timestep[i].y = (float *)malloc(num_steps*sizeof(float));
timestep[i].z = (float *)malloc(num_steps*sizeof(float));
}

for(int j=0; j<num_parts; j++)
{
for(i=0; i<num_steps; i++)
{
fscanf(fp3, "%s%s%s%s%s%s", s1, s2, s3);  //obtained from some ascii file
timestep[i].x[j] = (float) atof(s1);
timestep[i].y[j] = (float) atof(s2);
timestep[i].z[j] = (float) atof(s3);
}
}
}
//I call this function at some place in my code. The above scheme of memory allocation and deallocation kind of worked for me once. However, later in my code when I had to re-use the variable with some more memory, the program crashed.

Question: IS THIS A CORRECT SCHEME OF MEMORY ALLOCATION AND DE-ALLOCATION TO C-STRUCTURES OF UNKNOWN NUMBER WITH ITS ARRAY MEMBERS OF UNKNOWN SIZE ? If NO, what is the correct way? I dont have any idea of linked lists, and I am out of time to learn the ABCDs of linked lists. Can some one really explain me how to allocate and de-allocate memory in the above structure ? I also dont know the x, y, z array sizes. Can some one please help me?

Thanks,
Vijay.

0
Question by:vijaykiran

LVL 9

Expert Comment

ID: 10910500
For allocation ,you'd do:

timestep = (struct TIMESTEP *)malloc(num_steps*sizeof(struct TIMESTEP));
for(int i=0; i<num_steps; i++)
{
timestep[i].x = (float *)malloc(num_steps*sizeof(float));
timestep[i].y = (float *)malloc(num_steps*sizeof(float));
timestep[i].z = (float *)malloc(num_steps*sizeof(float));
}

for(int i=0; i<num_steps; i++)
{
free(timestep[i].x);
free(timestep[i].y);
free(timestep[i].z);
}
free(timestep);

void blaw_blaw(int num_steps, int num_parts)
{
free(timestep->x);
free(timestep->y);
free(timestep->z);
free(timestep);

In the first execution,you're trying to free memory which hasnt been allocated as yet,which can lead to unexpected results.

So,place the freeing code at the end of the function(or the program as the case may be)
0

LVL 23

Assisted Solution

brettmjohnson earned 100 total points
ID: 10910680
You are overrunning your arrays of floats.

Each is allocated to hold num_steps (10) floats, but you populate them with num_parts (25) floats.

Your allocation should look like this:
timestep = (struct TIMESTEP *)malloc(num_steps*sizeof(struct TIMESTEP));
for(int i=0; i<num_steps; i++)
{
timestep[i].x = (float *)malloc(num_parts*sizeof(float));
timestep[i].y = (float *)malloc(num_parts*sizeof(float));
timestep[i].z = (float *)malloc(num_parts*sizeof(float));
}
0

Author Comment

ID: 10910801
Ohh sorry brettmjohnson,
I did a little mistake while posting the code snippet. I have written my code the way you mentioned though. However, I havent tried the method which ankuratvb suggested. I will check it and get back with results and comments.

Thanks,
vijay.
0

Author Comment

ID: 10914512
Hello ankuratvb,
I tried using the method you suggested. It still doesnt work for me. In my code, I call the function blaw_blaw a number of times, and I made sure that I free the memory only after I allocate memory atleast once. But even then, it blows up.

I used debug to go in and find out what could be the problem, but it says that it cannot go past the free() at all. I used the header <stdlib.h>
I then used realloc instead of malloc so that I can eliminate free altogether except that I placed free() at the end of the program, which obviously didnt work because I wasnt able to reach the end of the program.

If you guys have any idea what else could  be wrong, please let me know.

Thanks,
Vijay.
0

LVL 9

Expert Comment

ID: 10914663

Also,check the return value of malloc to see whether the mem. was successfully allocated or not.

If you are calling this function a lot of times,i'd suggest using realloc instead of mallocing and freeing every time.
0

Assisted Solution

agri_amit earned 100 total points
ID: 10915459
vijaykiran,

use calloc instead of malloc.and let me know the result.
Also put a error handling after allocating memory like.
if(!timestep )
printf("not able to allocate memory;

it will provide the better pic., what is happ. with ur code.

tx,
amit

0

Author Comment

ID: 10916091
A dumb question - Is it necessary to free the memory if i reuse a variable by using calloc ? I know that it is not necessary when using realloc. But I am not sure of the case with calloc.

ankuratvb, I am at school right now. I will post the code when I go home. Thank you very much for all the support guys. I really appreciate it. I should have used this site more often.

-vijay.
0

LVL 16

Accepted Solution

PaulCaswell earned 200 total points
ID: 10916519
vijay,

//globally declared variables
int num_steps = 0; // ** This will just confuse you because you have global and local versions of these variables.
int num_parts = 0; // ** I suggest you remove them.

struct TIMESTEP
{
float *x; // ** Can I guess that there are num_parts of these?
float *y; // ** And these?
float *z; // ** And these?
};
TIMESTEP *timestep; // ** And num_steps of these?

//right now, I dont know how many timestep structures I will need and how many x,y & z would be needed in the structure. I would know that info in the run time. Later, in the run time, I would know for example:
num_steps = 10; // ** Confusing again. See above.
num_parts = 25;

//Then, in some function blaw_blaw():

void blaw_blaw(int num_steps, int num_parts)
{
free(timestep->x);
free(timestep->y);
free(timestep->z);
free(timestep);

// ** This is not the problem!
timestep = (struct TIMESTEP *)malloc(num_steps*sizeof(struct TIMESTEP));
for(int i=0; i<num_steps; i++)
{
timestep[i].x = (float *)malloc(num_steps*sizeof(float)); // ** Change this to num_parts*sizeof(float)
timestep[i].y = (float *)malloc(num_steps*sizeof(float)); // ** And this.
timestep[i].z = (float *)malloc(num_steps*sizeof(float)); // ** And this.
}

for(int j=0; j<num_parts; j++) // ** Change this to i and num_steps
{
for(i=0; i<num_steps; i++) // ** Change this to j and num_parts
{
// ** You are reading 6 strings into 3 variables, probably a mistake.
fscanf(fp3, "%s%s%s%s%s%s", s1, s2, s3);  //obtained from some ascii file
timestep[i].x[j] = (float) atof(s1);
timestep[i].y[j] = (float) atof(s2);
timestep[i].z[j] = (float) atof(s3);
}
}
}

There are two primary errors that would/will cause crashes.

1. You are allocating the float arrays num_steps long instead of num_parts.
2. You are reading 6 strings into 3 variables. The other 3 strings will go to random locations.

The secondary error, as the others have pointed out, is that you need to deallocate the memory correctly.

Paul
0

LVL 9

Assisted Solution

ankuratvb earned 100 total points
ID: 10917406
Paul is right.The fscanf() might also be causing the crash(though on my compiler it doesnt crash,i guess it discards the extra parameters read in).

>A dumb question - Is it necessary to free the memory if i reuse a variable by using calloc ? >I know that it is not necessary when using realloc. But I am not sure of the case with >calloc.

Yes.calloc() is also used for allocating memory(not reallocating without free).The difference to malloc is that calloc sets all the allocated memory to zeroed bytes rather than junk values which exist with malloc.

0

Author Comment

ID: 10964371
I hate this hectic semester. Dont even have time to get some rest. Sorry guys, I've been very bad at responding to the queries/comments.

I am still facing the same problem with my code.

Paul, the code that I posted in my first question was a little changed for understanding sakes. So, I have stripped the un-necessary parts, and while doing so, I have mis-typed a few statements. And yes, I have the correct number of %s's in fscanf statement. Also, I swapped the order of the for loops (i & j). But I still face the same problem.

This function blaw_blaw gets called everytime the file associated with the file pointer fp3 gets changed. That means, I would need to reallocate memory every time the function blaw_blaw gets called. Neither does realloc nor malloc work for me.

The strange thing is that I am having no problems if I do not free the memory at all. If I put the statement free, my program is somehow crashing. When running in Debug mode, it points to the free() function call. I do not have any freaking idea why this is happening.

-vijay.
0

LVL 9

Expert Comment

ID: 10965479
Why on earth did you close the question then?

You could try this:

In your blaw_blaw function,give only the realloc command,and free the memory when your program is about to end,at the end of main().

What compiler are you using?
Do you have alloc.h or malloc.h included as well?
0

LVL 9

Expert Comment

ID: 10965487
You could also try the malloc and free() in a separate small program to test whether its your code or the library thats causing the problem.
0

## Featured Post

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

### Suggested Solutions

Problem with form project 66 317
Passing command line arguments in C 10 85
smtp c source code 7 45
Computer slow / BSOD 10 42
An Outlet in Cocoa is a persistent reference to a GUI control; it connects a property (a variable) to a control.  For example, it is common to create an Outlet for the text field GUI control and change the text that appears in this field via that Ouâ€¦
This is a short and sweet, but (hopefully) to the point article. There seems to be some fundamental misunderstanding about the function prototype for the "main" function in C and C++, more specifically what type this function should return. I see soâ€¦
The goal of this video is to provide viewers with basic examples to understand opening and writing to files in the C programming language.
The goal of this video is to provide viewers with basic examples to understand recursion in the C programming language.