forked from OSchip/llvm-project
[compiler-rt] Add common interceptor for wcrtomb.
Summary: Currently there is a libc++ test failing under MSAN because wcrtomb is not intercepted. This patch adds an interceptor for it. Reviewers: samsonov, eugenis Subscribers: tberghammer, danalbert, srhines, llvm-commits Differential Revision: http://reviews.llvm.org/D12311 llvm-svn: 245994
This commit is contained in:
parent
54ed7e18f2
commit
30130f2070
|
@ -1952,6 +1952,16 @@ TEST(MemorySanitizer, wcsnrtombs) {
|
|||
EXPECT_POISONED(buff[2]);
|
||||
}
|
||||
|
||||
TEST(MemorySanitizer, wcrtomb) {
|
||||
wchar_t x = L'a';
|
||||
char buff[10];
|
||||
mbstate_t mbs;
|
||||
memset(&mbs, 0, sizeof(mbs));
|
||||
size_t res = wcrtomb(buff, x, &mbs);
|
||||
EXPECT_EQ(res, (size_t)1);
|
||||
EXPECT_EQ(buff[0], 'a');
|
||||
}
|
||||
|
||||
TEST(MemorySanitizer, wmemset) {
|
||||
wchar_t x[25];
|
||||
break_optimization(x);
|
||||
|
|
|
@ -2717,7 +2717,7 @@ INTERCEPTOR(SIZE_T, wcsnrtombs, char *dest, const wchar_t **src, SIZE_T nms,
|
|||
// its metadata. See
|
||||
// https://code.google.com/p/address-sanitizer/issues/detail?id=321.
|
||||
SIZE_T res = REAL(wcsnrtombs)(dest, src, nms, len, ps);
|
||||
if (res != (SIZE_T) - 1 && dest && src) {
|
||||
if (res != ((SIZE_T)-1) && dest && src) {
|
||||
SIZE_T write_cnt = res + !*src;
|
||||
COMMON_INTERCEPTOR_WRITE_RANGE(ctx, dest, write_cnt);
|
||||
}
|
||||
|
@ -2729,6 +2729,28 @@ INTERCEPTOR(SIZE_T, wcsnrtombs, char *dest, const wchar_t **src, SIZE_T nms,
|
|||
#define INIT_WCSNRTOMBS
|
||||
#endif
|
||||
|
||||
|
||||
#if SANITIZER_INTERCEPT_WCRTOMB
|
||||
INTERCEPTOR(SIZE_T, wcrtomb, char *dest, wchar_t src, void *ps) {
|
||||
void *ctx;
|
||||
COMMON_INTERCEPTOR_ENTER(ctx, wcrtomb, dest, src, ps);
|
||||
if (ps) COMMON_INTERCEPTOR_READ_RANGE(ctx, ps, mbstate_t_sz);
|
||||
// FIXME: under ASan the call below may write to freed memory and corrupt
|
||||
// its metadata. See
|
||||
// https://code.google.com/p/address-sanitizer/issues/detail?id=321.
|
||||
SIZE_T res = REAL(wcrtomb)(dest, src, ps);
|
||||
if (res != ((SIZE_T)-1) && dest) {
|
||||
SIZE_T write_cnt = res;
|
||||
COMMON_INTERCEPTOR_WRITE_RANGE(ctx, dest, write_cnt);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
#define INIT_WCRTOMB COMMON_INTERCEPT_FUNCTION(wcrtomb);
|
||||
#else
|
||||
#define INIT_WCRTOMB
|
||||
#endif
|
||||
|
||||
#if SANITIZER_INTERCEPT_TCGETATTR
|
||||
INTERCEPTOR(int, tcgetattr, int fd, void *termios_p) {
|
||||
void *ctx;
|
||||
|
@ -5160,6 +5182,7 @@ static void InitializeCommonInterceptors() {
|
|||
INIT_MBSNRTOWCS;
|
||||
INIT_WCSTOMBS;
|
||||
INIT_WCSNRTOMBS;
|
||||
INIT_WCRTOMB;
|
||||
INIT_TCGETATTR;
|
||||
INIT_REALPATH;
|
||||
INIT_CANONICALIZE_FILE_NAME;
|
||||
|
|
|
@ -143,6 +143,8 @@
|
|||
#define SANITIZER_INTERCEPT_WCSTOMBS SI_NOT_WINDOWS
|
||||
#define SANITIZER_INTERCEPT_WCSNRTOMBS \
|
||||
SI_FREEBSD || SI_MAC || SI_LINUX_NOT_ANDROID
|
||||
#define SANITIZER_INTERCEPT_WCRTOMB \
|
||||
SI_FREEBSD || SI_MAC || SI_LINUX_NOT_ANDROID
|
||||
#define SANITIZER_INTERCEPT_TCGETATTR SI_LINUX_NOT_ANDROID
|
||||
#define SANITIZER_INTERCEPT_REALPATH SI_NOT_WINDOWS
|
||||
#define SANITIZER_INTERCEPT_CANONICALIZE_FILE_NAME SI_LINUX_NOT_ANDROID
|
||||
|
|
Loading…
Reference in New Issue