[C-safe-secure-studygroup] checker

Martin Sebor msebor at gmail.com
Wed Jan 23 20:35:15 GMT 2019


On 1/23/19 11:06 AM, Robert Seacord wrote:
> Has anyone implemented a static analysis checker that would detect when 
> a programmer incorrectly specifies the size of the source array instead 
> of the destination array, for example:
> 
> void func (void) {
> 
>    char source[] = "...";
> 
>    char dest[N];
> 
>    ...
> 
>    strcpy_s(dest, sizeof source, source);
> 
> }

GCC detects this bug in the uses of the standard functions.  It's
a fairly simple check done in the front-end so in principle it could
be extended to any other function whose API makes it clear which
integer argument is the size of which pointer argument.  This could
be done even for user-defined functions by providing an attribute
such objsize:

   __attribute__ ((objsize (1, 2))
   char* strcpy_s (char*, size_t, const char*);

The attribute specifies that the size of the object pointed to by
the argument 1 is specified by argument 2.  I have been working on
a project that does that so that it's also possible to verify that
the specified size isn't greater than the actual size of the buffer.

GCC also detects buffer overflows when it can determine both the size
of the buffer and the length of the string.  This is more involved
and usually only available with optimization (the copy has to be used
to get the warning, otherwise the code is eliminated before the warning
is issued).  This is what the attribute above will hook into when it's
done.

$ cat u.c && gcc -O -S -Wall
#include <string.h>

char dest[2];

void f (void)
{
   char source[] = "...";
   strncpy (dest, source, sizeof source);
}
u.c: In function ‘f’:
u.c:8:33: warning: argument to ‘sizeof’ in ‘strncpy’ call is the same 
expression as the source; did you mean to use the size of the 
destination? [-Wsizeof-pointer-memaccess]
     8 |   strncpy (dest, source, sizeof source);
       |                                 ^~~~~~
u.c:8:3: warning: ‘strncpy’ forming offset [3, 4] is out of the bounds 
[0, 2] of object ‘dest’ with type ‘char[2]’ [-Warray-bounds]
     8 |   strncpy (dest, source, sizeof source);
       |   ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
u.c:3:6: note: ‘dest’ declared here
     3 | char dest[2];
       |      ^~~~

Martin



More information about the C-safe-secure-studygroup mailing list