don't bother iterating through generic array items in cpy.*Arr on free

This commit is contained in:
dzaima 2022-07-23 23:51:01 +03:00
parent 32d8c09e2b
commit c1b66c5982
5 changed files with 58 additions and 27 deletions

View File

@ -58,6 +58,7 @@ static void fillarr_visit(Value* x) { assert(x->type == t_fillarr);
}
static bool fillarr_canStore(B x) { return true; }
static void fillarr_freeT(Value* x) { FillArr* s=(void*)x; dec(s->fill); decSh(x); mm_free(x); }
static void fillslice_visit(Value* x) { FillSlice* s=(void*)x; mm_visitP(s->p); mm_visit(s->fill); }
static void fillslice_freeO(Value* x) { FillSlice* s=(void*)x; ptr_dec(s->p); dec(s->fill); decSh(x); }
@ -69,6 +70,7 @@ void fillarr_init() {
TIi(t_fillarr,slice) = fillarr_slice; TIi(t_fillslice,slice) = fillslice_slice;
TIi(t_fillarr,freeO) = fillarr_freeO; TIi(t_fillslice,freeO) = fillslice_freeO;
TIi(t_fillarr,freeF) = fillarr_freeF; TIi(t_fillslice,freeF) = fillslice_freeF;
TIi(t_fillarr,freeT) = fillarr_freeT;
TIi(t_fillarr,visit) = fillarr_visit; TIi(t_fillslice,visit) = fillslice_visit;
TIi(t_fillarr,print) = farr_print; TIi(t_fillslice,print) = farr_print;
TIi(t_fillarr,isArr) = true; TIi(t_fillslice,isArr) = true;

View File

@ -130,15 +130,29 @@ static void harrP_print(FILE* f, B x) {
fprintf(f, "⟩)");
}
#if DEBUG
static void harr_freeT(Value* x) {
B* p = ((HArr*)x)->a;
usz ia = ((Arr*)x)->ia;
for (usz i = 0; i < ia; i++) assert(!isVal(p[i]));
tyarr_freeF(x);
}
#endif
void harr_init() {
TIi(t_harr,get) = harr_get; TIi(t_hslice,get) = hslice_get; TIi(t_harrPartial,get) = harrP_get;
TIi(t_harr,getU) = harr_getU; TIi(t_hslice,getU) = hslice_getU; TIi(t_harrPartial,getU) = harrP_get;
TIi(t_harr,slice) = harr_slice; TIi(t_hslice,slice) = hslice_slice;
TIi(t_harr,freeO) = harr_freeO; TIi(t_hslice,freeO) = slice_freeO; TIi(t_harrPartial,freeO) = harrP_freeO;
TIi(t_harr,freeF) = harr_freeF; TIi(t_hslice,freeF) = slice_freeF; TIi(t_harrPartial,freeF) = harrP_freeF;
TIi(t_harr,visit) = harr_visit; TIi(t_hslice,visit) = slice_visit; TIi(t_harrPartial,visit) = harrP_visit;
TIi(t_harr,print) = farr_print; TIi(t_hslice,print) = farr_print; TIi(t_harrPartial,print) = harrP_print;
TIi(t_harr,isArr) = true; TIi(t_hslice,isArr) = true;
TIi(t_harr,get) = harr_get; TIi(t_hslice,get) = hslice_get; TIi(t_harrPartial,get) = harrP_get;
TIi(t_harr,getU) = harr_getU; TIi(t_hslice,getU) = hslice_getU; TIi(t_harrPartial,getU) = harrP_get;
TIi(t_harr,slice) = harr_slice; TIi(t_hslice,slice) = hslice_slice;
TIi(t_harr,freeO) = harr_freeO; TIi(t_hslice,freeO) = slice_freeO; TIi(t_harrPartial,freeO) = harrP_freeO;
TIi(t_harr,freeF) = harr_freeF; TIi(t_hslice,freeF) = slice_freeF; TIi(t_harrPartial,freeF) = harrP_freeF;
#if DEBUG
TIi(t_harr,freeT) = harr_freeT;
#else
TIi(t_harr,freeT) = tyarr_freeF;
#endif
TIi(t_harr,visit) = harr_visit; TIi(t_hslice,visit) = slice_visit; TIi(t_harrPartial,visit) = harrP_visit;
TIi(t_harr,print) = farr_print; TIi(t_hslice,print) = farr_print; TIi(t_harrPartial,print) = harrP_print;
TIi(t_harr,isArr) = true; TIi(t_hslice,isArr) = true;
TIi(t_harr,canStore) = harr_canStore;
bi_emptyHVec = m_harrUv(0).b; gc_add(bi_emptyHVec);
}

View File

@ -510,6 +510,7 @@ typedef B (*D2C2)(Md2D*, B, B);
F(FB2v, print) /* doesn't consume */ \
F(V2v, visit) /* call mm_visit for all referents */ \
F(V2v, freeO) /* like freeF, but doesn't call mm_free for GC to be able to clear cycles */ \
F(V2v, freeT) /* freeF, but assumes this is an array which consists of non-heap-allocated elements */ \
F(B2B, decompose) /* consumes; must return a HArr */ \
F(bool, isArr) /* whether this type would have an ARR_TAG tag, in cases where the tag is unknown */ \
F(bool, arrD1) /* is always an array with depth 1 */ \
@ -573,6 +574,10 @@ static inline void decG(B x) {
Value* vx = v(x);
if(!--vx->refc) value_free(vx);
}
FORCE_INLINE void ptr_decT(Arr* x) { // assumes argument is an array and consists of non-heap-allocated elements
if (x->refc==1) TIv(x,freeT)((Value*) x);
else x->refc--;
}
static inline B incG(B x) { // inc for guaranteed heap-allocated objects
assert(isVal(x));
v(VALIDATE(x))->refc++;

View File

@ -5,7 +5,7 @@
#include "ns.h"
#include "builtins.h"
#define FOR_INIT(F) F(base) F(harr) F(mutF) F(fillarr) F(tyarr) F(hash) F(sfns) F(fns) F(arith) F(md1) F(md2) F(derv) F(comp) F(rtWrap) F(ns) F(nfn) F(sysfn) F(inverse) F(load) F(sysfnPost) F(dervPost) F(ffi) F(mmap)
#define FOR_INIT(F) F(base) F(harr) F(mutF) F(fillarr) F(tyarr) F(hash) F(sfns) F(fns) F(arith) F(md1) F(md2) F(derv) F(comp) F(rtWrap) F(ns) F(nfn) F(sysfn) F(inverse) F(load) F(sysfnPost) F(dervPost) F(ffi) F(mmap) F(typesFinished)
#define F(X) void X##_init(void);
FOR_INIT(F)
#undef F
@ -595,6 +595,9 @@ void customObj_visit(Value* v) { ((CustomObj*)v)->visit(v); }
void customObj_freeO(Value* v) { ((CustomObj*)v)->freeO(v); }
void customObj_freeF(Value* v) { ((CustomObj*)v)->freeO(v); mm_free(v); }
void def_fallbackTriv(Value* v) { // used while vtables aren't yet fully loaded; should become completely unused after typesFinished_init
TIv(v,freeF)(v);
}
static NOINLINE B m_bfn(BB2B c1, BBB2B c2, u8 id) {
BFn* f = mm_alloc(sizeof(BFn), t_funBI);
@ -638,6 +641,7 @@ static NOINLINE B m_bm2(D2C1 c1, D2C2 c2, u8 id) {
void base_init() { // very first init function
for (u64 i = 0; i < t_COUNT; i++) {
TIi(i,freeO) = def_freeO;
TIi(i,freeT) = def_fallbackTriv;
TIi(i,freeF) = def_freeF;
TIi(i,visit) = def_visit;
TIi(i,get) = def_get;
@ -708,6 +712,11 @@ void base_init() { // very first init function
#undef FM
#undef FD
}
void typesFinished_init() {
for (u64 i = 0; i < t_COUNT; i++) {
if (TIi(i,freeT) == def_fallbackTriv) TIi(i,freeT) = TIi(i,freeF);
}
}
bool cbqn_initialized;
void cbqn_init() {

View File

@ -213,34 +213,35 @@ DEF_G(void, copy, B, (void* a, usz ms, B x, usz xs, usz l), ms, x, x
}
#define COPY_FN(X,R) avx2_copy_##X##_##R
#define MAKE_CPY(MAKE, GET, WR, XRP, H2T, T, ...) \
static copy_fn copy##T##Fns[10]; \
#define MAKE_CPY(TY, MAKE, GET, WR, XRP, H2T, T, ...) \
static copy_fn copy##T##Fns[10]; \
static void cpy##T##Arr_B(u8* xp, u8* rp, u64 ia, u8* xRaw) { \
Arr* xa = (Arr*)xRaw; B* bxp = arrV_bptr(xa); \
if (bxp!=NULL && sizeof(B)==sizeof(f64)) { \
H2T; \
} else { AS2B fn = TIv(xa,GET); \
for (usz i=0; i<ia; i++) WR(fn(xa,i)); \
} \
} \
static copy_fn copy##T##Fns[] = __VA_ARGS__; \
Arr* xa = (Arr*)xRaw; B* bxp = arrV_bptr(xa); \
if (bxp!=NULL && sizeof(B)==sizeof(f64)) { \
H2T; \
} else { AS2B fn = TIv(xa,GET); \
for (usz i=0; i<ia; i++) WR(fn(xa,i)); \
} \
} \
static copy_fn copy##T##Fns[] = __VA_ARGS__; \
T##Arr* cpy##T##Arr(B x) { \
usz ia = a(x)->ia; \
MAKE; arr_shCopy(r, x); \
if (ia>0) { \
copy##T##Fns[TI(x,elType)](tyany_ptr(x), (u8*)(XRP), ia, (u8*)a(x)); \
} \
decG(x); \
if (TY) ptr_decT(a(x)); \
else decG(x); \
return (T##Arr*)r; \
}
#define BIT_PUT(V) bitp_set((u64*)rp, i, o2bu(V))
#define H2T_COPY(T) copy##T##Fns[el_MAX]((u8*)bxp, rp, ia, xRaw)
#define MAKE_TYCPY(T, E, F, ...) MAKE_CPY(T##Atom* rp; Arr* r = m_##E##arrp(&rp, ia), getU, ((T##Atom*)rp)[i] = F, rp, H2T_COPY(T), T, __VA_ARGS__)
#define MAKE_TYCPY(T, E, F, ...) MAKE_CPY(1, T##Atom* rp; Arr* r = m_##E##arrp(&rp, ia), getU, ((T##Atom*)rp)[i] = F, rp, H2T_COPY(T), T, __VA_ARGS__)
#define MAKE_CCPY(T,E) MAKE_TYCPY(T, E, o2cu, {badCopy, badCopy, badCopy, badCopy, badCopy, COPY_FN(c8,E),COPY_FN(c16,E),COPY_FN(c32,E),cpy##T##Arr_B,COPY_FN(B,E)})
#define MAKE_ICPY(T,E) MAKE_TYCPY(T, E, o2fu, {COPY_FN(1,E),COPY_FN(i8,E),COPY_FN(i16,E),COPY_FN(i32,E),COPY_FN(f64,E),badCopy, badCopy, badCopy, cpy##T##Arr_B,COPY_FN(f64,E)})
MAKE_CPY(HArr_p p = m_harrUp(ia); Arr* r = (Arr*)p.c, get, ((B*)rp)[i] =, p.a, for (usz i=0; i<ia; i++) ((B*)rp)[i] = inc(bxp[i]),
MAKE_CPY(0, HArr_p p = m_harrUp(ia); Arr* r = (Arr*)p.c, get, ((B*)rp)[i] =, p.a, for (usz i=0; i<ia; i++) ((B*)rp)[i] = inc(bxp[i]),
H, {COPY_FN(1,B),COPY_FN(i8,B),COPY_FN(i16,B),COPY_FN(i32,B),COPY_FN(f64,B),COPY_FN(c8,B),COPY_FN(c16,B),COPY_FN(c32,B),cpyHArr_B, COPY_FN(f64,B)})
MAKE_CPY(u64* rp; Arr* r = m_bitarrp(&rp, ia), getU, BIT_PUT, rp, H2T_COPY(Bit),
MAKE_CPY(1, u64* rp; Arr* r = m_bitarrp(&rp, ia), getU, BIT_PUT, rp, H2T_COPY(Bit),
Bit, {COPY_FN(1,1),COPY_FN(i8,1),COPY_FN(i16,1),COPY_FN(i32,1),COPY_FN(f64,1),badCopy, badCopy, badCopy, cpyBitArr_B, COPY_FN(f64,1)})
#else
@ -259,7 +260,7 @@ DEF_G(void, copy, B, (void* a, usz ms, B x, usz xs, usz l), ms, x, x
if (xp!=NULL) { for (usz i=0; i<ia; i++) rp[i]=o2fu(xp[i] ); } \
else { SGetU(x) for (usz i=0; i<ia; i++) rp[i]=o2fu(GetU(x,i)); } \
} \
decG(x); \
ptr_decT(a(x)); \
return (T##Arr*)r; \
}
@ -277,7 +278,7 @@ DEF_G(void, copy, B, (void* a, usz ms, B x, usz xs, usz l), ms, x, x
if (xp!=NULL) { for (usz i=0; i<ia; i++) rp[i]=o2cu(xp[i] ); } \
else { SGetU(x) for (usz i=0; i<ia; i++) rp[i]=o2cu(GetU(x,i)); } \
} \
decG(x); \
ptr_decT(a(x)); \
return (T##Arr*)r; \
}
@ -298,7 +299,7 @@ DEF_G(void, copy, B, (void* a, usz ms, B x, usz xs, usz l), ms, x, x
if (xp!=NULL) { for (usz i=0; i<ia; i++) r.a[i] = inc(xp[i]); }
else { SGet(x) for (usz i=0; i<ia; i++) r.a[i] = Get(x, i); }
}
dec(x);
decG(x);
return r.c;
}
BitArr* cpyBitArr(B x) {
@ -316,7 +317,7 @@ DEF_G(void, copy, B, (void* a, usz ms, B x, usz xs, usz l), ms, x, x
if (xp!=NULL) { for (usz i=0; i<ia; i++) bitp_set(rp,i,o2fu(xp[i] )); }
else { SGetU(x) for (usz i=0; i<ia; i++) bitp_set(rp,i,o2fu(GetU(x,i))); }
}
decG(x);
ptr_decT(a(x));
return (BitArr*)r;
}