Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Comment: made variable names more distinct

...

The following noncompliant code example defines A to be a variable length array type and then uses the sizeof operator to compute its size at runtime.  When the function is called with an argument greater than SIZE_MAX / (N N1 * n2 * sizeof (int)), the runtime sizeof expression may wrap around, yielding a result that is smaller than the mathematical product N N1 * n n2 * sizeof (int).  The call to malloc(), when successful, will then allocate storage for fewer than n n2 elements of the array, causing one of the final memset() calls in the for loop to write past the end of that storage.

Code Block
bgColor#FFCCCC
langc
#include <stdlib.h>
#include <string.h>
 
enum { NN1 = 4096 };

void* func(size_t nn2) {
  typedef int A [nn2][NN1];

  A *array = malloc(sizeof (A));

  for (size_t i = 0; i != nn2; ++i)
    memset(array [i], 0, NN1 * sizeof (int));

  return array;
}

...

Code Block
bgColor#ccccff
langc
#include <stdlib.h>
#include <string.h>
 
enum { NN1 = 4096 };

void* func(size_t nn2) {
  if (nn2 > SIZE_MAX / (NN1 * sizeof (int))) {
    /* Prevent sizeof wrapping */
    return NULL;
  }

  typedef int A [nn2][NN1];

  A *array = malloc(sizeof (A));
  if (array == NULL) {
    /* Handle malloc failure */
    return NULL;
  } 

  for (size_t i = 0; i != nn2; ++i)
    memset( array [i], 0, NN1 * sizeof (int));

  return array;
}

...