Skip to content

Commit

Permalink
fix-cost: negative test with CostLimitException
Browse files Browse the repository at this point in the history
  • Loading branch information
aslesarenko committed Mar 25, 2021
1 parent e5397ed commit e2faf2e
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 11 deletions.
37 changes: 26 additions & 11 deletions sigmastate/src/test/scala/sigmastate/CostingSpecification.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package sigmastate

import org.ergoplatform.SigmaConstants.ScriptCostLimit
import org.ergoplatform.validation.ValidationRules
import org.ergoplatform.{ErgoLikeContext, ErgoBox}
import org.ergoplatform.{ErgoBox, ErgoLikeContext}
import scorex.crypto.authds.avltree.batch.Lookup
import scorex.crypto.authds.{ADDigest, ADKey}
import scorex.crypto.hash.Blake2b256
Expand All @@ -13,11 +13,12 @@ import sigmastate.eval._
import sigmastate.helpers.TestingHelpers._
import sigmastate.helpers.{ContextEnrichingTestProvingInterpreter, ErgoLikeTestInterpreter}
import sigmastate.interpreter.ContextExtension
import sigmastate.interpreter.Interpreter.{ScriptNameProp, ScriptEnv, emptyEnv}
import sigmastate.interpreter.Interpreter.{ScriptEnv, ScriptNameProp, emptyEnv}
import sigmastate.utxo.CostTable
import sigmastate.utxo.CostTable._
import special.sigma.{SigmaTestingData, AvlTree}
import special.sigma.{AvlTree, SigmaTestingData}
import sigmastate.lang.Terms.ValueOps
import sigmastate.lang.exceptions.CostLimitException

class CostingSpecification extends SigmaTestingData with CrossVersionProps {
implicit lazy val IR = new TestingIRContext {
Expand Down Expand Up @@ -408,8 +409,7 @@ class CostingSpecification extends SigmaTestingData with CrossVersionProps {
property("ErgoTree with SigmaPropConstant costs") {
val d = new TestData; import d._

def testTree(tree: ErgoTree, initCost: Long, expectedCost: Long) = {
val ctx = context.withInitCost(initCost)
def proveAndVerify(ctx: ErgoLikeContext, tree: ErgoTree, expectedCost: Long) = {
val pr = interpreter.prove(tree, ctx, fakeMessage).get
pr.cost shouldBe expectedCost

Expand All @@ -422,19 +422,34 @@ class CostingSpecification extends SigmaTestingData with CrossVersionProps {
val tree1 = ErgoTree.fromSigmaBoolean(pkA) // without segregation
val tree2 = ErgoTree.withSegregation(pkA) // with segregation, have different `complexity`

testTree(tree1, 0, 10141)
testTree(tree2, 0, 10161)
{
val ctx = context.withInitCost(0)
proveAndVerify(ctx, tree1, expectedCost = 10141)
proveAndVerify(ctx, tree2, expectedCost = 10161)
}

{
val ctx = context.withInitCost(10000)
proveAndVerify(ctx, tree1, expectedCost = 20141)
proveAndVerify(ctx, tree2, expectedCost = 20161)
}

testTree(tree1, context.initCost, 20141)
testTree(tree2, context.initCost, 20161)
{
val ctx = context.withInitCost(10000).withCostLimit(20000)
assertExceptionThrown(
proveAndVerify(ctx, tree1, expectedCost = 20141),
exceptionLike[CostLimitException](
"Estimated execution cost", "exceeds the limit")
)
}

// more complex tree without Deserialize
val tree3 = ErgoTree.fromProposition(compiler
.compile(env, "{ sigmaProp(HEIGHT == 2) }")
.asSigmaProp)

testTree(tree3, 0, 541)
testTree(tree3, context.initCost, 10541)
proveAndVerify(context.withInitCost(0), tree3, expectedCost = 541)
proveAndVerify(context.withInitCost(10000), tree3, expectedCost = 10541)
}

property("laziness of AND, OR costs") {
Expand Down
13 changes: 13 additions & 0 deletions sigmastate/src/test/scala/sigmastate/helpers/NegativeTesting.scala
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package sigmastate.helpers
import org.scalatest.Matchers

import scala.annotation.tailrec
import scala.reflect.ClassTag

trait NegativeTesting extends Matchers {

Expand Down Expand Up @@ -33,4 +34,16 @@ trait NegativeTesting extends Matchers {
if (t.getCause == null) t
else rootCause(t.getCause)

/** Creates an assertion which checks the given type and message contents.
*
* @tparam E expected type of exception
* @param msgParts expected parts of the exception message
* @return the assertion which can be used in assertExceptionThrown method
*/
def exceptionLike[E <: Throwable : ClassTag]
(msgParts: String*): Throwable => Boolean = {
case t: E => msgParts.forall(t.getMessage.contains(_))
case _ => false
}

}

0 comments on commit e2faf2e

Please sign in to comment.