Skip to content

Commit

Permalink
i486-toBytes: toBigEndianBytes implemented
Browse files Browse the repository at this point in the history
  • Loading branch information
aslesarenko committed May 25, 2024
1 parent 2427db3 commit 02e2d06
Show file tree
Hide file tree
Showing 6 changed files with 84 additions and 56 deletions.
13 changes: 13 additions & 0 deletions core/shared/src/main/scala/sigma/VersionContext.scala
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,12 @@ case class VersionContext(activatedVersion: Byte, ergoTreeVersion: Byte) {
/** @return true, if the activated script version of Ergo protocol on the network is
* including Evolution update. */
def isV6SoftForkActivated: Boolean = activatedVersion >= V6SoftForkVersion

/** @return true if another [[VersionContext]] is greater than this. */
def <= (that: VersionContext): Boolean = {
this.activatedVersion < that.activatedVersion ||
(this.activatedVersion == that.activatedVersion && this.ergoTreeVersion <= that.ergoTreeVersion)
}
}

object VersionContext {
Expand Down Expand Up @@ -104,4 +110,11 @@ object VersionContext {
}
}

/** Returns the VersionContext with V5 activation and the given ErgoTree version. */
def sinceV5AndTreeVersion(treeVersion: Byte): VersionContext =
VersionContext(JitActivationVersion, ergoTreeVersion = treeVersion)

