Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Comment: still perfecting...

...

Noncompliant Code Example (Function Arguments)

When using structures with a flexible array member you should never directly pass an instance of the structure as an argument to a function. In this noncompliant code, the flexible array structure is passed directly to a function which tries to print the array elements.

Code Block
bgColor#FFcccc
void print_array(struct flexArrayStruct structP) {
  size_t i;

  puts("Array is: ");
  for (i = 0; i < structP.num; i++) {
    printf("%d", structP.data[i]);
  }
  puts("\n");
}

struct flexArrayStruct *structP;
size_t array_size;
size_t i;

/* initialize array_size */

/* space is allocated for the struct */
structP = (struct flexArrayStruct *)malloc(
  sizeof(struct flexArrayStruct) + sizeof(int) * array_size
);
if (structP == NULL) {
  /* Handle malloc failure */
}

structP->num = array_size;

for (i = 0; i < array_size; i++) {
  structP->data[i] = i;
}

print_array(*structP);

The problem with this code is that passing the structure directly to the function actually makes a copy of the structure. This copied fails for the same reason as the previous copy exampleBecause C passes the argument by value, a the structure is copied onto the stack. The size of the flexible array member is not considered when the structure is copied and only the first member of the structure, num, is copied.

Compliant Solution (Function Arguments)

Never allow a structure with a flexible array member to be passed directly in a function call. The above code can be fixed by changing the function to accept In this compliant solution, the {{print_array()}}function accepts a pointer to the structure and not .

Code Block
bgColor#ccccff
void print_array(struct flexArrayStruct *structP) {
  size_t i;

  puts("Array is: ");
  for (i = 0; i < structP->num; i++) {
    printf("%d", structP->data[i]);
  }
  puts("\n");
}

struct flexArrayStruct *structP;
size_t array_size;
size_t i;

/* initialize array_size */

/* space is allocated for the struct */
structP = (struct flexArrayStruct *)malloc(
  sizeof(struct flexArrayStruct) + sizeof(int) * array_size
);
if (structP == NULL) {
  /* Handle malloc failure */
}

structP->num = array_size;

for (i = 0; i < array_size; i++) {
  structP->data[i] = i;
}

print_array(structP);

...