Add strncat and strrchr to bounds checking

This commit is contained in:
herman ten brugge 2022-11-25 00:31:32 -06:00
parent f48efeef8c
commit 28fa4d3db6
6 changed files with 89 additions and 7 deletions

View File

@ -269,7 +269,9 @@
__BOTH(int, strcmp, (const char*, const char*))
__BOTH(int, strncmp, (const char*, const char*, __SIZE_TYPE__))
__BOTH(char*, strcat, (char*, const char*))
__BOTH(char*, strncat, (char*, const char*, __SIZE_TYPE__))
__BOTH(char*, strchr, (const char*, int))
__BOTH(char*, strrchr, (const char*, int))
__BOTH(char*, strdup, (const char*))
#if defined __ARM_EABI__
__BOUND(void*,__aeabi_memcpy,(void*,const void*,__SIZE_TYPE__))

View File

@ -292,7 +292,9 @@ DLL_EXPORT char *__bound_strncpy(char *dst, const char *src, size_t n);
DLL_EXPORT int __bound_strcmp(const char *s1, const char *s2);
DLL_EXPORT int __bound_strncmp(const char *s1, const char *s2, size_t n);
DLL_EXPORT char *__bound_strcat(char *dest, const char *src);
DLL_EXPORT char *__bound_strncat(char *dest, const char *src, size_t n);
DLL_EXPORT char *__bound_strchr(const char *string, int ch);
DLL_EXPORT char *__bound_strrchr(const char *string, int ch);
DLL_EXPORT char *__bound_strdup(const char *s);
#if defined(__arm__) && defined(__ARM_EABI__)
@ -424,7 +426,9 @@ static unsigned long long bound_strncpy_count;
static unsigned long long bound_strcmp_count;
static unsigned long long bound_strncmp_count;
static unsigned long long bound_strcat_count;
static unsigned long long bound_strncat_count;
static unsigned long long bound_strchr_count;
static unsigned long long bound_strrchr_count;
static unsigned long long bound_strdup_count;
static unsigned long long bound_not_found;
#define INCR_COUNT(x) ++x
@ -1259,7 +1263,9 @@ void __attribute__((destructor)) __bound_exit(void)
fprintf (stderr, "bound_strcmp_count %llu\n", bound_strcmp_count);
fprintf (stderr, "bound_strncmp_count %llu\n", bound_strncmp_count);
fprintf (stderr, "bound_strcat_count %llu\n", bound_strcat_count);
fprintf (stderr, "bound_strncat_count %llu\n", bound_strncat_count);
fprintf (stderr, "bound_strchr_count %llu\n", bound_strchr_count);
fprintf (stderr, "bound_strrchr_count %llu\n", bound_strrchr_count);
fprintf (stderr, "bound_strdup_count %llu\n", bound_strdup_count);
fprintf (stderr, "bound_not_found %llu\n", bound_not_found);
#endif
@ -1940,6 +1946,24 @@ char *__bound_strcat(char *dest, const char *src)
return strcat(r, s);
}
char *__bound_strncat(char *dest, const char *src, size_t n)
{
char *r = dest;
const char *s = src;
size_t len = n;
dprintf(stderr, "%s, %s(): %p, %p, 0x%lx\n",
__FILE__, __FUNCTION__, dest, src, (unsigned long)n);
INCR_COUNT(bound_strncat_count);
while (*dest++);
while (len-- && *src++);
__bound_check(r, (dest - r) + (src - s) - 1, "strncat dest");
__bound_check(s, src - s, "strncat src");
if (check_overlap(r, (dest - r) + (src - s) - 1, s, src - s, "strncat"))
return dest;
return strncat(r, s, n);
}
char *__bound_strchr(const char *s, int c)
{
const unsigned char *str = (const unsigned char *) s;
@ -1957,6 +1981,24 @@ char *__bound_strchr(const char *s, int c)
return *str == ch ? (char *) str : NULL;
}
char *__bound_strrchr(const char *s, int c)
{
const unsigned char *str = (const unsigned char *) s;
unsigned char ch = c;
dprintf(stderr, "%s, %s(): %p, %d\n",
__FILE__, __FUNCTION__, s, ch);
INCR_COUNT(bound_strrchr_count);
while (*str++);
__bound_check(s, (const char *)str - s, "strrchr");
while (str != (const unsigned char *)s) {
if (*--str == ch)
break;
}
__bound_check(s, (const char *)str - s, "strrchr");
return *str == ch ? (char *) str : NULL;
}
char *__bound_strdup(const char *s)
{
const char *p = s;

View File

@ -156,8 +156,18 @@ int main()
#elif defined test_bcheck_125
strcat(&a[3], &a[0]);
#elif defined test_bcheck_126
strchr(&b[0], 'a');
strncat(&a[7], &a[0], 3);
#elif defined test_bcheck_127
strncat(&a[0], &b[3], 8);
#elif defined test_bcheck_128
strncat(&a[0], &a[4], 3);
#elif defined test_bcheck_129
strncat(&a[3], &a[0], 10);
#elif defined test_bcheck_130
strchr(&b[0], 'a');
#elif defined test_bcheck_131
strrchr(&b[0], 'a');
#elif defined test_bcheck_132
free(strdup(&b[0]));
#endif
}

