summaryrefslogtreecommitdiff
path: root/src/lfunc.js
diff options
context:
space:
mode:
authordaurnimator <quae@daurnimator.com>2017-05-29 13:28:24 +1000
committerdaurnimator <quae@daurnimator.com>2017-05-29 13:43:11 +1000
commitb3f5b92b221c0ad8a94b8cb95081bb85d235c39f (patch)
treeddfacca952778520fe74976a88bd97b3cdb68785 /src/lfunc.js
parent587b5c78d193426410c45c6f055272acf4a8bc7c (diff)
downloadfengari-b3f5b92b221c0ad8a94b8cb95081bb85d235c39f.tar.gz
fengari-b3f5b92b221c0ad8a94b8cb95081bb85d235c39f.tar.bz2
fengari-b3f5b92b221c0ad8a94b8cb95081bb85d235c39f.zip
Have lua closures point to directly to their upvalues on stack
Diffstat (limited to 'src/lfunc.js')
-rw-r--r--src/lfunc.js39
1 files changed, 18 insertions, 21 deletions
diff --git a/src/lfunc.js b/src/lfunc.js
index 663f614..97e5f02 100644
--- a/src/lfunc.js
+++ b/src/lfunc.js
@@ -30,19 +30,14 @@ class Proto {
class UpVal {
constructor() {
- this.L = null; /* Keep track of the thread it comes from */
- this.v = null; /* if open: stack index. if closed: null (find it in this.value) */
- this.open_next = null; /* linked list (when open) */
+ this.v = void 0; /* if open: reference to TValue on stack. if closed: TValue */
+ this.vOff = void 0; /* if open: index on stack. if closed: undefined */
this.refcount = 0;
- this.value = null; /* the TValue (when closed) */
- }
-
- val() {
- return this.v !== null ? this.L.stack[this.v] : this.value;
+ this.open_next = null; /* linked list (when open) */
}
isopen() {
- return this.v !== null;
+ return this.vOff !== void 0;
}
}
@@ -56,9 +51,9 @@ const luaF_newLclosure = function(L, n) {
const luaF_findupval = function(L, level) {
let prevp;
let p = L.openupval;
- while (p !== null && p.v >= level) {
+ while (p !== null && p.vOff >= level) {
assert(p.isopen());
- if (p.v === level) /* found a corresponding upvalue? */
+ if (p.vOff === level) /* found a corresponding upvalue? */
return p; /* return it */
prevp = p;
p = p.open_next;
@@ -71,23 +66,25 @@ const luaF_findupval = function(L, level) {
prevp.open_next = uv;
else
L.openupval = uv;
- /* current value lives in the stack */
- uv.L = L;
- uv.v = level;
+ uv.v = L.stack[level]; /* current value lives in the stack */
+ uv.vOff = level;
return uv;
};
const luaF_close = function(L, level) {
- while (L.openupval !== null && L.openupval.v >= level) {
+ while (L.openupval !== null && L.openupval.vOff >= level) {
let uv = L.openupval;
assert(uv.isopen());
L.openupval = uv.open_next; /* remove from 'open' list */
- if (uv.refcount > 0) {
- let from = uv.L.stack[uv.v];
- uv.L = null;
- uv.v = null;
- uv.value = new lobject.TValue(from.type, from.value);
+ if (uv.refcount === 0) { /* no references? */
+ /* free upvalue */
+ uv.v = void 0;
+ uv.open_next = null;
+ } else {
+ let from = uv.v;
+ uv.v = new lobject.TValue(from.type, from.value);
}
+ uv.vOff = void 0;
}
};
@@ -98,7 +95,7 @@ const luaF_initupvals = function(L, cl) {
for (let i = 0; i < cl.nupvalues; i++) {
let uv = new UpVal(L);
uv.refcount = 1;
- uv.value = new lobject.TValue(CT.LUA_TNIL, null);
+ uv.v = new lobject.TValue(CT.LUA_TNIL, null);
cl.upvals[i] = uv;
}
};