/** Returns the VersionContext with V6 activation and the given ErgoTree version. */
def sinceV6AndTreeVersion(treeVersion: Byte): VersionContext =
VersionContext(V6SoftForkVersion, ergoTreeVersion = treeVersion)
}
9 changes: 7 additions & 2 deletions data/shared/src/main/scala/sigma/ast/SMethod.scala
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ case class SMethod(
def invokeFixed(obj: Any, args: Array[Any]): Any = {
userDefinedInvoke match {
case Some(h) =>
h(obj, args)
h(this, obj, args)
case None =>
javaMethod.invoke(obj, args.asInstanceOf[Array[AnyRef]]:_*)
}
Expand Down Expand Up @@ -159,6 +159,11 @@ case class SMethod(
m
}

/** Create a new instance with the given user-defined invoke handler. */
def withUserDefinedInvoke(handler: SMethod.InvokeHandler): SMethod = {
copy(userDefinedInvoke = Some(handler))
}

/** Create a new instance with the given stype. */
def withSType(newSType: SFunc): SMethod = copy(stype = newSType)

Expand Down Expand Up @@ -272,7 +277,7 @@ object SMethod {
* Instances of this type can be attached to [[SMethod]] instances.
* @see SNumericTypeMethods.ToBytesMethod
*/
type InvokeHandler = (Any, Array[Any]) => Any
type InvokeHandler = (SMethod, Any, Array[Any]) => Any

/** Return [[Method]] descriptor for the given `methodName` on the given `cT` type.
* @param methodName the name of the method to lookup
Expand Down
11 changes: 10 additions & 1 deletion data/shared/src/main/scala/sigma/ast/methods.scala
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import sigma.ast.SCollection.{SBooleanArray, SBoxArray, SByteArray, SByteArray2,
import sigma.ast.SMethod.{MethodCallIrBuilder, MethodCostFunc, javaMethodOf}
import sigma.ast.SType.{TypeCode, paramT, tT}
import sigma.ast.syntax.{SValue, ValueOps}
import sigma.data.ExactIntegral.{ByteIsExactIntegral, IntIsExactIntegral, LongIsExactIntegral, ShortIsExactIntegral}
import sigma.data.OverloadHack.Overloaded1
import sigma.data.{DataValueComparer, KeyValueColl, Nullable, RType, SigmaConstants}
import sigma.eval.{CostDetails, ErgoTreeEvaluator, TracedCost}
Expand Down Expand Up @@ -230,6 +231,15 @@ object SNumericTypeMethods extends MethodsContainer {
val ToBytesMethod: SMethod = SMethod(
this, "toBytes", SFunc(tNum, SByteArray), 6, ToBytes_CostKind)
.withIRInfo(MethodCallIrBuilder)
.withUserDefinedInvoke({ (m: SMethod, obj: Any, _: Array[Any]) =>
m.objType match {
case SByteMethods => ByteIsExactIntegral.toBigEndianBytes(obj.asInstanceOf[Byte])
case SShortMethods => ShortIsExactIntegral.toBigEndianBytes(obj.asInstanceOf[Short])
case SIntMethods => IntIsExactIntegral.toBigEndianBytes(obj.asInstanceOf[Int])
case SLongMethods => LongIsExactIntegral.toBigEndianBytes(obj.asInstanceOf[Long])
case SBigIntMethods => obj.asInstanceOf[BigInt].toBytes
}
})
.withInfo(PropertyCall,
""" Returns a big-endian representation of this numeric value in a collection of bytes.
| For example, the \lst{Int} value \lst{0x12131415} would yield the
Expand Down Expand Up @@ -1547,7 +1557,6 @@ case object SGlobalMethods extends MonoTypeMethods {
def serialize_eval(mc: MethodCall, G: SigmaDslBuilder, value: SType#WrappedType)
(implicit E: ErgoTreeEvaluator): Coll[Byte] = {
// TODO v6.0: accumulate cost
CheckMinimalErgoTreeVersion(E.context.currentErgoTreeVersion, VersionContext.V6SoftForkVersion)
val t = Evaluation.stypeToRType(mc.args(0).tpe)
G.serialize(value)(t)
}
Expand Down
14 changes: 7 additions & 7 deletions sc/shared/src/test/scala/sigma/LanguageSpecificationV5.scala
Original file line number Diff line number Diff line change
Expand Up @@ -4802,7 +4802,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
}))
),
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
{ (x: Context) => x.selfBoxIndex },
{ (x: Context) => x.selfBoxIndex }, // see versioning in selfBoxIndex implementation
"{ (x: Context) => x.selfBoxIndex }",
Expand Down Expand Up @@ -5004,7 +5004,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
)
),
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
scalaFunc = { (x: Context) =>
// this error is expected in v3.x, v4.x
throw expectedError
Expand Down Expand Up @@ -5978,7 +5978,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
)
},
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
(x: Coll[Boolean]) => SigmaDsl.xorOf(x),
(x: Coll[Boolean]) => SigmaDsl.xorOf(x),
"{ (x: Coll[Boolean]) => xorOf(x) }",
Expand Down Expand Up @@ -6241,7 +6241,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
)
},
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
(x: (Coll[Byte], Coll[Byte])) => SigmaDsl.xor(x._1, x._2),
(x: (Coll[Byte], Coll[Byte])) => SigmaDsl.xor(x._1, x._2),
"{ (x: (Coll[Byte], Coll[Byte])) => xor(x._1, x._2) }",
Expand Down Expand Up @@ -8811,7 +8811,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
(Some(Long.MaxValue) -> Expected(new ArithmeticException("long overflow")))
),
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
scalaFunc = { (x: Option[Long]) =>
def f(opt: Long): Long = n.plus(opt, 1)
if (x.isDefined) f(x.get)
Expand Down Expand Up @@ -9367,7 +9367,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
)
},
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
{ (x: (Coll[Byte], Int)) =>
SigmaDsl.substConstants(x._1, Coll[Int](x._2), Coll[Any](SigmaDsl.sigmaProp(false))(sigma.AnyType))
},
Expand Down Expand Up @@ -9430,7 +9430,7 @@ class LanguageSpecificationV5 extends LanguageSpecificationBase { suite =>
)
),
changedFeature(
changedInVersion = VersionContext.JitActivationVersion,
changedInVersion = VersionContext.sinceV5AndTreeVersion(0),
{ (x: Context) =>
throw error
true
Expand Down
70 changes: 35 additions & 35 deletions sc/shared/src/test/scala/sigma/LanguageSpecificationV6.scala
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
Map()
)
),
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
}

property("Global.serialize[Byte]") {
Expand Down Expand Up @@ -76,7 +76,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>

property("Boolean.toByte") {
val toByte = newFeature((x: Boolean) => x.toByte, "{ (x: Boolean) => x.toByte }",
sinceVersion = VersionContext.V6SoftForkVersion
sinceVersion = VersionContext.sinceV6AndTreeVersion(0)
)

val cases = Seq(
Expand All @@ -102,22 +102,22 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
// which is checked below

lazy val toAbs = newFeature((x: Byte) => x.toAbs, "{ (x: Byte) => x.toAbs }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val compareTo = newFeature(
(x: (Byte, Byte)) => x._1.compareTo(x._2),
"{ (x: (Byte, Byte)) => x._1.compareTo(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitOr = newFeature(
{ (x: (Byte, Byte)) => (x._1 | x._2).toByteExact },
"{ (x: (Byte, Byte)) => (x._1 | x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitAnd = newFeature(
{ (x: (Byte, Byte)) => (x._1 & x._2).toByteExact },
"{ (x: (Byte, Byte)) => (x._1 & x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

forAll { x: Byte =>
Seq(toAbs).foreach(f => f.checkEquality(x))
Expand All @@ -136,21 +136,21 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
// which is checked below

lazy val toAbs = newFeature((x: Short) => x.toAbs, "{ (x: Short) => x.toAbs }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val compareTo = newFeature((x: (Short, Short)) => x._1.compareTo(x._2),
"{ (x: (Short, Short)) => x._1.compareTo(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitOr = newFeature(
{ (x: (Short, Short)) => (x._1 | x._2).toShortExact },
"{ (x: (Short, Short)) => x._1 | x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitAnd = newFeature(
{ (x: (Short, Short)) => (x._1 & x._2).toShortExact },
"{ (x: (Short, Short)) => x._1 & x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

forAll { x: Short =>
Seq(toAbs).foreach(_.checkEquality(x))
Expand All @@ -166,18 +166,18 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
// NOTE, for such versions the new features are not supported
// which is checked below
lazy val toAbs = newFeature((x: Int) => x.toAbs, "{ (x: Int) => x.toAbs }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val compareTo = newFeature((x: (Int, Int)) => x._1.compareTo(x._2),
"{ (x: (Int, Int)) => x._1.compareTo(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val bitOr = newFeature(
{ (x: (Int, Int)) => x._1 | x._2 },
"{ (x: (Int, Int)) => x._1 | x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val bitAnd = newFeature(
{ (x: (Int, Int)) => x._1 & x._2 },
"{ (x: (Int, Int)) => x._1 & x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
forAll { x: Int =>
Seq(toAbs).foreach(_.checkEquality(x))
}
Expand All @@ -192,20 +192,20 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
// NOTE, for such versions the new features are not supported
// which is checked below
lazy val toAbs = newFeature((x: Long) => x.toAbs, "{ (x: Long) => x.toAbs }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val compareTo = newFeature((x: (Long, Long)) => x._1.compareTo(x._2),
"{ (x: (Long, Long)) => x._1.compareTo(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitOr = newFeature(
{ (x: (Long, Long)) => x._1 | x._2 },
"{ (x: (Long, Long)) => x._1 | x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

lazy val bitAnd = newFeature(
{ (x: (Long, Long)) => x._1 & x._2 },
"{ (x: (Long, Long)) => x._1 & x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

forAll { x: Long =>
Seq(toAbs).foreach(_.checkEquality(x))
Expand Down Expand Up @@ -240,30 +240,30 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
val toByte = newFeature((x: BigInt) => x.toByte,
"{ (x: BigInt) => x.toByte }",
FuncValue(Vector((1, SBigInt)), Downcast(ValUse(1, SBigInt), SByte)),
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
val toShort = newFeature((x: BigInt) => x.toShort,
"{ (x: BigInt) => x.toShort }",
FuncValue(Vector((1, SBigInt)), Downcast(ValUse(1, SBigInt), SShort)),
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
val toInt = newFeature((x: BigInt) => x.toInt,
"{ (x: BigInt) => x.toInt }",
FuncValue(Vector((1, SBigInt)), Downcast(ValUse(1, SBigInt), SInt)),
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
val toLong = newFeature((x: BigInt) => x.toLong,
"{ (x: BigInt) => x.toLong }",
FuncValue(Vector((1, SBigInt)), Downcast(ValUse(1, SBigInt), SLong)),
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val toAbs = newFeature((x: BigInt) => x.toAbs, "{ (x: BigInt) => x.toAbs }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val compareTo = newFeature((x: (BigInt, BigInt)) => x._1.compareTo(x._2),
"{ (x: (BigInt, BigInt)) => x._1.compareTo(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val bitOr = newFeature({ (x: (BigInt, BigInt)) => x._1 | x._2 },
"{ (x: (BigInt, BigInt)) => x._1 | x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
lazy val bitAnd = newFeature({ (x: (BigInt, BigInt)) => x._1 & x._2 },
"{ (x: (BigInt, BigInt)) => x._1 & x._2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

forAll { x: BigInt =>
Seq(toByte, toShort, toInt, toLong, toAbs).foreach(_.checkEquality(x))
Expand All @@ -278,7 +278,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
// TODO v6.0: related to https://github.com/ScorexFoundation/sigmastate-interpreter/issues/416
val getReg = newFeature((x: Box) => x.getReg[Int](1).get,
"{ (x: Box) => x.getReg[Int](1).get }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -294,7 +294,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
property("Coll find method equivalence") {
val find = newFeature((x: Coll[Int]) => x.find({ (v: Int) => v > 0 }),
"{ (x: Coll[Int]) => x.find({ (v: Int) => v > 0} ) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -313,7 +313,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
if (x.size > 2) x.slice(0, x.size - 2) else Colls.emptyColl[Boolean]
},
"{ (x: Coll[Boolean]) => x >> 2 }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -329,7 +329,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
property("Coll diff methods equivalence") {
val diff = newFeature((x: (Coll[Int], Coll[Int])) => x._1.diff(x._2),
"{ (x: (Coll[Int], Coll[Int])) => x._1.diff(x._2) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -346,7 +346,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
val n = ExactNumeric.LongIsExactNumeric
val fold = newFeature({ (x: Option[Long]) => x.fold(5.toLong)( (v: Long) => n.plus(v, 1) ) },
"{ (x: Option[Long]) => x.fold(5, { (v: Long) => v + 1 }) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -362,7 +362,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
property("allZK equivalence") {
lazy val allZK = newFeature((x: Coll[SigmaProp]) => SigmaDsl.allZK(x),
"{ (x: Coll[SigmaProp]) => allZK(x) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand All @@ -378,7 +378,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
property("anyZK equivalence") {
lazy val anyZK = newFeature((x: Coll[SigmaProp]) => SigmaDsl.anyZK(x),
"{ (x: Coll[SigmaProp]) => anyZK(x) }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))

if (activatedVersionInTests < VersionContext.V6SoftForkVersion) {
// NOTE, for such versions getReg is not supported
Expand Down Expand Up @@ -442,7 +442,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
}
),
changedFeature(
changedInVersion = VersionContext.V6SoftForkVersion,
changedInVersion = VersionContext.sinceV6AndTreeVersion(0),
{ (x: (Coll[Byte], Int)) =>
SigmaDsl.substConstants(x._1, Coll[Int](x._2), Coll[Any](SigmaDsl.sigmaProp(false))(sigma.AnyType))
},
Expand Down Expand Up @@ -479,7 +479,7 @@ class LanguageSpecificationV6 extends LanguageSpecificationBase { suite =>
lazy val toBytes = newFeature(
{ (x: Byte) => x.toBigEndianBytes },
"{ (x: Byte) => x.toBytes }",
sinceVersion = VersionContext.V6SoftForkVersion)
sinceVersion = VersionContext.sinceV6AndTreeVersion(0))
val cases = Seq(
(0.toByte, Success(Coll(0.toByte))),
(1.toByte, Success(Coll(1.toByte)))
Expand Down
Loading

0 comments on commit 02e2d06

Please sign in to comment.