View File

@ -134,9 +134,29 @@
[returns 255]
[test_bcheck_126]
112_backtrace.c:159: at main: BCHECK: invalid pointer ........, size 0x? in strchr
112_backtrace.c:159: at main: BCHECK: invalid pointer ........, size 0x? in strncat dest
[returns 255]
[test_bcheck_127]
112_backtrace.c:161: at main: BCHECK: invalid pointer ........, size 0x? in strdup
112_backtrace.c:161: at main: BCHECK: invalid pointer ........, size 0x? in strncat dest
[returns 255]
[test_bcheck_128]
112_backtrace.c:163: at main: BCHECK: overlapping regions ........(0x?), ........(0x?) in strncat
[returns 255]
[test_bcheck_129]
112_backtrace.c:165: at main: BCHECK: overlapping regions ........(0x?), ........(0x?) in strncat
[returns 255]
[test_bcheck_130]
112_backtrace.c:167: at main: BCHECK: invalid pointer ........, size 0x? in strchr
[returns 255]
[test_bcheck_131]
112_backtrace.c:169: at main: BCHECK: invalid pointer ........, size 0x? in strrchr
[returns 255]
[test_bcheck_132]
112_backtrace.c:171: at main: BCHECK: invalid pointer ........, size 0x? in strdup
[returns 255]

View File

@ -60,12 +60,20 @@ main (void)
r = (__builtin_memcmp (p, str, sizeof(str)));
printf(" 11:%d", !r);
r = (__builtin_strchr(p, 'z') != &p[25]);
tmp[0] = '\0';
p = __builtin_strncat(tmp, str, __builtin_strlen(str));
r = (__builtin_memcmp (p, str, sizeof(str)));
printf(" 12:%d", !r);
r = (__builtin_strchr(p, 'z') != &p[25]);
printf(" 13:%d", !r);
r = (__builtin_strrchr(p, 'z') != &p[25]);
printf(" 14:%d", !r);
p = __builtin_strdup (str);
r = (__builtin_memcmp (p, str, sizeof(str)));
printf(" 13:%d", !r);
printf(" 15:%d", !r);
__builtin_free(p);
p = __builtin_malloc (100);

View File

@ -1,4 +1,4 @@
BOUNDS OFF:
1:1 2:1 3:1 4:1 5:1 6:1 7:1 8:1 9:1 10:1 11:1 12:1 13:1
1:1 2:1 3:1 4:1 5:1 6:1 7:1 8:1 9:1 10:1 11:1 12:1 13:1 14:1 15:1
BOUNDS ON:
1:1 2:1 3:1 4:1 5:1 6:1 7:1 8:1 9:1 10:1 11:1 12:1 13:1
1:1 2:1 3:1 4:1 5:1 6:1 7:1 8:1 9:1 10:1 11:1 12:1 13:1 14:1 15:1