From b2c20e6c16278fe556ce4c4ff7d3b146b3a8f009 Mon Sep 17 00:00:00 2001 From: jvoisin Date: Mon, 11 Sep 2023 20:23:12 +0200 Subject: Factorize overlap checks into a macro --- include/fortify-headers.h | 9 +++++++++ include/string.h | 25 +++++-------------------- 2 files changed, 14 insertions(+), 20 deletions(-) (limited to 'include') diff --git a/include/fortify-headers.h b/include/fortify-headers.h index 5be4271..3eaed7c 100644 --- a/include/fortify-headers.h +++ b/include/fortify-headers.h @@ -123,6 +123,15 @@ #endif /* __has_attribute */ +//TODO(jvoisin) Add a check for overflows +/* check if pointers are overlapping but not if dst == src, + * since gcc seems to like to generate code that relies on dst == src */ +#define __fh_overlap(a, b, l) \ + ( \ + ((a) < (b) && (b) < (a) + (size_t)(l)) \ + || ((b) < (a) && (a) < (b) + (size_t)(l)) \ + ) + /* * We're not making use of C23's since: * - there is no elegant way to make it ignore the results. diff --git a/include/string.h b/include/string.h index 342bde0..0a9cd07 100644 --- a/include/string.h +++ b/include/string.h @@ -49,10 +49,7 @@ _FORTIFY_FN(memcpy) void *memcpy(void * _FORTIFY_POS0 __od, char *__d = (char *)__od; const char *__s = (const char *)__os; - /* trap if pointers are overlapping but not if dst == src. - * gcc seems to like to generate code that relies on dst == src */ - if ((__d < __s && __d + __n > __s) || - (__s < __d && __s + __n > __d)) + if __fh_overlap(__d, __s, __n) __builtin_trap(); if (__n > __bd || __n > __bs) __builtin_trap(); @@ -131,10 +128,7 @@ _FORTIFY_FN(stpcpy) char *stpcpy(char * _FORTIFY_POS0 __d, const char *__s) { size_t __n = strlen(__s) + 1; - /* trap if pointers are overlapping but not if dst == src. - * gcc seems to like to generate code that relies on dst == src */ - if ((__d < __s && __d + __n > __s) || - (__s < __d && __s + __n > __d)) + if (__fh_overlap(__d, __s, __n)) __builtin_trap(); size_t __b = __bos(__d, 0); @@ -150,10 +144,7 @@ __diagnose_as_builtin(__builtin_stpncpy, 1, 2, 3) _FORTIFY_FN(stpncpy) char *stpncpy(char * _FORTIFY_POS0 __d, const char *__s, size_t __n) { - /* trap if pointers are overlapping but not if dst == src. - * gcc seems to like to generate code that relies on dst == src */ - if ((__d < __s && __d + __n > __s) || - (__s < __d && __s + __n > __d)) + if (__fh_overlap(__d, __s, __n)) __builtin_trap(); size_t __b = __bos(__d, 0); @@ -182,10 +173,7 @@ _FORTIFY_FN(strcpy) char *strcpy(char * _FORTIFY_POS0 __d, const char *__s) { size_t __n = strlen(__s) + 1; - /* trap if pointers are overlapping but not if dst == src. - * gcc seems to like to generate code that relies on dst == src */ - if ((__d < __s && __d + __n > __s) || - (__s < __d && __s + __n > __d)) + if (__fh_overlap(__d, __s, __n)) __builtin_trap(); size_t __b = __bos(__d, 0); @@ -219,10 +207,7 @@ __diagnose_as_builtin(__builtin_strncpy, 1, 2, 3) _FORTIFY_FN(strncpy) char *strncpy(char * _FORTIFY_POS0 __d, const char *__s, size_t __n) { - /* trap if pointers are overlapping but not if dst == src. - * gcc seems to like to generate code that relies on dst == src */ - if ((__d < __s && __d + __n > __s) || - (__s < __d && __s + __n > __d)) + if (__fh_overlap(__d, __s, __n)) __builtin_trap(); size_t __b = __bos(__d, 0); -- cgit v1.3