Showing the changes to src (9 of 15 files). Show all
Unified · Split
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: ldo.c,v 1.217 2003/04/03 13:35:34 roberto Exp $ | |
| 2 | +** $Id: ldo.c,v 1.217a 2003/04/03 13:35:34 roberto Exp $ | |
| 3 | 3 | ** Stack and Call structure of Lua |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -322,11 +322,11 @@ static void resume (lua_State *L, void *ud) { · 316 unmodified lines | ||
| 322 | 322 | int nargs = *cast(int *, ud); |
| 323 | 323 | CallInfo *ci = L->ci; |
| 324 | 324 | if (ci == L->base_ci) { /* no activation record? */ |
| 325 | − if (nargs >= L->top - L->base) | |
| 326 | − luaG_runerror(L, "cannot resume dead coroutine"); | |
| 325 | + lua_assert(nargs < L->top - L->base); | |
| 327 | 326 | luaD_precall(L, L->top - (nargs + 1)); /* start coroutine */ |
| 328 | 327 | } |
| 329 | − else if (ci->state & CI_YIELD) { /* inside a yield? */ | |
| 328 | + else { /* inside a yield */ | |
| 329 | + lua_assert(ci->state & CI_YIELD); | |
| 330 | 330 | if (ci->state & CI_C) { /* `common' yield? */ |
| 331 | 331 | /* finish interrupted execution of `OP_CALL' */ |
| 332 | 332 | int nresults; |
| @@ -341,18 +341,31 @@ static void resume (lua_State *L, void *ud) { · 8 unmodified lines | ||
| 341 | 341 | ci->state &= ~CI_YIELD; |
| 342 | 342 | } |
| 343 | 343 | } |
| 344 | − else | |
| 345 | − luaG_runerror(L, "cannot resume non-suspended coroutine"); | |
| 346 | 344 | firstResult = luaV_execute(L); |
| 347 | 345 | if (firstResult != NULL) /* return? */ |
| 348 | 346 | luaD_poscall(L, LUA_MULTRET, firstResult); /* finalize this coroutine */ |
| 349 | 347 | } |
| 350 | 348 | |
| 351 | 349 | |
| 350 | +static int resume_error (lua_State *L, const char *msg) { | |
| 351 | + L->top = L->ci->base; | |
| 352 | + setsvalue2s(L->top, luaS_new(L, msg)); | |
| 353 | + incr_top(L); | |
| 354 | + lua_unlock(L); | |
| 355 | + return LUA_ERRRUN; | |
| 356 | +} | |
| 357 | + | |
| 358 | + | |
| 352 | 359 | LUA_API int lua_resume (lua_State *L, int nargs) { |
| 353 | 360 | int status; |
| 354 | 361 | lu_byte old_allowhooks; |
| 355 | 362 | lua_lock(L); |
| 363 | + if (L->ci == L->base_ci) { | |
| 364 | + if (nargs >= L->top - L->base) | |
| 365 | + return resume_error(L, "cannot resume dead coroutine"); | |
| 366 | + } | |
| 367 | + else if (!(L->ci->state & CI_YIELD)) /* not inside a yield? */ | |
| 368 | + return resume_error(L, "cannot resume non-suspended coroutine"); | |
| 356 | 369 | old_allowhooks = L->allowhook; |
| 357 | 370 | lua_assert(L->errfunc == 0 && L->nCcalls == 0); |
| 358 | 371 | status = luaD_rawrunprotected(L, resume, &nargs); |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: lgc.c,v 1.171 2003/04/03 13:35:34 roberto Exp $ | |
| 2 | +** $Id: lgc.c,v 1.171a 2003/04/03 13:35:34 roberto Exp $ | |
| 3 | 3 | ** Garbage Collector |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -110,7 +110,8 @@ static void marktmu (GCState *st) { · 104 unmodified lines | ||
| 110 | 110 | |
| 111 | 111 | |
| 112 | 112 | /* move `dead' udata that need finalization to list `tmudata' */ |
| 113 | −void luaC_separateudata (lua_State *L) { | |
| 113 | +size_t luaC_separateudata (lua_State *L) { | |
| 114 | + size_t deadmem = 0; | |
| 114 | 115 | GCObject **p = &G(L)->rootudata; |
| 115 | 116 | GCObject *curr; |
| 116 | 117 | GCObject *collected = NULL; /* to collect udata with gc event */ |
| @@ -125,6 +126,7 @@ void luaC_separateudata (lua_State *L) { · 8 unmodified lines | ||
| 125 | 126 | p = &curr->gch.next; |
| 126 | 127 | } |
| 127 | 128 | else { /* must call its gc method */ |
| 129 | + deadmem += sizeudata(gcotou(curr)->uv.len); | |
| 128 | 130 | *p = curr->gch.next; |
| 129 | 131 | curr->gch.next = NULL; /* link `curr' at the end of `collected' list */ |
| 130 | 132 | *lastcollected = curr; |
| @@ -134,6 +136,7 @@ void luaC_separateudata (lua_State *L) { · 3 unmodified lines | ||
| 134 | 136 | /* insert collected udata with gc event into `tmudata' list */ |
| 135 | 137 | *lastcollected = G(L)->tmudata; |
| 136 | 138 | G(L)->tmudata = collected; |
| 139 | + return deadmem; | |
| 137 | 140 | } |
| 138 | 141 | |
| 139 | 142 | |
| @@ -244,7 +247,7 @@ static void traversestack (GCState *st, lua_State *L1) { · 104 unmodified lines | ||
| 244 | 247 | for (ci = L1->base_ci; ci <= L1->ci; ci++) { |
| 245 | 248 | lua_assert(ci->top <= L1->stack_last); |
| 246 | 249 | lua_assert(ci->state & (CI_C | CI_HASFRAME | CI_SAVEDPC)); |
| 247 | − if (!(ci->state & CI_C) && lim < ci->top) | |
| 250 | + if (lim < ci->top) | |
| 248 | 251 | lim = ci->top; |
| 249 | 252 | } |
| 250 | 253 | for (o = L1->stack; o < L1->top; o++) |
| @@ -387,7 +390,7 @@ static void sweepstrings (lua_State *L, int all) { · 136 unmodified lines | ||
| 387 | 390 | } |
| 388 | 391 | |
| 389 | 392 | |
| 390 | −static void checkSizes (lua_State *L) { | |
| 393 | +static void checkSizes (lua_State *L, size_t deadmem) { | |
| 391 | 394 | /* check size of string hash */ |
| 392 | 395 | if (G(L)->strt.nuse < cast(ls_nstr, G(L)->strt.size/4) && |
| 393 | 396 | G(L)->strt.size > MINSTRTABSIZE*2) |
| @@ -397,7 +400,7 @@ static void checkSizes (lua_State *L) { · 3 unmodified lines | ||
| 397 | 400 | size_t newsize = luaZ_sizebuffer(&G(L)->buff) / 2; |
| 398 | 401 | luaZ_resizebuffer(L, &G(L)->buff, newsize); |
| 399 | 402 | } |
| 400 | − G(L)->GCthreshold = 2*G(L)->nblocks; /* new threshold */ | |
| 403 | + G(L)->GCthreshold = 2*G(L)->nblocks - deadmem; /* new threshold */ | |
| 401 | 404 | } |
| 402 | 405 | |
| 403 | 406 | |
| @@ -451,7 +454,8 @@ static void markroot (GCState *st, lua_State *L) { · 47 unmodified lines | ||
| 451 | 454 | } |
| 452 | 455 | |
| 453 | 456 | |
| 454 | −static void mark (lua_State *L) { | |
| 457 | +static size_t mark (lua_State *L) { | |
| 458 | + size_t deadmem; | |
| 455 | 459 | GCState st; |
| 456 | 460 | GCObject *wkv; |
| 457 | 461 | st.g = G(L); |
| @@ -464,7 +468,7 @@ static void mark (lua_State *L) { · 6 unmodified lines | ||
| 464 | 468 | wkv = st.wkv; /* keys must be cleared after preserving udata */ |
| 465 | 469 | st.wkv = NULL; |
| 466 | 470 | st.wv = NULL; |
| 467 | − luaC_separateudata(L); /* separate userdata to be preserved */ | |
| 471 | + deadmem = luaC_separateudata(L); /* separate userdata to be preserved */ | |
| 468 | 472 | marktmu(&st); /* mark `preserved' userdata */ |
| 469 | 473 | propagatemarks(&st); /* remark, to propagate `preserveness' */ |
| 470 | 474 | cleartablekeys(wkv); |
| @@ -473,13 +477,14 @@ static void mark (lua_State *L) { · 2 unmodified lines | ||
| 473 | 477 | cleartablevalues(st.wv); |
| 474 | 478 | cleartablekeys(st.wkv); |
| 475 | 479 | cleartablevalues(st.wkv); |
| 480 | + return deadmem; | |
| 476 | 481 | } |
| 477 | 482 | |
| 478 | 483 | |
| 479 | 484 | void luaC_collectgarbage (lua_State *L) { |
| 480 | − mark(L); | |
| 485 | + size_t deadmem = mark(L); | |
| 481 | 486 | luaC_sweep(L, 0); |
| 482 | − checkSizes(L); | |
| 487 | + checkSizes(L, deadmem); | |
| 483 | 488 | luaC_callGCTM(L); |
| 484 | 489 | } |
| 485 | 490 | |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: lgc.h,v 1.19 2003/02/28 19:45:15 roberto Exp $ | |
| 2 | +** $Id: lgc.h,v 1.19a 2003/02/28 19:45:15 roberto Exp $ | |
| 3 | 3 | ** Garbage Collector |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -15,7 +15,7 @@ · 9 unmodified lines | ||
| 15 | 15 | if (G(L)->nblocks >= G(L)->GCthreshold) luaC_collectgarbage(L); } |
| 16 | 16 | |
| 17 | 17 | |
| 18 | −void luaC_separateudata (lua_State *L); | |
| 18 | +size_t luaC_separateudata (lua_State *L); | |
| 19 | 19 | void luaC_callGCTM (lua_State *L); |
| 20 | 20 | void luaC_sweep (lua_State *L, int all); |
| 21 | 21 | void luaC_collectgarbage (lua_State *L); |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: lbaselib.c,v 1.130 2003/04/03 13:35:34 roberto Exp $ | |
| 2 | +** $Id: lbaselib.c,v 1.130a 2003/04/03 13:35:34 roberto Exp $ | |
| 3 | 3 | ** Basic library |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -324,7 +324,7 @@ static int luaB_xpcall (lua_State *L) { · 318 unmodified lines | ||
| 324 | 324 | |
| 325 | 325 | |
| 326 | 326 | static int luaB_tostring (lua_State *L) { |
| 327 | − char buff[64]; | |
| 327 | + char buff[128]; | |
| 328 | 328 | luaL_checkany(L, 1); |
| 329 | 329 | if (luaL_callmeta(L, 1, "__tostring")) /* is there a metafield? */ |
| 330 | 330 | return 1; /* use its value */ |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: liolib.c,v 2.39 2003/03/19 21:16:12 roberto Exp $ | |
| 2 | +** $Id: liolib.c,v 2.39a 2003/03/19 21:16:12 roberto Exp $ | |
| 3 | 3 | ** Standard I/O (and system) library |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -158,7 +158,7 @@ static int aux_close (lua_State *L) { · 152 unmodified lines | ||
| 158 | 158 | |
| 159 | 159 | |
| 160 | 160 | static int io_close (lua_State *L) { |
| 161 | − if (lua_isnone(L, 1)) { | |
| 161 | + if (lua_isnone(L, 1) && lua_type(L, lua_upvalueindex(1)) == LUA_TTABLE) { | |
| 162 | 162 | lua_pushstring(L, IO_OUTPUT); |
| 163 | 163 | lua_rawget(L, lua_upvalueindex(1)); |
| 164 | 164 | } |
| @@ -175,7 +175,7 @@ static int io_gc (lua_State *L) { · 10 unmodified lines | ||
| 175 | 175 | |
| 176 | 176 | |
| 177 | 177 | static int io_tostring (lua_State *L) { |
| 178 | − char buff[32]; | |
| 178 | + char buff[128]; | |
| 179 | 179 | FILE **f = topfile(L, 1); |
| 180 | 180 | if (*f == NULL) |
| 181 | 181 | strcpy(buff, "closed"); |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: lparser.c,v 1.208 2003/04/03 13:35:34 roberto Exp $ | |
| 2 | +** $Id: lparser.c,v 1.208a 2003/04/03 13:35:34 roberto Exp $ | |
| 3 | 3 | ** Lua Parser |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -1141,11 +1141,15 @@ static void ifstat (LexState *ls, int line) { · 1135 unmodified lines | ||
| 1141 | 1141 | |
| 1142 | 1142 | static void localfunc (LexState *ls) { |
| 1143 | 1143 | expdesc v, b; |
| 1144 | + FuncState *fs = ls->fs; | |
| 1144 | 1145 | new_localvar(ls, str_checkname(ls), 0); |
| 1145 | − init_exp(&v, VLOCAL, ls->fs->freereg++); | |
| 1146 | + init_exp(&v, VLOCAL, fs->freereg); | |
| 1147 | + luaK_reserveregs(fs, 1); | |
| 1146 | 1148 | adjustlocalvars(ls, 1); |
| 1147 | 1149 | body(ls, &b, 0, ls->linenumber); |
| 1148 | − luaK_storevar(ls->fs, &v, &b); | |
| 1150 | + luaK_storevar(fs, &v, &b); | |
| 1151 | + /* debug information will only see the variable after this point! */ | |
| 1152 | + getlocvar(fs, fs->nactvar - 1).startpc = fs->pc; | |
| 1149 | 1153 | } |
| 1150 | 1154 | |
| 1151 | 1155 | |
| @@ -13,7 +13,7 @@ T= $(BIN)/luac · 12 unmodified lines | ||
| 13 | 13 | all: $T |
| 14 | 14 | |
| 15 | 15 | $T: $(OBJS) $(LIB)/liblua.a $(LIB)/liblualib.a |
| 16 | − $(CC) -o $@ $(MYLDFLAGS) $(OBJS) -L$(LIB) -llua -llualib $(EXTRA_LIBS) | |
| 16 | + $(CC) -o $@ $(MYLDFLAGS) $(OBJS) -L$(LIB) -llua -llualib $(EXTRA_LIBS) $(DLLIB) | |
| 17 | 17 | |
| 18 | 18 | # print.c needs opcode names from lopcodes.c |
| 19 | 19 | lopcodes.o: ../lopcodes.c ../lopcodes.h |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: luac.c,v 1.44 2003/04/07 20:34:20 lhf Exp $ | |
| 2 | +** $Id: luac.c,v 1.44a 2003/04/07 20:34:20 lhf Exp $ | |
| 3 | 3 | ** Lua compiler (saves bytecodes to files; also list bytecodes) |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -182,7 +182,9 @@ int main(int argc, char* argv[]) · 176 unmodified lines | ||
| 182 | 182 | FILE* D=fopen(output,"wb"); |
| 183 | 183 | if (D==NULL) cannot(output,"open","out"); |
| 184 | 184 | if (stripping) strip(L,f); |
| 185 | + lua_lock(L); | |
| 185 | 186 | luaU_dump(L,f,writer,D); |
| 187 | + lua_unlock(L); | |
| 186 | 188 | if (ferror(D)) cannot(output,"write","out"); |
| 187 | 189 | fclose(D); |
| 188 | 190 | } |
| @@ -1,5 +1,5 @@ | ||
| 1 | 1 | /* |
| 2 | −** $Id: lvm.c,v 1.284 2003/04/03 13:35:34 roberto Exp $ | |
| 2 | +** $Id: lvm.c,v 1.284a 2003/04/03 13:35:34 roberto Exp $ | |
| 3 | 3 | ** Lua virtual machine |
| 4 | 4 | ** See Copyright Notice in lua.h |
| 5 | 5 | */ |
| @@ -66,7 +66,7 @@ int luaV_tostring (lua_State *L, StkId obj) { · 60 unmodified lines | ||
| 66 | 66 | |
| 67 | 67 | static void traceexec (lua_State *L) { |
| 68 | 68 | lu_byte mask = L->hookmask; |
| 69 | − if (mask > LUA_MASKLINE) { /* instruction-hook set? */ | |
| 69 | + if (mask & LUA_MASKCOUNT) { /* instruction-hook set? */ | |
| 70 | 70 | if (L->hookcount == 0) { |
| 71 | 71 | resethookcount(L); |
| 72 | 72 | luaD_callhook(L, LUA_HOOKCOUNT, -1); |
| @@ -399,10 +399,10 @@ StkId luaV_execute (lua_State *L) { · 326 unmodified lines | ||
| 399 | 399 | TObject *k; |
| 400 | 400 | const Instruction *pc; |
| 401 | 401 | callentry: /* entry point when calling new functions */ |
| 402 | − L->ci->u.l.pc = &pc; | |
| 403 | 402 | if (L->hookmask & LUA_MASKCALL) |
| 404 | 403 | luaD_callhook(L, LUA_HOOKCALL, -1); |
| 405 | 404 | retentry: /* entry point when returning to old functions */ |
| 405 | + L->ci->u.l.pc = &pc; | |
| 406 | 406 | lua_assert(L->ci->state == CI_SAVEDPC || |
| 407 | 407 | L->ci->state == (CI_SAVEDPC | CI_CALLING)); |
| 408 | 408 | L->ci->state = CI_HASFRAME; /* activate frame */ |
| @@ -673,9 +673,7 @@ StkId luaV_execute (lua_State *L) { · 264 unmodified lines | ||
| 673 | 673 | } |
| 674 | 674 | else { /* yes: continue its execution */ |
| 675 | 675 | int nresults; |
| 676 | − lua_assert(ci->u.l.pc == &pc && | |
| 677 | − ttisfunction(ci->base - 1) && | |
| 678 | − (ci->state & CI_SAVEDPC)); | |
| 676 | + lua_assert(ttisfunction(ci->base - 1) && (ci->state & CI_SAVEDPC)); | |
| 679 | 677 | lua_assert(GET_OPCODE(*(ci->u.l.savedpc - 1)) == OP_CALL); |
| 680 | 678 | nresults = GETARG_C(*(ci->u.l.savedpc - 1)) - 1; |
| 681 | 679 | luaD_poscall(L, nresults, ra); |