compile-time separated DFND
This commit is contained in:
parent
305f578707
commit
6b52c2069f
@ -213,9 +213,9 @@ Throw an error with `thrM("some message")` or `thr(some B instance)` or `thrOOM(
|
||||
|
||||
A fancier message can be created with `thrF(message, …)` with printf-like (but different!!) varargs (source in `do_fmt`):
|
||||
```
|
||||
%i decimal i32
|
||||
%i decimal i32 (also for i8/i16/ur)
|
||||
%l decimal i64
|
||||
%ui decimal u32
|
||||
%ui decimal u32 (also for u8/u16)
|
||||
%ul decimal u64
|
||||
%xi hex u32
|
||||
%xl hex u64
|
||||
|
||||
@ -185,7 +185,11 @@ B casrt_c2(B t, B w, B x) {
|
||||
}
|
||||
|
||||
B sys_c1(B t, B x);
|
||||
B out_c1(B t, B x) { printRaw(x); putchar('\n'); return x; }
|
||||
B out_c1(B t, B x) {
|
||||
if (isArr(x) && rnk(x)>1) thrF("•Out: Argument cannot have rank %i", rnk(x));
|
||||
printRaw(x); putchar('\n');
|
||||
return x;
|
||||
}
|
||||
B show_c1(B t, B x) {
|
||||
#if FORMATTER
|
||||
B fmt = bqn_fmt(inc(x));
|
||||
|
||||
@ -506,7 +506,6 @@ Nvm_res m_nvm(Body* body) {
|
||||
#define CCALL(F) { u64 f=(u64)(F); if(f>I32_MAX)thrM("JIT: Function address too large for call"); CALLi(f); }
|
||||
u32* origBC = body->bc;
|
||||
OptRes optRes = opt(origBC);
|
||||
Block** blocks = body->bl->blocks;
|
||||
i32 depth = 0;
|
||||
u32* bc = optRes.bc;
|
||||
i32 lGPos = 0; // last updated gStack offset
|
||||
@ -559,8 +558,8 @@ Nvm_res m_nvm(Body* body) {
|
||||
if (sz) { TOPp; IMM(R_A1, sz); lGPos=SPOSq(1-sz); INV(2,0,i_ARR_p); } // (B, i64 sz, S)
|
||||
else { TOPs; CCALL(i_ARR_0); } // unused with optimizations
|
||||
break;
|
||||
case DFND: TOPs; // (u32* bc, Scope* sc, Block* bl)
|
||||
Block* bl = blocks[*bc++];
|
||||
case DFND0: case DFND1: case DFND2: TOPs; // (u32* bc, Scope* sc, Block* bl)
|
||||
Block* bl = (Block*)L64;
|
||||
u64 fn = (u64)(bl->ty==0? i_DFND_0 : bl->ty==1? i_DFND_1 : bl->ty==2? i_DFND_2 : NULL);
|
||||
if (fn==0) thrM("JIT: Bad DFND argument");
|
||||
GET(R_A3,-1,2);
|
||||
|
||||
40
src/vm.c
40
src/vm.c
@ -33,7 +33,8 @@ u32* nextBC(u32* p) {
|
||||
case LOCO: case LOCM: case LOCU:
|
||||
case EXTO: case EXTM: case EXTU:
|
||||
case ADDI: case ADDU:
|
||||
case FN1Ci: case FN1Oi: case FN2Ci: case SETNi: case SETUi: case SETMi: case SETNv: case SETUv: case SETMv:
|
||||
case FN1Ci: case FN1Oi: case FN2Ci: case DFND0: case DFND1: case DFND2:
|
||||
case SETNi: case SETUi: case SETMi: case SETNv: case SETUv: case SETMv:
|
||||
off = 3; break;
|
||||
case FN2Oi: case SETHi:
|
||||
off = 5; break;
|
||||
@ -44,7 +45,8 @@ u32* nextBC(u32* p) {
|
||||
i32 stackDiff(u32* p) {
|
||||
if (*p==ARRO|*p==ARRM) return 1-p[1];
|
||||
switch(*p) { default: UD; // case ARRO: case ARRM: return 1-p[1];
|
||||
case PUSH: case VARO: case VARM: case DFND: case LOCO: case LOCM: case LOCU: case EXTO: case EXTM: case EXTU: case SYSV: case ADDI: case ADDU: return 1;
|
||||
case PUSH: case VARO: case VARM: case DFND: case LOCO: case LOCM: case DFND0:case DFND1:case DFND2:
|
||||
case LOCU: case EXTO: case EXTM: case EXTU: case SYSV: case ADDI: case ADDU: return 1;
|
||||
case FN1Ci:case FN1Oi:case CHKV: case VFYM: case FLDO: case FLDM: case RETD: case NSPM: return 0;
|
||||
case FN2Ci:case FN2Oi:case FN1C: case FN1O: case OP1D: case TR2D: case POPS: case OP2H: case RETN: return -1;
|
||||
case OP2D: case TR3D: case FN2C: case FN2O: case TR3O: case SETH: case SETHi:return -2;
|
||||
@ -58,7 +60,8 @@ i32 stackDiff(u32* p) {
|
||||
i32 stackConsumed(u32* p) {
|
||||
if (*p==ARRO|*p==ARRM) return p[1];
|
||||
switch(*p) { default: UD; // case ARRO: case ARRM: return -p[1];
|
||||
case PUSH: case VARO: case VARM: case DFND: case LOCO: case LOCM: case LOCU: case EXTO: case EXTM: case EXTU: case SYSV: case ADDI: case ADDU: return 0;
|
||||
case PUSH: case VARO: case VARM: case DFND: case LOCO: case LOCM: case LOCU: case EXTO: case EXTM:
|
||||
case EXTU: case SYSV: case ADDI: case ADDU: case DFND0:case DFND1:case DFND2:return 0;
|
||||
case CHKV: case RETD: return 0;
|
||||
case FN1Ci:case FN1Oi:case FLDO: case FLDM: case NSPM: case RETN: case POPS: case VFYM: return 1;
|
||||
case FN2Ci:case FN2Oi:case FN1C: case FN1O: case OP1D: case TR2D: case OP2H: case SETH: case SETHi:return 2;
|
||||
@ -278,9 +281,10 @@ Block* compileBlock(B block, Comp* comp, bool* bDone, u32* bc, usz bcIA, B allBl
|
||||
if ((u32)id >= a(allBlocks)->ia) thrM("VM compiler: DFND index out-of-bounds");
|
||||
if (bDone[id]) thrM("VM compiler: DFND of the same block in multiple places");
|
||||
bDone[id] = true;
|
||||
TSADD(newBC, DFND);
|
||||
TSADD(newBC, TSSIZE(usedBlocks));
|
||||
TSADD(usedBlocks, compileBlock(TI(allBlocks,getU)(allBlocks,id), comp, bDone, bc, bcIA, allBlocks, allBodies, nameList, sc, depth+1));
|
||||
Block* bl = compileBlock(TI(allBlocks,getU)(allBlocks,id), comp, bDone, bc, bcIA, allBlocks, allBodies, nameList, sc, depth+1);
|
||||
TSADD(newBC, bl->ty==0? DFND0 : bl->ty==1? DFND1 : DFND2);
|
||||
A64((u64)bl);
|
||||
TSADD(usedBlocks, bl);
|
||||
break;
|
||||
}
|
||||
case LOCO: case LOCM: case LOCU: {
|
||||
@ -532,7 +536,6 @@ B evalBC(Block* bl, Body* b, Scope* sc) { // doesn't consume
|
||||
printf("new eval\n");
|
||||
#endif
|
||||
B* objs = bl->comp->objs->a;
|
||||
Block** blocks = bl->blocks;
|
||||
u32* bc = b->bc;
|
||||
pushEnv(sc, bc);
|
||||
gsReserve(b->maxStack);
|
||||
@ -626,16 +629,19 @@ B evalBC(Block* bl, Body* b, Scope* sc) { // doesn't consume
|
||||
}
|
||||
break;
|
||||
}
|
||||
case DFND: {
|
||||
GS_UPD;POS_UPD;
|
||||
Block* cbl = blocks[*bc++];
|
||||
switch(cbl->ty) { default: UD;
|
||||
case 0: ADD(m_funBlock(cbl, sc)); break;
|
||||
case 1: ADD(m_md1Block(cbl, sc)); break;
|
||||
case 2: ADD(m_md2Block(cbl, sc)); break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case DFND0: { GS_UPD;POS_UPD; ADD(m_funBlock((Block*)L64, sc)); break; }
|
||||
case DFND1: { GS_UPD;POS_UPD; ADD(m_md1Block((Block*)L64, sc)); break; }
|
||||
case DFND2: { GS_UPD;POS_UPD; ADD(m_md2Block((Block*)L64, sc)); break; }
|
||||
// case DFND: {
|
||||
// GS_UPD;POS_UPD;
|
||||
// Block* cbl = blocks[*bc++];
|
||||
// switch(cbl->ty) { default: UD;
|
||||
// case 0: ADD(m_funBlock(cbl, sc)); break;
|
||||
// case 1: ADD(m_md1Block(cbl, sc)); break;
|
||||
// case 2: ADD(m_md2Block(cbl, sc)); break;
|
||||
// }
|
||||
// break;
|
||||
// }
|
||||
case OP1D: { P(f)P(m) GS_UPD;POS_UPD; ADD(m1_d (m,f )); break; }
|
||||
case OP2D: { P(f)P(m)P(g) GS_UPD;POS_UPD; ADD(m2_d (m,f,g)); break; }
|
||||
case OP2H: { P(m)P(g) ADD(m2_h (m, g)); break; }
|
||||
|
||||
1
src/vm.h
1
src/vm.h
@ -49,6 +49,7 @@ enum {
|
||||
SETNi, SETUi, SETMi, // SET_ alternatives that expect the set variable as a depth-position pair like LOC_
|
||||
SETNv, SETUv, SETMv, // SET_i alternatives that also don't return the result
|
||||
SETHi, // internal version of SETH, with 2×u64 arguments specifying bodies to jump to on fail (or NULL if is last)
|
||||
DFND0, DFND1, DFND2, // internal versions of DFND with a specific type, and a u64 argument representing the block pointer
|
||||
FAIL, // this body cannot be called monadically/dyadically
|
||||
BC_SIZE
|
||||
};
|
||||
|
||||
Loading…
Reference in New Issue
Block a user