BLI: deduplicate address sanitizer code
Reviewers: brecht, campbellbarton Differential Revision: https://developer.blender.org/D7731
This commit is contained in:
parent
ea84c12a2b
commit
461fee5328
|
@ -0,0 +1,45 @@
|
|||
/*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation; either version 2
|
||||
* of the License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __BLI_ADDRESS_SANITIZER_H__
|
||||
#define __BLI_ADDRESS_SANITIZER_H__
|
||||
|
||||
/* Clang defines this. */
|
||||
#ifndef __has_feature
|
||||
# define __has_feature(x) 0
|
||||
#endif
|
||||
|
||||
#if defined(__SANITIZE_ADDRESS__) || __has_feature(address_sanitizer)
|
||||
# include "sanitizer/asan_interface.h"
|
||||
#else
|
||||
/* Ensure return value is used. Just using UNUSED_VARS results in a warning. */
|
||||
# define ASAN_POISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
# define ASAN_UNPOISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Mark a region of memory as "freed". When using address sanitizer, accessing the given memory
|
||||
* region will cause an use-after-poison error. This can be used to find errors when dealing with
|
||||
* uninitialized memory in custom containers.
|
||||
*/
|
||||
#define BLI_asan_poison(addr, size) ASAN_POISON_MEMORY_REGION(addr, size)
|
||||
|
||||
/**
|
||||
* Mark a region of memory as usable again.
|
||||
*/
|
||||
#define BLI_asan_unpoison(addr, size) ASAN_UNPOISON_MEMORY_REGION(addr, size)
|
||||
|
||||
#endif /* __BLI_ADDRESS_SANITIZER_H__ */
|
|
@ -138,7 +138,7 @@ set(SRC
|
|||
intern/list_sort_impl.h
|
||||
|
||||
|
||||
|
||||
BLI_asan.h
|
||||
BLI_alloca.h
|
||||
BLI_allocator.hh
|
||||
BLI_args.h
|
||||
|
|
|
@ -34,6 +34,7 @@
|
|||
|
||||
#include "MEM_guardedalloc.h"
|
||||
|
||||
#include "BLI_asan.h"
|
||||
#include "BLI_memarena.h"
|
||||
#include "BLI_strict_flags.h"
|
||||
#include "BLI_utildefines.h"
|
||||
|
@ -46,18 +47,6 @@
|
|||
# define VALGRIND_MEMPOOL_ALLOC(pool, addr, size) UNUSED_VARS(pool, addr, size)
|
||||
#endif
|
||||
|
||||
/* Clang defines this. */
|
||||
#ifndef __has_feature
|
||||
# define __has_feature(x) 0
|
||||
#endif
|
||||
#if defined(__SANITIZE_ADDRESS__) || __has_feature(address_sanitizer)
|
||||
# include "sanitizer/asan_interface.h"
|
||||
#else
|
||||
/* Ensure return value is used. */
|
||||
# define ASAN_POISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
# define ASAN_UNPOISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
#endif
|
||||
|
||||
struct MemBuf {
|
||||
struct MemBuf *next;
|
||||
uchar data[0];
|
||||
|
@ -80,7 +69,7 @@ static void memarena_buf_free_all(struct MemBuf *mb)
|
|||
struct MemBuf *mb_next = mb->next;
|
||||
|
||||
/* Unpoison memory because MEM_freeN might overwrite it. */
|
||||
ASAN_UNPOISON_MEMORY_REGION(mb, (uint)MEM_allocN_len(mb));
|
||||
BLI_asan_unpoison(mb, (uint)MEM_allocN_len(mb));
|
||||
|
||||
MEM_freeN(mb);
|
||||
mb = mb_next;
|
||||
|
@ -160,7 +149,7 @@ void *BLI_memarena_alloc(MemArena *ma, size_t size)
|
|||
mb->next = ma->bufs;
|
||||
ma->bufs = mb;
|
||||
|
||||
ASAN_POISON_MEMORY_REGION(ma->curbuf, ma->cursize);
|
||||
BLI_asan_poison(ma->curbuf, ma->cursize);
|
||||
|
||||
memarena_curbuf_align(ma);
|
||||
}
|
||||
|
@ -171,7 +160,7 @@ void *BLI_memarena_alloc(MemArena *ma, size_t size)
|
|||
|
||||
VALGRIND_MEMPOOL_ALLOC(ma, ptr, size);
|
||||
|
||||
ASAN_UNPOISON_MEMORY_REGION(ptr, size);
|
||||
BLI_asan_unpoison(ptr, size);
|
||||
|
||||
return ptr;
|
||||
}
|
||||
|
@ -215,7 +204,7 @@ void BLI_memarena_clear(MemArena *ma)
|
|||
if (ma->use_calloc) {
|
||||
memset(ma->curbuf, 0, curbuf_used);
|
||||
}
|
||||
ASAN_POISON_MEMORY_REGION(ma->curbuf, ma->cursize);
|
||||
BLI_asan_poison(ma->curbuf, ma->cursize);
|
||||
}
|
||||
|
||||
VALGRIND_DESTROY_MEMPOOL(ma);
|
||||
|
|
|
@ -40,6 +40,7 @@
|
|||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "BLI_asan.h"
|
||||
#include "BLI_utildefines.h"
|
||||
|
||||
#include "BLI_memiter.h" /* own include */
|
||||
|
@ -50,18 +51,6 @@
|
|||
|
||||
/* TODO: Valgrind. */
|
||||
|
||||
/* Clang defines this. */
|
||||
#ifndef __has_feature
|
||||
# define __has_feature(x) 0
|
||||
#endif
|
||||
#if defined(__SANITIZE_ADDRESS__) || __has_feature(address_sanitizer)
|
||||
# include "sanitizer/asan_interface.h"
|
||||
#else
|
||||
/* Ensure return value is used. */
|
||||
# define ASAN_POISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
# define ASAN_UNPOISON_MEMORY_REGION(addr, size) (void)(0 && ((size) != 0 && (addr) != NULL))
|
||||
#endif
|
||||
|
||||
typedef uintptr_t data_t;
|
||||
typedef intptr_t offset_t;
|
||||
|
||||
|
@ -114,7 +103,7 @@ static void memiter_set_rewind_offset(BLI_memiter *mi)
|
|||
{
|
||||
BLI_memiter_elem *elem = (BLI_memiter_elem *)mi->data_curr;
|
||||
|
||||
ASAN_UNPOISON_MEMORY_REGION(elem, sizeof(BLI_memiter_elem));
|
||||
BLI_asan_unpoison(elem, sizeof(BLI_memiter_elem));
|
||||
|
||||
elem->size = (offset_t)(((data_t *)mi->tail) - mi->data_curr);
|
||||
BLI_assert(elem->size < 0);
|
||||
|
@ -197,14 +186,14 @@ void *BLI_memiter_alloc(BLI_memiter *mi, uint elem_size)
|
|||
mi->data_last = chunk->data + (chunk_size - 1);
|
||||
data_curr_next = mi->data_curr + (1 + data_offset);
|
||||
|
||||
ASAN_POISON_MEMORY_REGION(chunk->data, chunk_size * sizeof(data_t));
|
||||
BLI_asan_poison(chunk->data, chunk_size * sizeof(data_t));
|
||||
}
|
||||
|
||||
BLI_assert(data_curr_next <= mi->data_last);
|
||||
|
||||
BLI_memiter_elem *elem = (BLI_memiter_elem *)mi->data_curr;
|
||||
|
||||
ASAN_UNPOISON_MEMORY_REGION(elem, sizeof(BLI_memiter_elem) + elem_size);
|
||||
BLI_asan_unpoison(elem, sizeof(BLI_memiter_elem) + elem_size);
|
||||
|
||||
elem->size = (offset_t)elem_size;
|
||||
mi->data_curr = data_curr_next;
|
||||
|
@ -242,7 +231,7 @@ static void memiter_free_data(BLI_memiter *mi)
|
|||
BLI_memiter_chunk *chunk_next = chunk->next;
|
||||
|
||||
/* Unpoison memory because MEM_freeN might overwrite it. */
|
||||
ASAN_UNPOISON_MEMORY_REGION(chunk, MEM_allocN_len(chunk));
|
||||
BLI_asan_unpoison(chunk, MEM_allocN_len(chunk));
|
||||
|
||||
MEM_freeN(chunk);
|
||||
chunk = chunk_next;
|
||||
|
|
Loading…
Reference in New Issue