diff --git a/convex-core/src/main/java/convex/core/cvm/AOp.java b/convex-core/src/main/java/convex/core/cvm/AOp.java index 87d392d3c..136b6b3ab 100644 --- a/convex-core/src/main/java/convex/core/cvm/AOp.java +++ b/convex-core/src/main/java/convex/core/cvm/AOp.java @@ -51,13 +51,6 @@ public ACell toCanonical() { return this; } - /** - * Returns the opcode for this op - * - * @return Opcode as a byte - */ - public abstract byte opCode(); - @Override public final int encode(byte[] bs, int pos) { bs[pos++]=getTag(); @@ -70,6 +63,10 @@ public int encodeRaw(byte[] bs, int pos) { return encodeAfterOpcode(bs,pos); } + protected byte opCode() { + return 0; + } + /** * Writes the raw data for this Op to the specified bytebuffer. Assumes Op tag * and opcode already written. diff --git a/convex-core/src/main/java/convex/core/cvm/Ops.java b/convex-core/src/main/java/convex/core/cvm/Ops.java index 9374048c1..2c16f8e68 100644 --- a/convex-core/src/main/java/convex/core/cvm/Ops.java +++ b/convex-core/src/main/java/convex/core/cvm/Ops.java @@ -22,14 +22,10 @@ public class Ops { public static final byte TRY = 3; public static final byte LET = 4; public static final byte LOOP = 5; - public static final byte DEF = 6; public static final byte LOOKUP = 7; public static final byte LAMBDA = 8; public static final byte QUERY = 9; - public static final byte LOCAL=10; - public static final byte SET = 11; - public static final byte SPECIAL = 15; // public static final byte CALL = 9; // public static final byte RETURN = 10; @@ -59,14 +55,16 @@ public static AOp read(byte tag, Blob b, int pos) throws Ba case Ops.LOOKUP: return Lookup.read(b,pos); case CVMTag.OPCODE_LAMBDA: - return (AOp) Lambda.read(b,pos); + return (AOp) Lambda.read(b,pos); case Ops.LET: return Let.read(b,pos,false); case Ops.QUERY: return Query.read(b,pos); case Ops.LOOP: return Let.read(b,pos,true); - case Ops.SET: + + // These tags mean we must have a Long integer, which resolves to a Set operation + case 0x10: case 0x11: case 0x12: case 0x13: case 0x14: case 0x15: case 0x16: case 0x17: case 0x18: return Set.read(b,pos); default: diff --git a/convex-core/src/main/java/convex/core/cvm/ops/Def.java b/convex-core/src/main/java/convex/core/cvm/ops/Def.java index 48a56bcf1..9b37292d0 100644 --- a/convex-core/src/main/java/convex/core/cvm/ops/Def.java +++ b/convex-core/src/main/java/convex/core/cvm/ops/Def.java @@ -4,7 +4,6 @@ import convex.core.cvm.CVMTag; import convex.core.cvm.Context; import convex.core.cvm.Juice; -import convex.core.cvm.Ops; import convex.core.cvm.Syntax; import convex.core.data.ACell; import convex.core.data.Blob; @@ -100,11 +99,6 @@ public boolean print(BlobBuilder sb, long limit) { return sb.check(limit); } - @Override - public byte opCode() { - return Ops.DEF; - } - @Override public int estimatedEncodingSize() { return 100; diff --git a/convex-core/src/main/java/convex/core/cvm/ops/Local.java b/convex-core/src/main/java/convex/core/cvm/ops/Local.java index 2576ead5a..27b87f90b 100644 --- a/convex-core/src/main/java/convex/core/cvm/ops/Local.java +++ b/convex-core/src/main/java/convex/core/cvm/ops/Local.java @@ -5,7 +5,6 @@ import convex.core.cvm.CVMTag; import convex.core.cvm.Context; import convex.core.cvm.Juice; -import convex.core.cvm.Ops; import convex.core.data.ACell; import convex.core.data.AVector; import convex.core.data.Format; @@ -55,11 +54,6 @@ public Context execute(Context ctx) { T result = (T)env.get(position); return ctx.withResult(Juice.LOOKUP,result); } - - @Override - public byte opCode() { - return Ops.LOCAL; - } @Override public byte getTag() { diff --git a/convex-core/src/main/java/convex/core/cvm/ops/Set.java b/convex-core/src/main/java/convex/core/cvm/ops/Set.java index c001fc1c0..95f7591d2 100644 --- a/convex-core/src/main/java/convex/core/cvm/ops/Set.java +++ b/convex-core/src/main/java/convex/core/cvm/ops/Set.java @@ -2,6 +2,7 @@ import convex.core.ErrorCodes; import convex.core.cvm.AOp; +import convex.core.cvm.CVMTag; import convex.core.cvm.Context; import convex.core.cvm.Juice; import convex.core.cvm.Ops; @@ -10,33 +11,31 @@ import convex.core.data.Blob; import convex.core.data.Cells; import convex.core.data.Format; -import convex.core.data.IRefFunction; import convex.core.data.Ref; +import convex.core.data.prim.CVMLong; import convex.core.data.util.BlobBuilder; import convex.core.exceptions.BadFormatException; import convex.core.exceptions.InvalidDataException; -import convex.core.util.ErrorMessages; /** * Op to set a lexical value in the local execution context. i.e. `set!` * * @param Result type of Op */ -public class Set extends AOp { +public class Set extends ACodedOp> { /** * Stack position in lexical stack */ private final long position; - /** - * Op to compute new value - */ - private final Ref> op; - + public Set(Ref code, Ref> value) { + super(CVMTag.OP_CODED,code,value); + this.position = code.getValue().longValue(); // safe because always embedded + } + private Set(long position, Ref> op) { - this.position = position; - this.op = op; + this(CVMLong.create(position).getRef(),op); } /** @@ -59,7 +58,7 @@ public Context execute(Context ctx) { return ctx.withError(ErrorCodes.BOUNDS, "Bad position for set!: " + position); } - ctx = ctx.execute(op.getValue()); + ctx = ctx.execute(value.getValue()); if (ctx.isExceptional()) return ctx; ACell value = ctx.getResult(); @@ -68,18 +67,6 @@ public Context execute(Context ctx) { return ctx.consumeJuice(Juice.SET_BANG); } - @Override - public byte opCode() { - return Ops.SET; - } - - @Override - public int encodeAfterOpcode(byte[] bs, int pos) { - pos = Format.writeVLQLong(bs, pos, position); - pos = op.encode(bs,pos); - return pos; - } - /** * Reads a Set Op from a Blob encoding * @@ -103,44 +90,27 @@ public static Set read(Blob b, int pos) throws BadFormatExc return result; } - @Override - public Set updateRefs(IRefFunction func) { - @SuppressWarnings("unchecked") - Ref> newOp = (Ref>) func.apply(op); - if (op == newOp) return this; - return new Set(position, newOp); - } - @Override public void validateCell() throws InvalidDataException { - if (op == null) { - throw new InvalidDataException("Null Set op ", this); - } if (position < 0) { throw new InvalidDataException("Invalid Local position " + position, this); } } - @Override - public int getRefCount() { - return 1; - } - - @SuppressWarnings("unchecked") - @Override - public Ref> getRef(int i) { - if (i != 0) throw new IndexOutOfBoundsException(ErrorMessages.badIndex(i)); - return op; - } - @Override public boolean print(BlobBuilder sb, long limit) { sb.append("(set! %"); sb.append(Long.toString(position)); sb.append(' '); - if (!op.getValue().print(sb, limit)) return false; + if (!value.getValue().print(sb, limit)) return false; sb.append(')'); return sb.check(limit); } + @Override + protected AOp rebuild(Ref newCode, Ref> newValue) { + if ((newCode==code)&&(newValue==value)) return this; + return new Set(newCode,newValue); + } + } diff --git a/convex-core/src/main/java/convex/core/cvm/ops/Special.java b/convex-core/src/main/java/convex/core/cvm/ops/Special.java index 92028dbff..9a18602c3 100644 --- a/convex-core/src/main/java/convex/core/cvm/ops/Special.java +++ b/convex-core/src/main/java/convex/core/cvm/ops/Special.java @@ -147,11 +147,6 @@ public Context execute(Context ctx) { } return ctx.consumeJuice(Juice.SPECIAL); } - - @Override - public byte opCode() { - return Ops.SPECIAL; - } @Override public byte getTag() { diff --git a/convex-core/src/test/java/convex/core/lang/OpsTest.java b/convex-core/src/test/java/convex/core/lang/OpsTest.java index 405d3ae27..bc34e4fb7 100644 --- a/convex-core/src/test/java/convex/core/lang/OpsTest.java +++ b/convex-core/src/test/java/convex/core/lang/OpsTest.java @@ -213,7 +213,7 @@ public void testSpecial() { @Test public void testSet() throws BadFormatException { AOp
op = Set.create(45, Constant.nil()); - Blob expectedEncoding=Blob.fromHex("c00b2dc0b000"); + Blob expectedEncoding=Blob.fromHex("c0112dc0b000"); assertEquals(expectedEncoding,op.getEncoding()); assertEquals(op,Format.read(expectedEncoding)); doOpTest(op);