Simplify and fix upvalue implementation.

This commit is contained in:
James Roseborough
2009-11-09 15:16:38 +00:00
parent 7cc18046ab
commit b45bc98b37
3 changed files with 33 additions and 70 deletions

View File

@@ -30,7 +30,6 @@ public class LuaClosure extends LuaFunction {
public final Prototype p;
public final UpValue[] upValues;
private UpValue openUpValues = null;
LuaClosure() {
p = null;
@@ -43,6 +42,12 @@ public class LuaClosure extends LuaFunction {
this.upValues = p.nups>0? new UpValue[p.nups]: NOUPVALUES;
}
protected LuaClosure(int nupvalues, LuaValue env) {
super( env );
this.p = null;
this.upValues = nupvalues>0? new UpValue[nupvalues]: NOUPVALUES;
}
public boolean isclosure() {
return true;
}
@@ -103,7 +108,7 @@ public class LuaClosure extends LuaFunction {
return execute(stack,p.is_vararg!=0? varargs.subargs(p.numparams+1): NONE);
}
private final Varargs execute( LuaValue[] stack, Varargs varargs ) {
protected Varargs execute( LuaValue[] stack, Varargs varargs ) {
// loop through instructions
int i,a,b,c,pc=0,top=0;
LuaValue o;
@@ -111,6 +116,9 @@ public class LuaClosure extends LuaFunction {
int[] code = p.code;
LuaValue[] k = p.k;
// upvalues are only possible when closures create closures
UpValue[] openups = p.p.length>0? new UpValue[stack.length]: null;
// create varargs "arg" table
if ( p.is_vararg >= Lua.VARARG_NEEDSARG )
stack[p.numparams] = new LuaTable(varargs);
@@ -319,7 +327,6 @@ public class LuaClosure extends LuaFunction {
}
case Lua.OP_RETURN: /* A B return R(A), ... ,R(A+B-2) (see note) */
closeUpValues();
b = i>>>23;
switch ( b ) {
case 0: return varargsOf(stack, a, top-v.narg()-a, v);
@@ -394,7 +401,11 @@ public class LuaClosure extends LuaFunction {
continue;
case Lua.OP_CLOSE: /* A close all variables in the stack up to (>=) R(A)*/
closeUpValues( a );
for ( b=openups.length; --b>=a; )
if ( openups[b]!=null ) {
openups[b].close();
openups[b] = null;
}
continue;
case Lua.OP_CLOSURE: /* A Bx R(A):= closure(KPROTO[Bx], R(A), ... ,R(A+n)) */
@@ -407,7 +418,7 @@ public class LuaClosure extends LuaFunction {
b = i>>>23;
newcl.upValues[j] = (i&4) != 0?
upValues[b]:
findUpValue(stack,b);
openups[b]!=null? openups[b]: (openups[b]=new UpValue(stack,b));
}
stack[a] = newcl;
}
@@ -436,56 +447,20 @@ public class LuaClosure extends LuaFunction {
throw le;
} finally {
LuaThread.onReturn();
}
}
// TODO: inline, optimize when targs come in ascending order?
UpValue findUpValue(LuaValue[] stack, int target) {
UpValue prev=null,up=openUpValues;
while ( up != null ) {
if (up.index == target) {
return up;
} else if (up.index < target) {
break;
}
up = (prev=up).next;
}
up = new UpValue(stack, target, up);
if ( prev!=null )
prev.next = up;
else
this.openUpValues = up;
return up;
}
// TODO: inline?
void closeUpValues(int limit) {
UpValue prev=null,up=openUpValues;
while ( up != null ) {
UpValue next = up.next;
if ( up.close(limit) ) {
if ( prev==null )
this.openUpValues = up.next;
else
prev.next = up.next;
up.next = null;
} else {
prev = up;
}
up = next;
if ( openups != null )
for ( int u=openups.length; --u>=0; )
if ( openups[u] != null )
openups[u].close();
}
}
// TODO: inline?
void closeUpValues() {
UpValue up=openUpValues;
while ( up != null ) {
UpValue next = up.next;
up.close(-1);
up.next = null;
up = next;
}
openUpValues = null;
protected LuaValue getUpvalue(int i) {
return upValues[i].getValue();
}
protected void setUpvalue(int i, LuaValue v) {
upValues[i].setValue(v);
}
}

View File

@@ -27,17 +27,14 @@ public final class UpValue {
LuaValue[] array; // initially the stack, becomes a holder
int index;
boolean closed;
UpValue next = null;
public UpValue( LuaValue[] stack, int index, UpValue next ) {
public UpValue( LuaValue[] stack, int index) {
this.array = stack;
this.index = index;
this.next = next;
}
public String toString() {
return (closed? "-": "+") + array[index];
return array[index].toString();
}
public final LuaValue getValue() {
@@ -48,17 +45,8 @@ public final class UpValue {
array[index] = value;
}
public final boolean close( int limit ) {
if ( (!closed) && (index>=limit) ) {
array = new LuaValue[] { array[index] };
index = 0;
return (closed = true);
} else {
return false;
}
}
public final boolean isClosed() {
return closed;
public final void close() {
array = new LuaValue[] { array[index] };
index = 0;
}
}

View File

@@ -1,2 +1,2 @@
# on the way to version 2.0
version: 1.9.52
version: 1.9.53