diff --git a/src/core/stuff.h b/src/core/stuff.h index 174cf395..0e1ed65e 100644 --- a/src/core/stuff.h +++ b/src/core/stuff.h @@ -220,6 +220,11 @@ static bool atomEqual(B w, B x) { // doesn't consume (not that that matters real static void pst(char* msg) { VALGRIND_PRINTF_BACKTRACE("%s", msg); } +#else + #define vg_def_p(X, L) + #define vg_undef_p(X, L) + #define vg_def_v(X) (X) + #define vg_undef_v(X) (X) #endif // call stuff diff --git a/src/opt/mm_buddyTemplate.c b/src/opt/mm_buddyTemplate.c index 4cfbc3fd..f55e1819 100644 --- a/src/opt/mm_buddyTemplate.c +++ b/src/opt/mm_buddyTemplate.c @@ -26,9 +26,11 @@ FORCE_INLINE void BN(splitTo)(EmptyValue* c, i64 from, i64 to, bool notEqual) { b->type = t_empty; b->mmInfo = MMI(from); b->next = buckets[from]; + vg_undef_p(b, sizeof(EmptyValue)); buckets[from] = b; } c->next = buckets[from]; + vg_undef_p(c, sizeof(EmptyValue)); buckets[from] = c; } @@ -44,9 +46,6 @@ static NOINLINE void* BN(allocateMore)(i64 bucket, u8 type, i64 from, i64 to) { EmptyValue* c = MMAP(sz); if (c==MAP_FAILED) thrOOM(); #endif - #ifdef USE_VALGRIND - VALGRIND_MAKE_MEM_UNDEFINED(c, sz); - #endif if (alSize+1>=alCap) { alCap = alCap? alCap*2 : 1024; al = realloc(al, sizeof(AllocInfo)*alCap); @@ -55,6 +54,7 @@ static NOINLINE void* BN(allocateMore)(i64 bucket, u8 type, i64 from, i64 to) { c->type = t_empty; c->mmInfo = from; c->next = 0; + vg_undef_p(c, sz); BN(splitTo)(c, from, to, false); return BN(allocL)(bucket, type); } @@ -67,8 +67,8 @@ NOINLINE void* BN(allocS)(i64 bucket, u8 type) { from++; if (buckets[from]) { c = buckets[from]; - assert((c->mmInfo&63)==from); - buckets[from] = c->next; + assert((vg_def_v(c->mmInfo)&63)==from); + buckets[from] = vg_def_v(c->next); break; } if (from >= ALSZ) return BN(allocateMore)(bucket, type, from, to); @@ -83,8 +83,8 @@ void BN(forHeap)(V2v f) { Value* s = ci.p; Value* e = (Value*)(ci.sz + (u8*)ci.p); while (s!=e) { - if (s->type!=t_empty) f(s); - s = (Value*)(BSZ(s->mmInfo&63) + (u8*)s); + if (vg_def_v(s->type)!=t_empty) f(s); + s = (Value*)(BSZ(vg_def_v(s->mmInfo)&63) + (u8*)s); } } } @@ -94,8 +94,8 @@ void BN(forFreedHeap)(V2v f) { Value* s = ci.p; Value* e = (Value*)(ci.sz + (u8*)ci.p); while (s!=e) { - if (s->type==t_empty) f(s); - s = (Value*)(BSZ(s->mmInfo&63) + (u8*)s); + if (vg_def_v(s->type)==t_empty) f(s); + s = (Value*)(BSZ(vg_def_v(s->mmInfo)&63) + (u8*)s); } } } diff --git a/src/opt/mm_buddyTemplate.h b/src/opt/mm_buddyTemplate.h index 5036a4c2..2a44860e 100644 --- a/src/opt/mm_buddyTemplate.h +++ b/src/opt/mm_buddyTemplate.h @@ -1,11 +1,6 @@ #define buckets BN(buckets) static void BN(free)(Value* x) { onFree(x); - #ifdef USE_VALGRIND - VALGRIND_MAKE_MEM_UNDEFINED(x, BSZ(x->mmInfo&127)); - VALGRIND_MAKE_MEM_DEFINED(&x->mmInfo, 1); - VALGRIND_MAKE_MEM_DEFINED(&x->type, 1); - #endif #ifdef DONT_FREE if (x->type!=t_freed) x->flags = x->type; #else @@ -15,17 +10,14 @@ static void BN(free)(Value* x) { buckets[b] = (EmptyValue*)x; #endif x->type = t_empty; + vg_undef_p(x, BSZ(x->mmInfo&127)); } NOINLINE void* BN(allocS)(i64 bucket, u8 type); static void* BN(allocL)(i64 bucket, u8 type) { EmptyValue* x = buckets[bucket]; if (RARE(x==NULL)) return BN(allocS)(bucket, type); - buckets[bucket] = x->next; - #ifdef USE_VALGRIND - VALGRIND_MAKE_MEM_UNDEFINED(x, BSZ(bucket)); - VALGRIND_MAKE_MEM_DEFINED(&x->mmInfo, 1); - #endif + buckets[bucket] = vg_def_v(x->next); BN(ctrs)[bucket]++; x->flags = x->extra = x->type = x->mmInfo = 0; x->refc = 1; diff --git a/src/opt/mm_malloc.c b/src/opt/mm_malloc.c index 5765e00b..065dc001 100644 --- a/src/opt/mm_malloc.c +++ b/src/opt/mm_malloc.c @@ -2,6 +2,10 @@ #include #include +#if USE_VALGRIND +#warning "USE_VALGRIND=1 and MM=0 don't work well together; CBQN requires the ability to read past the end of allocations, but malloc doesn't provide that." +#endif + void gc_add(B x) { } void gc_addFn(vfn f) { } void gc_maybeGC() { } diff --git a/src/utils/valgrind.h b/src/utils/valgrind.h index 956c377d..4bbd954d 100644 --- a/src/utils/valgrind.h +++ b/src/utils/valgrind.h @@ -30,4 +30,9 @@ u64 vg_rand(u64 x); // randomize undefined bits in x, and return the value with void vg_printDefined_u64(char* name, u64 x); void vg_printDump_p(char* name, void* data, u64 len); -#define vg_printDump_v(X) ({ AUTO x_ = (X); vg_printDump_p(#X, &x_, sizeof(x_)); }) \ No newline at end of file +#define vg_printDump_v(X) ({ AUTO x_ = (X); vg_printDump_p(#X, &x_, sizeof(x_)); x_; }) + +static void vg_def_p(void* data, u64 len) { VALGRIND_MAKE_MEM_DEFINED(data, len); } +static void vg_undef_p(void* data, u64 len) { VALGRIND_MAKE_MEM_UNDEFINED(data, len); } +#define vg_def_v(X) ({ AUTO x_ = (X); vg_def_p (&x_, sizeof(x_)); x_; }) +#define vg_undef_v(X) ({ AUTO x_ = (X); vg_undef_p(&x_, sizeof(x_)); x_; }) \ No newline at end of file