Skip to content

Commit

Permalink
improving UnsignedBigInt support in JS
Browse files Browse the repository at this point in the history
  • Loading branch information
kushti committed Nov 1, 2024
1 parent 2d8af9d commit 933b2cc
Show file tree
Hide file tree
Showing 16 changed files with 49 additions and 43 deletions.
3 changes: 3 additions & 0 deletions core/js/src/main/scala/sigma/js/Type.scala
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ object Type extends js.Object {
/** Descriptor of ErgoScript type BigInt. */
val BigInt = new Type(sigma.BigIntRType)

/** Descriptor of ErgoScript type BigInt. */
val UnsignedBigInt = new Type(sigma.UnsignedBigIntRType)

/** Descriptor of ErgoScript type GroupElement. */
val GroupElement = new Type(sigma.GroupElementRType)

Expand Down
5 changes: 3 additions & 2 deletions core/shared/src/main/scala/sigma/data/CBigInt.scala
Original file line number Diff line number Diff line change
Expand Up @@ -69,9 +69,9 @@ case class CBigInt(override val wrappedValue: BigInteger) extends BigInt with Wr
}
}

/** A default implementation of [[BigInt]] interface.
/** A default implementation of [[UnsignedBigInt]] interface.
*
* @see [[BigInt]] for detailed descriptions
* @see [[UnsignedBigInt]] for detailed descriptions
*/
case class CUnsignedBigInt(override val wrappedValue: BigInteger) extends UnsignedBigInt with WrapperOf[BigInteger] {

Expand Down Expand Up @@ -144,4 +144,5 @@ case class CUnsignedBigInt(override val wrappedValue: BigInteger) extends Unsign
override def toSigned(): BigInt = {
CBigInt(wrappedValue.toSignedBigIntValueExact)
}

}
2 changes: 1 addition & 1 deletion core/shared/src/main/scala/sigma/package.scala
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ package object sigma {
implicit val StringType : RType[String] = GeneralType(StringClassTag)

implicit val BigIntRType : RType[BigInt] = GeneralType(BigIntClassTag)
implicit val UnsignedBigIntRType : RType[UnsignedBigInt] = GeneralType(UnsignedBigIntClassTag)
implicit val UnsignedBigIntRType : RType[UnsignedBigInt] = GeneralType(UnsignedBigIntClassTag)
implicit val GroupElementRType: RType[GroupElement] = GeneralType(GroupElementClassTag)
implicit val SigmaPropRType : RType[SigmaProp] = GeneralType(SigmaPropClassTag)
implicit val SigmaBooleanRType: RType[SigmaBoolean] = GeneralType(SigmaBooleanClassTag)
Expand Down
35 changes: 18 additions & 17 deletions core/shared/src/main/scala/sigma/reflection/ReflectionData.scala
Original file line number Diff line number Diff line change
Expand Up @@ -130,44 +130,45 @@ object ReflectionData {
}
{
val clazz = classOf[sigma.UnsignedBigInt]
val paramTypes = Array[Class[_]](clazz)
val oneParamTypes = Array[Class[_]](clazz)
val twoParamTypes = Array[Class[_]](clazz, clazz)
registerClassEntry(clazz,
methods = Map(
mkMethod(clazz, "add", paramTypes) { (obj, args) =>
mkMethod(clazz, "add", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].add(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "max", paramTypes) { (obj, args) =>
mkMethod(clazz, "max", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].max(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "min", paramTypes) { (obj, args) =>
mkMethod(clazz, "min", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].min(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "subtract", paramTypes) { (obj, args) =>
mkMethod(clazz, "subtract", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].subtract(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "multiply", paramTypes) { (obj, args) =>
mkMethod(clazz, "multiply", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].multiply(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "mod", paramTypes) { (obj, args) =>
mkMethod(clazz, "mod", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].mod(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "divide", paramTypes) { (obj, args) =>
mkMethod(clazz, "divide", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].divide(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "plusMod", paramTypes) { (obj, args) =>
mkMethod(clazz, "mod", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].mod(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "modInverse", oneParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].modInverse(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "plusMod", twoParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].plusMod(args(0).asInstanceOf[UnsignedBigInt], args(1).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "subtractMod", paramTypes) { (obj, args) =>
mkMethod(clazz, "subtractMod", twoParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].subtractMod(args(0).asInstanceOf[UnsignedBigInt], args(1).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "multiplyMod", paramTypes) { (obj, args) =>
mkMethod(clazz, "multiplyMod", twoParamTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].multiplyMod(args(0).asInstanceOf[UnsignedBigInt], args(1).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "mod", paramTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].mod(args(0).asInstanceOf[UnsignedBigInt])
},
mkMethod(clazz, "modInverse", paramTypes) { (obj, args) =>
obj.asInstanceOf[UnsignedBigInt].modInverse(args(0).asInstanceOf[UnsignedBigInt])
}
)
)
Expand Down
2 changes: 2 additions & 0 deletions data/js/src/main/scala/sigma/js/Value.scala
Original file line number Diff line number Diff line change
Expand Up @@ -164,6 +164,8 @@ object Value extends js.Object {
n
case sigma.BigIntRType =>
data.asInstanceOf[js.BigInt]
case sigma.UnsignedBigIntRType =>
data.asInstanceOf[js.BigInt]
case sigma.GroupElementRType =>
data.asInstanceOf[GroupElement]
case sigma.SigmaPropRType =>
Expand Down
5 changes: 2 additions & 3 deletions data/shared/src/main/scala/sigma/ast/methods.scala
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ package sigma.ast
import org.ergoplatform._
import org.ergoplatform.validation._
import sigma.Evaluation.stypeToRType
import sigma._
import sigma.{UnsignedBigInt, _}
import sigma.ast.SCollection.{SBooleanArray, SBoxArray, SByteArray, SByteArray2, SHeaderArray}
import sigma.ast.SMethod.{MethodCallIrBuilder, MethodCostFunc, javaMethodOf}
import sigma.ast.SType.TypeCode
Expand Down Expand Up @@ -536,7 +536,6 @@ case object SUnsignedBigIntMethods extends SNumericTypeMethods {
final val ToNBitsCostInfo = OperationCostInfo(
FixedCost(JitCost(5)), NamedDesc("NBitsMethodCall"))


// todo: costing
final val ModInverseCostInfo = ToNBitsCostInfo

Expand Down Expand Up @@ -1008,7 +1007,7 @@ object SCollectionMethods extends MethodsContainer with MethodByNameUnapply {
| \lst{f} to each element of this collection and concatenating the results.
""".stripMargin, ArgInfo("f", "the function to apply to each element."))

/** We assume all flatMap body patterns have similar executon cost. */
/** We assume all flatMap body patterns have similar execution cost. */
final val CheckFlatmapBody_Info = OperationCostInfo(
PerItemCost(baseCost = JitCost(20), perChunkCost = JitCost(20), chunkSize = 1),
NamedDesc("CheckFlatmapBody"))
Expand Down
9 changes: 6 additions & 3 deletions data/shared/src/main/scala/sigma/data/CSigmaDslBuilder.scala
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,8 @@ import org.ergoplatform.ErgoBox
import org.ergoplatform.validation.ValidationRules
import scorex.crypto.hash.{Blake2b256, Sha256}
import scorex.utils.{Ints, Longs}
import sigma.ast.{AtLeast, SBigInt, SubstConstants}
import sigma.ast.{AtLeast, SBigInt, SType, SUnsignedBigInt, SubstConstants}
import scorex.utils.Longs
import sigma.ast.{AtLeast, SType, SubstConstants}
import sigma.crypto.{CryptoConstants, EcPointType, Ecp}
import sigma.eval.Extensions.EvalCollOps
import sigma.serialization.{DataSerializer, GroupElementSerializer, SigmaSerializer}
Expand Down Expand Up @@ -235,7 +234,11 @@ class CSigmaDslBuilder extends SigmaDslBuilder { dsl =>
throw SerializerException(s"BigInt value doesn't not fit into ${SBigInt.MaxSizeInBytes} bytes in fromBigEndianBytes")
}
CBigInt(new BigInteger(bytes.toArray).toSignedBigIntValueExact).asInstanceOf[T]
// todo: UnsignedBitInt
case sigma.UnsignedBigIntRType =>
if (bytes.length > SUnsignedBigInt.MaxSizeInBytes) {
throw SerializerException(s"BigInt value doesn't not fit into ${SBigInt.MaxSizeInBytes} bytes in fromBigEndianBytes")
}
CUnsignedBigInt(new BigInteger(bytes.toArray).toSignedBigIntValueExact).asInstanceOf[T]
case _ => throw new IllegalArgumentException("Unsupported type provided in fromBigEndianBytes")
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,7 @@ object DataValueComparer {
val descriptors: AVHashMap[RType[_], (OperationCostInfo[FixedCost], OperationCostInfo[PerItemCost])] =
AVHashMap.fromSeq(Array[(RType[_], (OperationCostInfo[FixedCost], OperationCostInfo[PerItemCost]))](
(BigIntRType, (EQ_BigInt, EQ_COA_BigInt)),
(UnsignedBigIntRType, (EQ_BigInt, EQ_COA_BigInt)),
(GroupElementRType, (EQ_GroupElement, EQ_COA_GroupElement)),
(AvlTreeRType, (EQ_AvlTree, EQ_COA_AvlTree)),
(BoxRType, (EQ_Box, EQ_COA_Box)),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,7 @@ object OpCodes {
val OptionIsDefinedCode: OpCode = newOpCode(118)

// Modular arithmetic operations codes
// todo: remove?
val ModQCode : OpCode = newOpCode(119)
val PlusModQCode : OpCode = newOpCode(120)
val MinusModQCode: OpCode = newOpCode(121)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ trait ContractSyntax { contract: SigmaContract =>
case _: String => StringType
case _: Unit => UnitType
case _: sigma.BigInt => BigIntRType
case _: sigma.BigInt => UnsignedBigIntRType
case _: GroupElement => GroupElementRType
case _: ErgoBox => syntax.ErgoBoxRType // TODO remove this RType
case _: Box => BoxRType
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -145,13 +145,13 @@ object GraphIRReflection {
mkMethod(clazz, "divide", Array[Class[_]](classOf[Base#Ref[_]])) { (obj, args) =>
obj.asInstanceOf[ctx.UnsignedBigInt].divide(args(0).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]])
},
mkMethod(clazz, "plusMod", Array[Class[_]](classOf[Base#Ref[_]])) { (obj, args) =>
mkMethod(clazz, "plusMod", Array[Class[_]](classOf[Base#Ref[_]], classOf[Base#Ref[_]])) { (obj, args) =>
obj.asInstanceOf[ctx.UnsignedBigInt].plusMod(args(0).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]], args(1).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]])
},
mkMethod(clazz, "subtractMod", Array[Class[_]](classOf[Base#Ref[_]])) { (obj, args) =>
mkMethod(clazz, "subtractMod", Array[Class[_]](classOf[Base#Ref[_]], classOf[Base#Ref[_]])) { (obj, args) =>
obj.asInstanceOf[ctx.UnsignedBigInt].subtractMod(args(0).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]], args(1).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]])
},
mkMethod(clazz, "multiplyMod", Array[Class[_]](classOf[Base#Ref[_]])) { (obj, args) =>
mkMethod(clazz, "multiplyMod", Array[Class[_]](classOf[Base#Ref[_]], classOf[Base#Ref[_]])) { (obj, args) =>
obj.asInstanceOf[ctx.UnsignedBigInt].multiplyMod(args(0).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]], args(1).asInstanceOf[ctx.Ref[ctx.UnsignedBigInt]])
},
mkMethod(clazz, "mod", Array[Class[_]](classOf[Base#Ref[_]])) { (obj, args) =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -521,7 +521,8 @@ object UnsignedBigInt extends EntityObject("UnsignedBigInt") {
override protected def collectMethods: Map[RMethod, MethodDesc] = {
super.collectMethods ++
Elem.declaredMethods(RClass(classOf[UnsignedBigInt]), RClass(classOf[UnsignedBigInt]), Set(
"add", "subtract", "multiply", "divide", "mod", "min", "max", "plusMod", "subtractMod", "multiplyMod"
"add", "subtract", "multiply", "divide", "mod", "modInverse",
"min", "max", "plusMod", "subtractMod", "multiplyMod"
))
}
}
Expand Down
3 changes: 2 additions & 1 deletion sc/shared/src/test/scala/sigma/SigmaDslTesting.scala
Original file line number Diff line number Diff line change
Expand Up @@ -1376,6 +1376,7 @@ class SigmaDslTesting extends AnyPropSpec
case IntType => arbInt
case LongType => arbLong
case BigIntRType => arbBigInt
case UnsignedBigIntRType => arbUnsignedBigInt
case GroupElementRType => arbGroupElement
case SigmaPropRType => arbSigmaProp
case BoxRType => arbBox
Expand Down Expand Up @@ -1404,7 +1405,7 @@ class SigmaDslTesting extends AnyPropSpec
*/
def updateArbitrary[A](t: RType[A], sampled: Sampled[A]) = {
t match {
case BigIntRType | GroupElementRType | SigmaPropRType |
case BigIntRType | UnsignedBigIntRType | GroupElementRType | SigmaPropRType |
BoxRType | PreHeaderRType | HeaderRType | AvlTreeRType |
_: CollType[_] | _: PairType[_,_] | _: OptionType[_] =>
val newArb = Arbitrary(Gen.oneOf(sampled.samples))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -154,7 +154,6 @@ class BasicOpsSpecification extends CompilerTestingCommons
flexVerifier.verify(verifyEnv, tree, ctxExt, pr.proof, fakeMessage).get._1 shouldBe true
}


property("getVarFromInput") {
def getVarTest(): Assertion = {
val customExt = Map(
Expand Down
10 changes: 0 additions & 10 deletions sdk/shared/src/main/scala/org/ergoplatform/sdk/JavaHelpers.scala
Original file line number Diff line number Diff line change
Expand Up @@ -315,16 +315,6 @@ object JavaHelpers {

def collRType[T](tItem: RType[T]): RType[Coll[T]] = sigma.collRType(tItem)

def BigIntRType: RType[sigma.BigInt] = sigma.BigIntRType

def GroupElementRType: RType[sigma.GroupElement] = sigma.GroupElementRType

def SigmaPropRType: RType[sigma.SigmaProp] = sigma.SigmaPropRType

def AvlTreeRType: RType[sigma.AvlTree] = sigma.AvlTreeRType

def BoxRType: RType[sigma.Box] = sigma.BoxRType

def SigmaDsl: CSigmaDslBuilder = sigma.eval.SigmaDsl

def collFrom(arr: Array[Byte]): Coll[Byte] = {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package org.ergoplatform.sdk.utils

import org.ergoplatform.ErgoBox
import sigma.data.{AvlTreeData, AvlTreeFlags, CAvlTree, CBigInt, CGroupElement, CSigmaProp, CollType, FuncType, OptionType, PairType, RType, TrivialProp, TupleType}
import sigma.data.{AvlTreeData, AvlTreeFlags, CAvlTree, CBigInt, CGroupElement, CSigmaProp, CUnsignedBigInt, CollType, FuncType, OptionType, PairType, RType, TrivialProp, TupleType}
import sigma.data.RType._
import scorex.crypto.authds.avltree.batch.BatchAVLProver
import scorex.crypto.hash.{Blake2b256, Digest32}
Expand All @@ -11,6 +11,7 @@ import sigma._
import sigma.ast.ErgoTree
import ErgoTree.HeaderType
import sigma.crypto.CryptoConstants

import java.math.BigInteger
import scala.language.implicitConversions

Expand Down Expand Up @@ -48,6 +49,7 @@ object Zero extends ZeroLowPriority {
implicit val IntIsZero: Zero[Int] = CZero(0)
implicit val LongIsZero: Zero[Long] = CZero(0L)
implicit val BigIntIsZero: Zero[BigInt] = CZero(CBigInt(BigInteger.ZERO))
implicit val UnsignedBigIntIsZero: Zero[UnsignedBigInt] = CZero(CUnsignedBigInt(BigInteger.ZERO))
implicit val GroupElementIsZero: Zero[GroupElement] = CZero(CGroupElement(CryptoConstants.dlogGroup.identity))
implicit val AvlTreeIsZero: Zero[AvlTree] = CZero({
val avlProver = new BatchAVLProver[Digest32, Blake2b256.type](keyLength = 32, None)
Expand Down Expand Up @@ -88,6 +90,7 @@ object Zero extends ZeroLowPriority {
case LongType => Zero[Long]
case UnitType => Zero[Unit]
case BigIntRType => Zero[BigInt]
case UnsignedBigIntRType => Zero[UnsignedBigInt]
case BoxRType => Zero[Box]
case GroupElementRType => Zero[GroupElement]
case AvlTreeRType => Zero[AvlTree]
Expand Down

0 comments on commit 933b2cc

Please sign in to comment.