newprogrammer
newprogrammer

Reputation: 620

Malloc an array of structs.

I am still learning C and have run into some trouble while trying to malloc structures. I have the following structure:

struct data {
int *ref; 
int *port;
char data[MAX_STRING];
}temp, valid, invalid;

I intend on using the 'temp' struct to store input data before it is validated, then dependent on the outcome of the validation the struct will be copied to a member of either the valid or invalid array of structs.

int main(){
   char inputfile[100];
   FILE *file; = fopen("file.txt" , "r");

   if (file != NULL){
      read_file (file);
   }

   else{
    // Some code here..
   }

   return 0;
}  

void read_file(FILE *file)
{

char buf[1024];

   while(!feof (file))
   {
       struct temp *p_temp = malloc(sizeof(temp));

       p_temp->ref = malloc(sizeof(int));         <<<<<<< 'dereferencing pointer to incomplete type'
       p_temp->port = malloc(sizeof(int));        <<<<<<< 'dereferencing pointer to incomplete type'
       p_temp->data = malloc(sizeof(MAX_STRING)); <<<<<<< 'dereferencing pointer to incomplete type'

       fgets(buf, sizeof buf, file); 

       sscanf(buffer, "%d.%d.%s", p_temp->ref, p_temp->port,  p_temp->data);

       validate();

     }
}

Have I gone about using malloc the correct way with the temporary structure? I am getting the error 'dereferencing to incomplete type'

How would I then go about creating an array of valid and invalid structures that are malloced? Would I create a function such as:

vaild* vaild_record(){

struct vaild *p_vaild = malloc(sizeof(vaild));
if ( p_vaild == NULL)

{
    // some code here
}

p_vaild->ref= malloc(sizeof(int));
p_vaild->port = malloc(sizeof(int));
p_vaild->data =(char)malloc(sizeof(STRINGMAX);

if ( p_vaild->ref == NULL || p_vaild->port == NULL || p_vaild->data == NULL)
{
   // some code here
}

return 0;
}

Im a bit confused about the whole thing. Any clarity would be great thanks.

Upvotes: 0

Views: 1475

Answers (3)

user3629249
user3629249

Reputation: 16550

Your definition of the struct:

struct data {
    int *ref; 
    int *port;
    char data[MAX_STRING];
}temp, valid, invalid;

should be more like this:

struct data 
{
    int *ref; 
    int *port;
    char data[MAX_STRING];
};

then define the arrays similar to this:

struct data temp;

struct data* valid = NULL;
struct data* invalid = NULL;
int currentValidSize = 0;
int currentInvalidSize = 0;
struct data * validTemp = NULL;
struct data * invalidTemp = NULL;

then, each time the code needs room for (another) instance of a struct

struct data *validTemp = realloc(valid, (currentValidSize+1)* sizeof(data) );
if( NULL == validTemp )
{ // realloc failed
    perrof( "realloc failed" );

    // free everything, close files, etc here probably be writing a sub function
    // and calling it here.
    // a sub function that: 
    // that walks the valid and invalid arrays, 
    // first free'ing any malloc'd fields
    // then finally free'ing the whole array

    exit( EXIT_FAILURE );
}

// implied else, realloc successful

// update array size counter
currentValidSize++;

// update ptr to valid array of structs
valid = validTemp;
validTemp = NULL;

similar for adding an entry to the invalid array of structs

then update the valid array of structs from temp as:
(note the '-1' in the offset into valid[])

memcpy( &valid[currentValidSize-1], &temp, sizeof data );
// Note you will also have to perform a 'deep' copy of any areas 
// that were malloc'd within the 'temp' struct

Upvotes: 1

Iharob Al Asimi
Iharob Al Asimi

Reputation: 53046

Your problem is the way you declared the struct it should be

struct data 
{
    int *ref; 
    int *port;
    char data[MAX_STRING];
};

and then you do

struct data *p_valid;
p_valid = malloc(sizeof(struct data));

another thing is

p_valid->data = malloc(sizeof(STRINGMAX));

is wrong because data is not a pointer. And sizeof(STRINGMAX) is wrong too, since STRINGMAX seems to be a macro and hence it will expand to it's value say if you have #define STRINGMAX 4 then it would expand to sizeof(4).

Upvotes: 3

Antony
Antony

Reputation: 199

From just a quick look, I think your problem may be where you are mallocing in the read_file function. You should havemalloc(sizeof(struct temp)).

Also casting the malloc wouldn't hurt.

Also there is no need for the temp, valid, invalid at the end of the struct, just use struct data

Hope this helps

Upvotes: -1

Related Questions