Merge branch 'dev'
This commit is contained in:
commit
46c0af68bd
24
ChangeLog
24
ChangeLog
@ -5,6 +5,30 @@ found in the git revision history:
|
|||||||
|
|
||||||
https://github.com/jemalloc/jemalloc
|
https://github.com/jemalloc/jemalloc
|
||||||
|
|
||||||
|
* 3.6.0 (March 31, 2014)
|
||||||
|
|
||||||
|
This version contains a critical bug fix for a regression present in 3.5.0 and
|
||||||
|
3.5.1.
|
||||||
|
|
||||||
|
Bug fixes:
|
||||||
|
- Fix a regression in arena_chunk_alloc() that caused crashes during
|
||||||
|
small/large allocation if chunk allocation failed. In the absence of this
|
||||||
|
bug, chunk allocation failure would result in allocation failure, e.g. NULL
|
||||||
|
return from malloc(). This regression was introduced in 3.5.0.
|
||||||
|
- Fix backtracing for gcc intrinsics-based backtracing by specifying
|
||||||
|
-fno-omit-frame-pointer to gcc. Note that the application (and all the
|
||||||
|
libraries it links to) must also be compiled with this option for
|
||||||
|
backtracing to be reliable.
|
||||||
|
- Use dss allocation precedence for huge allocations as well as small/large
|
||||||
|
allocations.
|
||||||
|
- Fix test assertion failure message formatting. This bug did not manifect on
|
||||||
|
x86_64 systems because of implementation subtleties in va_list.
|
||||||
|
- Fix inconsequential test failures for hash and SFMT code.
|
||||||
|
|
||||||
|
New features:
|
||||||
|
- Support heap profiling on FreeBSD. This feature depends on the proc
|
||||||
|
filesystem being mounted during heap profile dumping.
|
||||||
|
|
||||||
* 3.5.1 (February 25, 2014)
|
* 3.5.1 (February 25, 2014)
|
||||||
|
|
||||||
This version primarily addresses minor bugs in test code.
|
This version primarily addresses minor bugs in test code.
|
||||||
|
@ -141,7 +141,7 @@ TESTS_INTEGRATION := $(srcroot)test/integration/aligned_alloc.c \
|
|||||||
$(srcroot)test/integration/xallocx.c
|
$(srcroot)test/integration/xallocx.c
|
||||||
ifeq ($(enable_experimental), 1)
|
ifeq ($(enable_experimental), 1)
|
||||||
TESTS_INTEGRATION += $(srcroot)test/integration/allocm.c \
|
TESTS_INTEGRATION += $(srcroot)test/integration/allocm.c \
|
||||||
$(srcroot)test/integration/ALLOCM_ARENA.c \
|
$(srcroot)test/integration/MALLOCX_ARENA.c \
|
||||||
$(srcroot)test/integration/rallocm.c
|
$(srcroot)test/integration/rallocm.c
|
||||||
endif
|
endif
|
||||||
TESTS_STRESS :=
|
TESTS_STRESS :=
|
||||||
|
28
bin/pprof
28
bin/pprof
@ -4197,8 +4197,12 @@ sub FindLibrary {
|
|||||||
# For libc libraries, the copy in /usr/lib/debug contains debugging symbols
|
# For libc libraries, the copy in /usr/lib/debug contains debugging symbols
|
||||||
sub DebuggingLibrary {
|
sub DebuggingLibrary {
|
||||||
my $file = shift;
|
my $file = shift;
|
||||||
if ($file =~ m|^/| && -f "/usr/lib/debug$file") {
|
if ($file =~ m|^/|) {
|
||||||
|
if (-f "/usr/lib/debug$file") {
|
||||||
return "/usr/lib/debug$file";
|
return "/usr/lib/debug$file";
|
||||||
|
} elsif (-f "/usr/lib/debug$file.debug") {
|
||||||
|
return "/usr/lib/debug$file.debug";
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return undef;
|
return undef;
|
||||||
}
|
}
|
||||||
@ -4360,6 +4364,19 @@ sub ParseLibraries {
|
|||||||
$finish = HexExtend($2);
|
$finish = HexExtend($2);
|
||||||
$offset = $zero_offset;
|
$offset = $zero_offset;
|
||||||
$lib = $3;
|
$lib = $3;
|
||||||
|
}
|
||||||
|
# FreeBSD 10.0 virtual memory map /proc/curproc/map as defined in
|
||||||
|
# function procfs_doprocmap (sys/fs/procfs/procfs_map.c)
|
||||||
|
#
|
||||||
|
# Example:
|
||||||
|
# 0x800600000 0x80061a000 26 0 0xfffff800035a0000 r-x 75 33 0x1004 COW NC vnode /libexec/ld-elf.s
|
||||||
|
# o.1 NCH -1
|
||||||
|
elsif ($l =~ /^(0x$h)\s(0x$h)\s\d+\s\d+\s0x$h\sr-x\s\d+\s\d+\s0x\d+\s(COW|NCO)\s(NC|NNC)\svnode\s(\S+\.so(\.\d+)*)/) {
|
||||||
|
$start = HexExtend($1);
|
||||||
|
$finish = HexExtend($2);
|
||||||
|
$offset = $zero_offset;
|
||||||
|
$lib = FindLibrary($5);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
next;
|
next;
|
||||||
}
|
}
|
||||||
@ -4382,6 +4399,7 @@ sub ParseLibraries {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if($main::opt_debug) { printf STDERR "$start:$finish ($offset) $lib\n"; }
|
||||||
push(@{$result}, [$lib, $start, $finish, $offset]);
|
push(@{$result}, [$lib, $start, $finish, $offset]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -4589,6 +4607,12 @@ sub ExtractSymbols {
|
|||||||
my $finish = $lib->[2];
|
my $finish = $lib->[2];
|
||||||
my $offset = $lib->[3];
|
my $offset = $lib->[3];
|
||||||
|
|
||||||
|
# Use debug library if it exists
|
||||||
|
my $debug_libname = DebuggingLibrary($libname);
|
||||||
|
if ($debug_libname) {
|
||||||
|
$libname = $debug_libname;
|
||||||
|
}
|
||||||
|
|
||||||
# Get list of pcs that belong in this library.
|
# Get list of pcs that belong in this library.
|
||||||
my $contained = [];
|
my $contained = [];
|
||||||
my ($start_pc_index, $finish_pc_index);
|
my ($start_pc_index, $finish_pc_index);
|
||||||
@ -5019,7 +5043,7 @@ sub GetProcedureBoundariesViaNm {
|
|||||||
|
|
||||||
# Tag this routine with the starting address in case the image
|
# Tag this routine with the starting address in case the image
|
||||||
# has multiple occurrences of this routine. We use a syntax
|
# has multiple occurrences of this routine. We use a syntax
|
||||||
# that resembles template paramters that are automatically
|
# that resembles template parameters that are automatically
|
||||||
# stripped out by ShortFunctionName()
|
# stripped out by ShortFunctionName()
|
||||||
$this_routine .= "<$start_val>";
|
$this_routine .= "<$start_val>";
|
||||||
|
|
||||||
|
22
configure.ac
22
configure.ac
@ -150,6 +150,11 @@ if test "x$EXTRA_CFLAGS" != "x" ; then
|
|||||||
fi
|
fi
|
||||||
AC_PROG_CPP
|
AC_PROG_CPP
|
||||||
|
|
||||||
|
AC_C_BIGENDIAN([ac_cv_big_endian=1], [ac_cv_big_endian=0])
|
||||||
|
if test "x${ac_cv_big_endian}" = "x1" ; then
|
||||||
|
AC_DEFINE_UNQUOTED([JEMALLOC_BIG_ENDIAN], [ ])
|
||||||
|
fi
|
||||||
|
|
||||||
AC_CHECK_SIZEOF([void *])
|
AC_CHECK_SIZEOF([void *])
|
||||||
if test "x${ac_cv_sizeof_void_p}" = "x8" ; then
|
if test "x${ac_cv_sizeof_void_p}" = "x8" ; then
|
||||||
LG_SIZEOF_PTR=3
|
LG_SIZEOF_PTR=3
|
||||||
@ -742,22 +747,6 @@ if test "x$backtrace_method" = "x" -a "x$enable_prof_libgcc" = "x1" \
|
|||||||
-a "x$GCC" = "xyes" ; then
|
-a "x$GCC" = "xyes" ; then
|
||||||
AC_CHECK_HEADERS([unwind.h], , [enable_prof_libgcc="0"])
|
AC_CHECK_HEADERS([unwind.h], , [enable_prof_libgcc="0"])
|
||||||
AC_CHECK_LIB([gcc], [_Unwind_Backtrace], [LIBS="$LIBS -lgcc"], [enable_prof_libgcc="0"])
|
AC_CHECK_LIB([gcc], [_Unwind_Backtrace], [LIBS="$LIBS -lgcc"], [enable_prof_libgcc="0"])
|
||||||
dnl The following is conservative, in that it only has entries for CPUs on
|
|
||||||
dnl which jemalloc has been tested.
|
|
||||||
AC_MSG_CHECKING([libgcc-based backtracing reliability on ${host_cpu}])
|
|
||||||
case "${host_cpu}" in
|
|
||||||
i[[3456]]86)
|
|
||||||
AC_MSG_RESULT([unreliable])
|
|
||||||
enable_prof_libgcc="0";
|
|
||||||
;;
|
|
||||||
x86_64)
|
|
||||||
AC_MSG_RESULT([reliable])
|
|
||||||
;;
|
|
||||||
*)
|
|
||||||
AC_MSG_RESULT([unreliable])
|
|
||||||
enable_prof_libgcc="0";
|
|
||||||
;;
|
|
||||||
esac
|
|
||||||
if test "x${enable_prof_libgcc}" = "x1" ; then
|
if test "x${enable_prof_libgcc}" = "x1" ; then
|
||||||
backtrace_method="libgcc"
|
backtrace_method="libgcc"
|
||||||
AC_DEFINE([JEMALLOC_PROF_LIBGCC], [ ])
|
AC_DEFINE([JEMALLOC_PROF_LIBGCC], [ ])
|
||||||
@ -779,6 +768,7 @@ fi
|
|||||||
)
|
)
|
||||||
if test "x$backtrace_method" = "x" -a "x$enable_prof_gcc" = "x1" \
|
if test "x$backtrace_method" = "x" -a "x$enable_prof_gcc" = "x1" \
|
||||||
-a "x$GCC" = "xyes" ; then
|
-a "x$GCC" = "xyes" ; then
|
||||||
|
JE_CFLAGS_APPEND([-fno-omit-frame-pointer])
|
||||||
backtrace_method="gcc intrinsics"
|
backtrace_method="gcc intrinsics"
|
||||||
AC_DEFINE([JEMALLOC_PROF_GCC], [ ])
|
AC_DEFINE([JEMALLOC_PROF_GCC], [ ])
|
||||||
else
|
else
|
||||||
|
@ -1439,8 +1439,12 @@ malloc_conf = "xmalloc:true";]]></programlisting>
|
|||||||
<listitem><para>Set the precedence of dss allocation as related to mmap
|
<listitem><para>Set the precedence of dss allocation as related to mmap
|
||||||
allocation for arena <i>, or for all arenas if <i> equals
|
allocation for arena <i>, or for all arenas if <i> equals
|
||||||
<link
|
<link
|
||||||
linkend="arenas.narenas"><mallctl>arenas.narenas</mallctl></link>. See
|
linkend="arenas.narenas"><mallctl>arenas.narenas</mallctl></link>. Note
|
||||||
<link linkend="opt.dss"><mallctl>opt.dss</mallctl></link> for supported
|
that even during huge allocation this setting is read from the arena
|
||||||
|
that would be chosen for small or large allocation so that applications
|
||||||
|
can depend on consistent dss versus mmap allocation regardless of
|
||||||
|
allocation size. See <link
|
||||||
|
linkend="opt.dss"><mallctl>opt.dss</mallctl></link> for supported
|
||||||
settings.
|
settings.
|
||||||
</para></listitem>
|
</para></listitem>
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
@ -320,7 +320,7 @@ hash_x64_128(const void *key, const int len, const uint32_t seed,
|
|||||||
JEMALLOC_INLINE void
|
JEMALLOC_INLINE void
|
||||||
hash(const void *key, size_t len, const uint32_t seed, size_t r_hash[2])
|
hash(const void *key, size_t len, const uint32_t seed, size_t r_hash[2])
|
||||||
{
|
{
|
||||||
#if (LG_SIZEOF_PTR == 3)
|
#if (LG_SIZEOF_PTR == 3 && !defined(JEMALLOC_BIG_ENDIAN))
|
||||||
hash_x64_128(key, len, seed, (uint64_t *)r_hash);
|
hash_x64_128(key, len, seed, (uint64_t *)r_hash);
|
||||||
#else
|
#else
|
||||||
uint64_t hashes[2];
|
uint64_t hashes[2];
|
||||||
|
@ -17,18 +17,20 @@ extern size_t huge_allocated;
|
|||||||
/* Protects chunk-related data structures. */
|
/* Protects chunk-related data structures. */
|
||||||
extern malloc_mutex_t huge_mtx;
|
extern malloc_mutex_t huge_mtx;
|
||||||
|
|
||||||
void *huge_malloc(size_t size, bool zero);
|
void *huge_malloc(size_t size, bool zero, dss_prec_t dss_prec);
|
||||||
void *huge_palloc(size_t size, size_t alignment, bool zero);
|
void *huge_palloc(size_t size, size_t alignment, bool zero,
|
||||||
|
dss_prec_t dss_prec);
|
||||||
bool huge_ralloc_no_move(void *ptr, size_t oldsize, size_t size,
|
bool huge_ralloc_no_move(void *ptr, size_t oldsize, size_t size,
|
||||||
size_t extra);
|
size_t extra);
|
||||||
void *huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
|
void *huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
|
||||||
size_t alignment, bool zero, bool try_tcache_dalloc);
|
size_t alignment, bool zero, bool try_tcache_dalloc, dss_prec_t dss_prec);
|
||||||
#ifdef JEMALLOC_JET
|
#ifdef JEMALLOC_JET
|
||||||
typedef void (huge_dalloc_junk_t)(void *, size_t);
|
typedef void (huge_dalloc_junk_t)(void *, size_t);
|
||||||
extern huge_dalloc_junk_t *huge_dalloc_junk;
|
extern huge_dalloc_junk_t *huge_dalloc_junk;
|
||||||
#endif
|
#endif
|
||||||
void huge_dalloc(void *ptr, bool unmap);
|
void huge_dalloc(void *ptr, bool unmap);
|
||||||
size_t huge_salloc(const void *ptr);
|
size_t huge_salloc(const void *ptr);
|
||||||
|
dss_prec_t huge_dss_prec_get(arena_t *arena);
|
||||||
prof_ctx_t *huge_prof_ctx_get(const void *ptr);
|
prof_ctx_t *huge_prof_ctx_get(const void *ptr);
|
||||||
void huge_prof_ctx_set(const void *ptr, prof_ctx_t *ctx);
|
void huge_prof_ctx_set(const void *ptr, prof_ctx_t *ctx);
|
||||||
bool huge_boot(void);
|
bool huge_boot(void);
|
||||||
|
@ -770,7 +770,7 @@ imalloct(size_t size, bool try_tcache, arena_t *arena)
|
|||||||
if (size <= arena_maxclass)
|
if (size <= arena_maxclass)
|
||||||
return (arena_malloc(arena, size, false, try_tcache));
|
return (arena_malloc(arena, size, false, try_tcache));
|
||||||
else
|
else
|
||||||
return (huge_malloc(size, false));
|
return (huge_malloc(size, false, huge_dss_prec_get(arena)));
|
||||||
}
|
}
|
||||||
|
|
||||||
JEMALLOC_ALWAYS_INLINE void *
|
JEMALLOC_ALWAYS_INLINE void *
|
||||||
@ -787,7 +787,7 @@ icalloct(size_t size, bool try_tcache, arena_t *arena)
|
|||||||
if (size <= arena_maxclass)
|
if (size <= arena_maxclass)
|
||||||
return (arena_malloc(arena, size, true, try_tcache));
|
return (arena_malloc(arena, size, true, try_tcache));
|
||||||
else
|
else
|
||||||
return (huge_malloc(size, true));
|
return (huge_malloc(size, true, huge_dss_prec_get(arena)));
|
||||||
}
|
}
|
||||||
|
|
||||||
JEMALLOC_ALWAYS_INLINE void *
|
JEMALLOC_ALWAYS_INLINE void *
|
||||||
@ -813,9 +813,9 @@ ipalloct(size_t usize, size_t alignment, bool zero, bool try_tcache,
|
|||||||
ret = arena_palloc(choose_arena(arena), usize,
|
ret = arena_palloc(choose_arena(arena), usize,
|
||||||
alignment, zero);
|
alignment, zero);
|
||||||
} else if (alignment <= chunksize)
|
} else if (alignment <= chunksize)
|
||||||
ret = huge_malloc(usize, zero);
|
ret = huge_malloc(usize, zero, huge_dss_prec_get(arena));
|
||||||
else
|
else
|
||||||
ret = huge_palloc(usize, alignment, zero);
|
ret = huge_palloc(usize, alignment, zero, huge_dss_prec_get(arena));
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(ALIGNMENT_ADDR2BASE(ret, alignment) == ret);
|
assert(ALIGNMENT_ADDR2BASE(ret, alignment) == ret);
|
||||||
@ -984,7 +984,7 @@ iralloct(void *ptr, size_t size, size_t extra, size_t alignment, bool zero,
|
|||||||
try_tcache_dalloc));
|
try_tcache_dalloc));
|
||||||
} else {
|
} else {
|
||||||
return (huge_ralloc(ptr, oldsize, size, extra,
|
return (huge_ralloc(ptr, oldsize, size, extra,
|
||||||
alignment, zero, try_tcache_dalloc));
|
alignment, zero, try_tcache_dalloc, huge_dss_prec_get(arena)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -190,6 +190,9 @@
|
|||||||
/* C99 restrict keyword supported. */
|
/* C99 restrict keyword supported. */
|
||||||
#undef JEMALLOC_HAS_RESTRICT
|
#undef JEMALLOC_HAS_RESTRICT
|
||||||
|
|
||||||
|
/* For use by hash code. */
|
||||||
|
#undef JEMALLOC_BIG_ENDIAN
|
||||||
|
|
||||||
/* sizeof(int) == 2^LG_SIZEOF_INT. */
|
/* sizeof(int) == 2^LG_SIZEOF_INT. */
|
||||||
#undef LG_SIZEOF_INT
|
#undef LG_SIZEOF_INT
|
||||||
|
|
||||||
|
@ -197,6 +197,7 @@ huge_allocated
|
|||||||
huge_boot
|
huge_boot
|
||||||
huge_dalloc
|
huge_dalloc
|
||||||
huge_dalloc_junk
|
huge_dalloc_junk
|
||||||
|
huge_dss_prec_get
|
||||||
huge_malloc
|
huge_malloc
|
||||||
huge_mtx
|
huge_mtx
|
||||||
huge_ndalloc
|
huge_ndalloc
|
||||||
|
@ -614,8 +614,11 @@ arena_chunk_alloc(arena_t *arena)
|
|||||||
|
|
||||||
if (arena->spare != NULL)
|
if (arena->spare != NULL)
|
||||||
chunk = arena_chunk_init_spare(arena);
|
chunk = arena_chunk_init_spare(arena);
|
||||||
else
|
else {
|
||||||
chunk = arena_chunk_init_hard(arena);
|
chunk = arena_chunk_init_hard(arena);
|
||||||
|
if (chunk == NULL)
|
||||||
|
return (NULL);
|
||||||
|
}
|
||||||
|
|
||||||
/* Insert the run into the runs_avail tree. */
|
/* Insert the run into the runs_avail tree. */
|
||||||
arena_avail_insert(arena, chunk, map_bias, chunk_npages-map_bias,
|
arena_avail_insert(arena, chunk, map_bias, chunk_npages-map_bias,
|
||||||
|
26
src/huge.c
26
src/huge.c
@ -16,14 +16,14 @@ malloc_mutex_t huge_mtx;
|
|||||||
static extent_tree_t huge;
|
static extent_tree_t huge;
|
||||||
|
|
||||||
void *
|
void *
|
||||||
huge_malloc(size_t size, bool zero)
|
huge_malloc(size_t size, bool zero, dss_prec_t dss_prec)
|
||||||
{
|
{
|
||||||
|
|
||||||
return (huge_palloc(size, chunksize, zero));
|
return (huge_palloc(size, chunksize, zero, dss_prec));
|
||||||
}
|
}
|
||||||
|
|
||||||
void *
|
void *
|
||||||
huge_palloc(size_t size, size_t alignment, bool zero)
|
huge_palloc(size_t size, size_t alignment, bool zero, dss_prec_t dss_prec)
|
||||||
{
|
{
|
||||||
void *ret;
|
void *ret;
|
||||||
size_t csize;
|
size_t csize;
|
||||||
@ -48,8 +48,7 @@ huge_palloc(size_t size, size_t alignment, bool zero)
|
|||||||
* it is possible to make correct junk/zero fill decisions below.
|
* it is possible to make correct junk/zero fill decisions below.
|
||||||
*/
|
*/
|
||||||
is_zeroed = zero;
|
is_zeroed = zero;
|
||||||
ret = chunk_alloc(csize, alignment, false, &is_zeroed,
|
ret = chunk_alloc(csize, alignment, false, &is_zeroed, dss_prec);
|
||||||
chunk_dss_prec_get());
|
|
||||||
if (ret == NULL) {
|
if (ret == NULL) {
|
||||||
base_node_dealloc(node);
|
base_node_dealloc(node);
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -98,7 +97,7 @@ huge_ralloc_no_move(void *ptr, size_t oldsize, size_t size, size_t extra)
|
|||||||
|
|
||||||
void *
|
void *
|
||||||
huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
|
huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
|
||||||
size_t alignment, bool zero, bool try_tcache_dalloc)
|
size_t alignment, bool zero, bool try_tcache_dalloc, dss_prec_t dss_prec)
|
||||||
{
|
{
|
||||||
void *ret;
|
void *ret;
|
||||||
size_t copysize;
|
size_t copysize;
|
||||||
@ -113,18 +112,18 @@ huge_ralloc(void *ptr, size_t oldsize, size_t size, size_t extra,
|
|||||||
* space and copying.
|
* space and copying.
|
||||||
*/
|
*/
|
||||||
if (alignment > chunksize)
|
if (alignment > chunksize)
|
||||||
ret = huge_palloc(size + extra, alignment, zero);
|
ret = huge_palloc(size + extra, alignment, zero, dss_prec);
|
||||||
else
|
else
|
||||||
ret = huge_malloc(size + extra, zero);
|
ret = huge_malloc(size + extra, zero, dss_prec);
|
||||||
|
|
||||||
if (ret == NULL) {
|
if (ret == NULL) {
|
||||||
if (extra == 0)
|
if (extra == 0)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
/* Try again, this time without extra. */
|
/* Try again, this time without extra. */
|
||||||
if (alignment > chunksize)
|
if (alignment > chunksize)
|
||||||
ret = huge_palloc(size, alignment, zero);
|
ret = huge_palloc(size, alignment, zero, dss_prec);
|
||||||
else
|
else
|
||||||
ret = huge_malloc(size, zero);
|
ret = huge_malloc(size, zero, dss_prec);
|
||||||
|
|
||||||
if (ret == NULL)
|
if (ret == NULL)
|
||||||
return (NULL);
|
return (NULL);
|
||||||
@ -264,6 +263,13 @@ huge_salloc(const void *ptr)
|
|||||||
return (ret);
|
return (ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
dss_prec_t
|
||||||
|
huge_dss_prec_get(arena_t *arena)
|
||||||
|
{
|
||||||
|
|
||||||
|
return (arena_dss_prec_get(choose_arena(arena)));
|
||||||
|
}
|
||||||
|
|
||||||
prof_ctx_t *
|
prof_ctx_t *
|
||||||
huge_prof_ctx_get(const void *ptr)
|
huge_prof_ctx_get(const void *ptr)
|
||||||
{
|
{
|
||||||
|
@ -2076,7 +2076,7 @@ a0alloc(size_t size, bool zero)
|
|||||||
if (size <= arena_maxclass)
|
if (size <= arena_maxclass)
|
||||||
return (arena_malloc(arenas[0], size, zero, false));
|
return (arena_malloc(arenas[0], size, zero, false));
|
||||||
else
|
else
|
||||||
return (huge_malloc(size, zero));
|
return (huge_malloc(size, zero, huge_dss_prec_get(arenas[0])));
|
||||||
}
|
}
|
||||||
|
|
||||||
void *
|
void *
|
||||||
|
@ -935,9 +935,12 @@ prof_dump_maps(bool propagate_err)
|
|||||||
char filename[PATH_MAX + 1];
|
char filename[PATH_MAX + 1];
|
||||||
|
|
||||||
cassert(config_prof);
|
cassert(config_prof);
|
||||||
|
#ifdef __FreeBSD__
|
||||||
|
malloc_snprintf(filename, sizeof(filename), "/proc/curproc/map");
|
||||||
|
#else
|
||||||
malloc_snprintf(filename, sizeof(filename), "/proc/%d/maps",
|
malloc_snprintf(filename, sizeof(filename), "/proc/%d/maps",
|
||||||
(int)getpid());
|
(int)getpid());
|
||||||
|
#endif
|
||||||
mfd = open(filename, O_RDONLY);
|
mfd = open(filename, O_RDONLY);
|
||||||
if (mfd != -1) {
|
if (mfd != -1) {
|
||||||
ssize_t nread;
|
ssize_t nread;
|
||||||
|
@ -61,7 +61,7 @@
|
|||||||
* @return output
|
* @return output
|
||||||
*/
|
*/
|
||||||
JEMALLOC_ALWAYS_INLINE
|
JEMALLOC_ALWAYS_INLINE
|
||||||
static vector unsigned int vec_recursion(vector unsigned int a,
|
vector unsigned int vec_recursion(vector unsigned int a,
|
||||||
vector unsigned int b,
|
vector unsigned int b,
|
||||||
vector unsigned int c,
|
vector unsigned int c,
|
||||||
vector unsigned int d) {
|
vector unsigned int d) {
|
||||||
|
@ -1,13 +1,19 @@
|
|||||||
|
#define ASSERT_BUFSIZE 256
|
||||||
|
|
||||||
#define assert_cmp(t, a, b, cmp, neg_cmp, pri, fmt...) do { \
|
#define assert_cmp(t, a, b, cmp, neg_cmp, pri, fmt...) do { \
|
||||||
t a_ = (a); \
|
t a_ = (a); \
|
||||||
t b_ = (b); \
|
t b_ = (b); \
|
||||||
if (!(a_ cmp b_)) { \
|
if (!(a_ cmp b_)) { \
|
||||||
p_test_fail( \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
"%s:%s:%d: Failed assertion: " \
|
"%s:%s:%d: Failed assertion: " \
|
||||||
"(%s) "#cmp" (%s) --> " \
|
"(%s) "#cmp" (%s) --> " \
|
||||||
"%"pri" "#neg_cmp" %"pri": ", \
|
"%"pri" "#neg_cmp" %"pri": ", \
|
||||||
__func__, __FILE__, __LINE__, \
|
__func__, __FILE__, __LINE__, \
|
||||||
#a, #b, a_, b_, fmt); \
|
#a, #b, a_, b_); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
@ -208,24 +214,32 @@
|
|||||||
bool a_ = (a); \
|
bool a_ = (a); \
|
||||||
bool b_ = (b); \
|
bool b_ = (b); \
|
||||||
if (!(a_ == b_)) { \
|
if (!(a_ == b_)) { \
|
||||||
p_test_fail( \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
"%s:%s:%d: Failed assertion: " \
|
"%s:%s:%d: Failed assertion: " \
|
||||||
"(%s) == (%s) --> %s != %s: ", \
|
"(%s) == (%s) --> %s != %s: ", \
|
||||||
__func__, __FILE__, __LINE__, \
|
__func__, __FILE__, __LINE__, \
|
||||||
#a, #b, a_ ? "true" : "false", \
|
#a, #b, a_ ? "true" : "false", \
|
||||||
b_ ? "true" : "false", fmt); \
|
b_ ? "true" : "false"); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
#define assert_b_ne(a, b, fmt...) do { \
|
#define assert_b_ne(a, b, fmt...) do { \
|
||||||
bool a_ = (a); \
|
bool a_ = (a); \
|
||||||
bool b_ = (b); \
|
bool b_ = (b); \
|
||||||
if (!(a_ != b_)) { \
|
if (!(a_ != b_)) { \
|
||||||
p_test_fail( \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
"%s:%s:%d: Failed assertion: " \
|
"%s:%s:%d: Failed assertion: " \
|
||||||
"(%s) != (%s) --> %s == %s: ", \
|
"(%s) != (%s) --> %s == %s: ", \
|
||||||
__func__, __FILE__, __LINE__, \
|
__func__, __FILE__, __LINE__, \
|
||||||
#a, #b, a_ ? "true" : "false", \
|
#a, #b, a_ ? "true" : "false", \
|
||||||
b_ ? "true" : "false", fmt); \
|
b_ ? "true" : "false"); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
#define assert_true(a, fmt...) assert_b_eq(a, true, fmt)
|
#define assert_true(a, fmt...) assert_b_eq(a, true, fmt)
|
||||||
@ -233,26 +247,39 @@
|
|||||||
|
|
||||||
#define assert_str_eq(a, b, fmt...) do { \
|
#define assert_str_eq(a, b, fmt...) do { \
|
||||||
if (strcmp((a), (b))) { \
|
if (strcmp((a), (b))) { \
|
||||||
p_test_fail( \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
"%s:%s:%d: Failed assertion: " \
|
"%s:%s:%d: Failed assertion: " \
|
||||||
"(%s) same as (%s) --> " \
|
"(%s) same as (%s) --> " \
|
||||||
"\"%s\" differs from \"%s\": ", \
|
"\"%s\" differs from \"%s\": ", \
|
||||||
__func__, __FILE__, __LINE__, #a, #b, a, b, fmt); \
|
__func__, __FILE__, __LINE__, #a, #b, a, b); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
#define assert_str_ne(a, b, fmt...) do { \
|
#define assert_str_ne(a, b, fmt...) do { \
|
||||||
if (!strcmp((a), (b))) { \
|
if (!strcmp((a), (b))) { \
|
||||||
p_test_fail( \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
"%s:%s:%d: Failed assertion: " \
|
"%s:%s:%d: Failed assertion: " \
|
||||||
"(%s) differs from (%s) --> " \
|
"(%s) differs from (%s) --> " \
|
||||||
"\"%s\" same as \"%s\": ", \
|
"\"%s\" same as \"%s\": ", \
|
||||||
__func__, __FILE__, __LINE__, #a, #b, a, b, fmt); \
|
__func__, __FILE__, __LINE__, #a, #b, a, b); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define assert_not_reached(fmt...) do { \
|
#define assert_not_reached(fmt...) do { \
|
||||||
p_test_fail("%s:%s:%d: Unreachable code reached: ", \
|
char prefix[ASSERT_BUFSIZE]; \
|
||||||
__func__, __FILE__, __LINE__, fmt); \
|
char message[ASSERT_BUFSIZE]; \
|
||||||
|
malloc_snprintf(prefix, sizeof(prefix), \
|
||||||
|
"%s:%s:%d: Unreachable code reached: ", \
|
||||||
|
__func__, __FILE__, __LINE__); \
|
||||||
|
malloc_snprintf(message, sizeof(message), fmt); \
|
||||||
|
p_test_fail(prefix, message); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -299,4 +326,4 @@ void test_fail(const char *format, ...) JEMALLOC_ATTR(format(printf, 1, 2));
|
|||||||
test_status_t p_test(test_t* t, ...);
|
test_status_t p_test(test_t* t, ...);
|
||||||
void p_test_init(const char *name);
|
void p_test_init(const char *name);
|
||||||
void p_test_fini(void);
|
void p_test_fini(void);
|
||||||
void p_test_fail(const char *format, ...);
|
void p_test_fail(const char *prefix, const char *message);
|
||||||
|
@ -8,7 +8,7 @@ thd_start(void *arg)
|
|||||||
unsigned thread_ind = (unsigned)(uintptr_t)arg;
|
unsigned thread_ind = (unsigned)(uintptr_t)arg;
|
||||||
unsigned arena_ind;
|
unsigned arena_ind;
|
||||||
void *p;
|
void *p;
|
||||||
size_t rsz, sz;
|
size_t sz;
|
||||||
|
|
||||||
sz = sizeof(arena_ind);
|
sz = sizeof(arena_ind);
|
||||||
assert_d_eq(mallctl("arenas.extend", &arena_ind, &sz, NULL, 0), 0,
|
assert_d_eq(mallctl("arenas.extend", &arena_ind, &sz, NULL, 0), 0,
|
||||||
@ -27,9 +27,9 @@ thd_start(void *arg)
|
|||||||
sizeof(const char *)), 0, "Error in mallctlbymib()");
|
sizeof(const char *)), 0, "Error in mallctlbymib()");
|
||||||
}
|
}
|
||||||
|
|
||||||
assert_d_eq(allocm(&p, &rsz, 1, ALLOCM_ARENA(arena_ind)),
|
p = mallocx(1, MALLOCX_ARENA(arena_ind));
|
||||||
ALLOCM_SUCCESS, "Unexpected allocm() error");
|
assert_ptr_not_null(p, "Unexpected mallocx() error");
|
||||||
dallocm(p, 0);
|
dallocx(p, 0);
|
||||||
|
|
||||||
return (NULL);
|
return (NULL);
|
||||||
}
|
}
|
@ -1,8 +1,7 @@
|
|||||||
#include "test/jemalloc_test.h"
|
#include "test/jemalloc_test.h"
|
||||||
|
|
||||||
#define CHUNK 0x400000
|
#define CHUNK 0x400000
|
||||||
/* #define MAXALIGN ((size_t)UINT64_C(0x80000000000)) */
|
#define MAXALIGN (((size_t)1) << 25)
|
||||||
#define MAXALIGN ((size_t)0x2000000LU)
|
|
||||||
#define NITER 4
|
#define NITER 4
|
||||||
|
|
||||||
TEST_BEGIN(test_basic)
|
TEST_BEGIN(test_basic)
|
||||||
|
@ -1,8 +1,7 @@
|
|||||||
#include "test/jemalloc_test.h"
|
#include "test/jemalloc_test.h"
|
||||||
|
|
||||||
#define CHUNK 0x400000
|
#define CHUNK 0x400000
|
||||||
/* #define MAXALIGN ((size_t)UINT64_C(0x80000000000)) */
|
#define MAXALIGN (((size_t)1) << 25)
|
||||||
#define MAXALIGN ((size_t)0x2000000LU)
|
|
||||||
#define NITER 4
|
#define NITER 4
|
||||||
|
|
||||||
TEST_BEGIN(test_basic)
|
TEST_BEGIN(test_basic)
|
||||||
|
@ -112,7 +112,7 @@ TEST_BEGIN(test_align)
|
|||||||
{
|
{
|
||||||
void *p, *q;
|
void *p, *q;
|
||||||
size_t align;
|
size_t align;
|
||||||
#define MAX_ALIGN (ZU(1) << 29)
|
#define MAX_ALIGN (ZU(1) << 25)
|
||||||
|
|
||||||
align = ZU(1);
|
align = ZU(1);
|
||||||
p = mallocx(1, MALLOCX_ALIGN(align));
|
p = mallocx(1, MALLOCX_ALIGN(align));
|
||||||
@ -137,7 +137,7 @@ TEST_BEGIN(test_lg_align_and_zero)
|
|||||||
{
|
{
|
||||||
void *p, *q;
|
void *p, *q;
|
||||||
size_t lg_align, sz;
|
size_t lg_align, sz;
|
||||||
#define MAX_LG_ALIGN 29
|
#define MAX_LG_ALIGN 25
|
||||||
#define MAX_VALIDATE (ZU(1) << 22)
|
#define MAX_VALIDATE (ZU(1) << 22)
|
||||||
|
|
||||||
lg_align = ZU(0);
|
lg_align = ZU(0);
|
||||||
|
@ -49,6 +49,9 @@
|
|||||||
#include "test/jemalloc_test.h"
|
#include "test/jemalloc_test.h"
|
||||||
#include "test/SFMT-params.h"
|
#include "test/SFMT-params.h"
|
||||||
|
|
||||||
|
#if defined(JEMALLOC_BIG_ENDIAN) && !defined(BIG_ENDIAN64)
|
||||||
|
#define BIG_ENDIAN64 1
|
||||||
|
#endif
|
||||||
#if defined(__BIG_ENDIAN__) && !defined(__amd64) && !defined(BIG_ENDIAN64)
|
#if defined(__BIG_ENDIAN__) && !defined(__amd64) && !defined(BIG_ENDIAN64)
|
||||||
#define BIG_ENDIAN64 1
|
#define BIG_ENDIAN64 1
|
||||||
#endif
|
#endif
|
||||||
|
@ -86,15 +86,9 @@ p_test(test_t* t, ...)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
p_test_fail(const char *format, ...)
|
p_test_fail(const char *prefix, const char *message)
|
||||||
{
|
{
|
||||||
va_list ap;
|
|
||||||
|
|
||||||
va_start(ap, format);
|
malloc_cprintf(NULL, NULL, "%s%s\n", prefix, message);
|
||||||
malloc_vcprintf(NULL, NULL, format, ap);
|
|
||||||
format = va_arg(ap, const char *);
|
|
||||||
malloc_vcprintf(NULL, NULL, format, ap);
|
|
||||||
va_end(ap);
|
|
||||||
malloc_printf("\n");
|
|
||||||
test_status = test_status_fail;
|
test_status = test_status_fail;
|
||||||
}
|
}
|
||||||
|
@ -1576,7 +1576,7 @@ TEST_BEGIN(test_by_array_64)
|
|||||||
for (i = 0; i < BLOCK_SIZE64; i++) {
|
for (i = 0; i < BLOCK_SIZE64; i++) {
|
||||||
if (i < COUNT_1) {
|
if (i < COUNT_1) {
|
||||||
assert_u64_eq(array64[i], init_by_array_64_expected[i],
|
assert_u64_eq(array64[i], init_by_array_64_expected[i],
|
||||||
"Output mismatch for i=%d");
|
"Output mismatch for i=%d", i);
|
||||||
}
|
}
|
||||||
r = gen_rand64(ctx);
|
r = gen_rand64(ctx);
|
||||||
assert_u64_eq(r, array64[i],
|
assert_u64_eq(r, array64[i],
|
||||||
|
@ -29,7 +29,7 @@ TEST_BEGIN(test_count_insert_search_remove)
|
|||||||
assert_false(ckh_new(&ckh, 2, ckh_string_hash, ckh_string_keycomp),
|
assert_false(ckh_new(&ckh, 2, ckh_string_hash, ckh_string_keycomp),
|
||||||
"Unexpected ckh_new() error");
|
"Unexpected ckh_new() error");
|
||||||
assert_zu_eq(ckh_count(&ckh), 0,
|
assert_zu_eq(ckh_count(&ckh), 0,
|
||||||
"ckh_count() should return %zu, but it returned %zu", 0,
|
"ckh_count() should return %zu, but it returned %zu", ZU(0),
|
||||||
ckh_count(&ckh));
|
ckh_count(&ckh));
|
||||||
|
|
||||||
/* Insert. */
|
/* Insert. */
|
||||||
@ -101,11 +101,11 @@ TEST_END
|
|||||||
|
|
||||||
TEST_BEGIN(test_insert_iter_remove)
|
TEST_BEGIN(test_insert_iter_remove)
|
||||||
{
|
{
|
||||||
#define NITEMS 1000
|
#define NITEMS ZU(1000)
|
||||||
ckh_t ckh;
|
ckh_t ckh;
|
||||||
void **p[NITEMS];
|
void **p[NITEMS];
|
||||||
void *q, *r;
|
void *q, *r;
|
||||||
unsigned i;
|
size_t i;
|
||||||
|
|
||||||
assert_false(ckh_new(&ckh, 2, ckh_pointer_hash, ckh_pointer_keycomp),
|
assert_false(ckh_new(&ckh, 2, ckh_pointer_hash, ckh_pointer_keycomp),
|
||||||
"Unexpected ckh_new() error");
|
"Unexpected ckh_new() error");
|
||||||
@ -116,7 +116,7 @@ TEST_BEGIN(test_insert_iter_remove)
|
|||||||
}
|
}
|
||||||
|
|
||||||
for (i = 0; i < NITEMS; i++) {
|
for (i = 0; i < NITEMS; i++) {
|
||||||
unsigned j;
|
size_t j;
|
||||||
|
|
||||||
for (j = i; j < NITEMS; j++) {
|
for (j = i; j < NITEMS; j++) {
|
||||||
assert_false(ckh_insert(&ckh, p[j], p[j]),
|
assert_false(ckh_insert(&ckh, p[j], p[j]),
|
||||||
@ -152,7 +152,7 @@ TEST_BEGIN(test_insert_iter_remove)
|
|||||||
|
|
||||||
for (tabind = 0; ckh_iter(&ckh, &tabind, &q, &r) ==
|
for (tabind = 0; ckh_iter(&ckh, &tabind, &q, &r) ==
|
||||||
false;) {
|
false;) {
|
||||||
unsigned k;
|
size_t k;
|
||||||
|
|
||||||
assert_ptr_eq(q, r, "Key and val not equal");
|
assert_ptr_eq(q, r, "Key and val not equal");
|
||||||
|
|
||||||
@ -188,7 +188,7 @@ TEST_BEGIN(test_insert_iter_remove)
|
|||||||
}
|
}
|
||||||
|
|
||||||
assert_zu_eq(ckh_count(&ckh), 0,
|
assert_zu_eq(ckh_count(&ckh), 0,
|
||||||
"ckh_count() should return %zu, but it returned %zu", 0,
|
"ckh_count() should return %zu, but it returned %zu", ZU(0),
|
||||||
ckh_count(&ckh));
|
ckh_count(&ckh));
|
||||||
ckh_delete(&ckh);
|
ckh_delete(&ckh);
|
||||||
#undef NITEMS
|
#undef NITEMS
|
||||||
|
@ -122,9 +122,15 @@ hash_variant_verify(hash_variant_t variant)
|
|||||||
(final[3] << 24);
|
(final[3] << 24);
|
||||||
|
|
||||||
switch (variant) {
|
switch (variant) {
|
||||||
|
#ifdef JEMALLOC_BIG_ENDIAN
|
||||||
|
case hash_variant_x86_32: expected = 0x6213303eU; break;
|
||||||
|
case hash_variant_x86_128: expected = 0x266820caU; break;
|
||||||
|
case hash_variant_x64_128: expected = 0xcc622b6fU; break;
|
||||||
|
#else
|
||||||
case hash_variant_x86_32: expected = 0xb0f57ee3U; break;
|
case hash_variant_x86_32: expected = 0xb0f57ee3U; break;
|
||||||
case hash_variant_x86_128: expected = 0xb3ece62aU; break;
|
case hash_variant_x86_128: expected = 0xb3ece62aU; break;
|
||||||
case hash_variant_x64_128: expected = 0x6384ba69U; break;
|
case hash_variant_x64_128: expected = 0x6384ba69U; break;
|
||||||
|
#endif
|
||||||
default: not_reached();
|
default: not_reached();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -73,7 +73,7 @@ test_junk(size_t sz_min, size_t sz_max)
|
|||||||
if (sz_prev > 0) {
|
if (sz_prev > 0) {
|
||||||
assert_c_eq(s[0], 'a',
|
assert_c_eq(s[0], 'a',
|
||||||
"Previously allocated byte %zu/%zu is corrupted",
|
"Previously allocated byte %zu/%zu is corrupted",
|
||||||
0, sz_prev);
|
ZU(0), sz_prev);
|
||||||
assert_c_eq(s[sz_prev-1], 'a',
|
assert_c_eq(s[sz_prev-1], 'a',
|
||||||
"Previously allocated byte %zu/%zu is corrupted",
|
"Previously allocated byte %zu/%zu is corrupted",
|
||||||
sz_prev-1, sz_prev);
|
sz_prev-1, sz_prev);
|
||||||
|
@ -21,7 +21,7 @@ quarantine_clear(void)
|
|||||||
|
|
||||||
TEST_BEGIN(test_quarantine)
|
TEST_BEGIN(test_quarantine)
|
||||||
{
|
{
|
||||||
#define SZ 256
|
#define SZ ZU(256)
|
||||||
#define NQUARANTINED (QUARANTINE_SIZE/SZ)
|
#define NQUARANTINED (QUARANTINE_SIZE/SZ)
|
||||||
void *quarantined[NQUARANTINED+1];
|
void *quarantined[NQUARANTINED+1];
|
||||||
size_t i, j;
|
size_t i, j;
|
||||||
|
@ -48,8 +48,9 @@ TEST_BEGIN(test_rtree_bits)
|
|||||||
assert_u_eq(rtree_get(rtree, keys[k]), 1,
|
assert_u_eq(rtree_get(rtree, keys[k]), 1,
|
||||||
"rtree_get() should return previously set "
|
"rtree_get() should return previously set "
|
||||||
"value and ignore insignificant key bits; "
|
"value and ignore insignificant key bits; "
|
||||||
"i=%u, j=%u, k=%u, set key=%#x, "
|
"i=%u, j=%u, k=%u, set key=%#"PRIxPTR", "
|
||||||
"get key=%#x", i, j, k, keys[j], keys[k]);
|
"get key=%#"PRIxPTR, i, j, k, keys[j],
|
||||||
|
keys[k]);
|
||||||
}
|
}
|
||||||
assert_u_eq(rtree_get(rtree,
|
assert_u_eq(rtree_get(rtree,
|
||||||
(((uintptr_t)1) << (sizeof(uintptr_t)*8-i))), 0,
|
(((uintptr_t)1) << (sizeof(uintptr_t)*8-i))), 0,
|
||||||
|
@ -20,7 +20,7 @@ test_zero(size_t sz_min, size_t sz_max)
|
|||||||
if (sz_prev > 0) {
|
if (sz_prev > 0) {
|
||||||
assert_c_eq(s[0], 'a',
|
assert_c_eq(s[0], 'a',
|
||||||
"Previously allocated byte %zu/%zu is corrupted",
|
"Previously allocated byte %zu/%zu is corrupted",
|
||||||
0, sz_prev);
|
ZU(0), sz_prev);
|
||||||
assert_c_eq(s[sz_prev-1], 'a',
|
assert_c_eq(s[sz_prev-1], 'a',
|
||||||
"Previously allocated byte %zu/%zu is corrupted",
|
"Previously allocated byte %zu/%zu is corrupted",
|
||||||
sz_prev-1, sz_prev);
|
sz_prev-1, sz_prev);
|
||||||
|
Loading…
Reference in New Issue
Block a user