Skip to content

Commit

Permalink
Miniev implementation
Browse files Browse the repository at this point in the history
  • Loading branch information
phearnot committed Dec 27, 2022
1 parent deb8ae3 commit d5c6f17
Show file tree
Hide file tree
Showing 83 changed files with 2,219 additions and 1,926 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -167,7 +167,7 @@ object EnvironmentFunctionsBenchmark {

@State(Scope.Benchmark)
class AddressFromString {
val ctx: EvaluationContext[Environment, Id] =
val ctx: EvaluationContext[Id] =
WavesContext
.build(Global, DirectiveSet(V4, Account, DApp).explicitGet())
.evaluationContext(environment)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,23 +4,22 @@ import java.util.concurrent.TimeUnit

import cats.Id
import com.wavesplatform.lang.Common
import com.wavesplatform.lang.directives.values.{V1, V3}
import com.wavesplatform.lang.directives.values.{V1, V3, V5, V6}
import com.wavesplatform.lang.v1.EvaluatorV2Benchmark.*
import com.wavesplatform.lang.v1.compiler.Terms.{EXPR, IF, TRUE}
import com.wavesplatform.lang.v1.compiler.Terms.{CONST_LONG, EXPR, IF, TRUE}
import com.wavesplatform.lang.v1.compiler.TestCompiler
import com.wavesplatform.lang.v1.evaluator.EvaluatorV2
import com.wavesplatform.lang.v1.evaluator.ctx.{EvaluationContext, LoggedEvaluationContext}
import com.wavesplatform.lang.v1.evaluator.ctx.impl.PureContext
import com.wavesplatform.lang.v1.traits.Environment
import com.wavesplatform.lang.v1.evaluator.ctx.{EvaluationContext, LoggedEvaluationContext}
import org.openjdk.jmh.annotations.*
import org.openjdk.jmh.infra.Blackhole

import scala.annotation.tailrec

object EvaluatorV2Benchmark {
val pureContext: CTX[Environment] = PureContext.build(V1, useNewPowPrecision = true).withEnvironment[Environment]
val pureEvalContext: EvaluationContext[Environment, Id] = pureContext.evaluationContext(Common.emptyBlockchainEnvironment())
val evaluatorV2: EvaluatorV2 = new EvaluatorV2(LoggedEvaluationContext(_ => _ => (), pureEvalContext), V1, true, true)
val pureContext: CTX = PureContext.build(V1, useNewPowPrecision = true)
val pureEvalContext: EvaluationContext[Id] = pureContext.evaluationContext(Common.emptyBlockchainEnvironment())
val evaluatorV2: EvaluatorV2 = new EvaluatorV2(LoggedEvaluationContext(_ => _ => (), pureEvalContext), V1, true, true)
}

@OutputTimeUnit(TimeUnit.MILLISECONDS)
Expand All @@ -44,6 +43,45 @@ class EvaluatorV2Benchmark {

@Benchmark
def conditions(st: Conditions, bh: Blackhole): Unit = bh.consume(eval(pureEvalContext, st.expr, V1))

@Benchmark
def recFunc(st: RecFunc, bh: Blackhole): Unit = bh.consume {
val (_, _, res) = eval(pureEvalContext, st.expr, V1)
require(res == Right(CONST_LONG(13631488)), s"$res")
}

@Benchmark
def overheadCallable(st: OverheadTest, bh: Blackhole): Unit = bh.consume {
val (_, comp, res) = eval(pureEvalContext, st.expr.expr, V6)
require((Int.MaxValue - comp) == 1048576, s"$comp")
}

@Benchmark
def mini_funcs(st: Funcs, bh: Blackhole): Unit = bh.consume(miniEv(st.expr, pureEvalContext))

@Benchmark
def mini_lets(st: Lets, bh: Blackhole): Unit = bh.consume(miniEv(st.expr, pureEvalContext))

@Benchmark
def mini_custom(st: CustomFunc, bh: Blackhole): Unit = bh.consume(miniEv(st.expr, pureEvalContext))

@Benchmark
def mini_littleCustom(st: LittleCustomFunc, bh: Blackhole): Unit = bh.consume(miniEv(st.expr, pureEvalContext))

@Benchmark
def mini_conditions(st: Conditions, bh: Blackhole): Unit = bh.consume(miniEv(st.expr, pureEvalContext))

@Benchmark
def mini_recFunc(st: RecFunc, bh: Blackhole): Unit = bh.consume {
val (log, spentComplexity, res) = miniEv(st.expr, pureEvalContext)
require(res == Right(CONST_LONG(13631488)), s"$res")
}

@Benchmark
def mini_overheadCallable(st: OverheadTest, bh: Blackhole): Unit = bh.consume {
val (_, comp, res) = miniEv(st.expr.expr, pureEvalContext, 52000)
require(comp == 1048576, s"$comp")
}
}

@State(Scope.Benchmark)
Expand All @@ -58,7 +96,10 @@ class Funcs {
| a$count() == a$count()
""".stripMargin

val expr = TestCompiler(V3).compileExpression(script).expr.asInstanceOf[EXPR]
val expr = {
val sc = TestCompiler(V6).compileExpression(script, checkSize = false)
sc.expr
}
}

@State(Scope.Benchmark)
Expand All @@ -71,7 +112,22 @@ class Lets {
| a$count == a$count
""".stripMargin

val expr = TestCompiler(V3).compileExpression(script).expr.asInstanceOf[EXPR]
val expr = TestCompiler(V3).compileExpression(script, checkSize = false).expr
}

@State(Scope.Benchmark)
class RecFunc {
def scriptStr(size: Int) =
s"""func f1(i: Int) = i + 1
|${(2 to size)
.map { i =>
s"func f$i(${(0 until i).map(idx => s"i$idx: Int").mkString(",")}) = ${(1 until i).map(fi => s"f$fi(${(1 to fi).map(ii => s"i$ii").mkString(",")})").mkString("+")}"
}
.mkString("\n")}
|f${size}(${(1 to size).mkString(",")})
|""".stripMargin
private val script: String = scriptStr(22)
val expr = TestCompiler(V6).compileExpression(script, checkSize = false).expr
}

@State(Scope.Benchmark)
Expand Down Expand Up @@ -115,7 +171,7 @@ class CustomFunc {
| f() && f() && f() && f() && f() && f() && f()
""".stripMargin

val expr = TestCompiler(V3).compileExpression(script).expr.asInstanceOf[EXPR]
val expr = TestCompiler(V6).compileExpression(script).expr
}

@State(Scope.Benchmark)
Expand Down Expand Up @@ -159,7 +215,22 @@ class LittleCustomFunc {
| f()
""".stripMargin

val expr = TestCompiler(V3).compileExpression(script).expr.asInstanceOf[EXPR]
val expr = TestCompiler(V3).compileExpression(script).expr
}

@State(Scope.Benchmark)
class OverheadTest {
val expr = {
val n = 20
val scriptTest =
s"""
| func f0() = true
| ${(0 until n).map(i => s"func f${i + 1}() = if (f$i()) then f$i() else f$i()").mkString("\n")}
| f$n()
""".stripMargin
println(scriptTest)
TestCompiler(V5).compileExpression(scriptTest)
}
}

@State(Scope.Benchmark)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,20 +5,19 @@ import java.util.concurrent.{ThreadLocalRandom, TimeUnit}
import cats.Id
import com.google.common.primitives.Longs
import com.wavesplatform.common.state.ByteStr
import com.wavesplatform.common.utils._
import com.wavesplatform.common.utils.*
import com.wavesplatform.lang.directives.DirectiveSet
import com.wavesplatform.lang.directives.values._
import com.wavesplatform.lang.utils._
import com.wavesplatform.lang.directives.values.*
import com.wavesplatform.lang.utils.*
import com.wavesplatform.lang.v1.FunctionHeader.Native
import com.wavesplatform.lang.v1.PureFunctionsRebenchmark._
import com.wavesplatform.lang.v1.PureFunctionsRebenchmark.*
import com.wavesplatform.lang.v1.compiler.Terms
import com.wavesplatform.lang.v1.compiler.Terms._
import com.wavesplatform.lang.v1.compiler.Terms.*
import com.wavesplatform.lang.v1.evaluator.ctx.EvaluationContext
import com.wavesplatform.lang.v1.evaluator.ctx.impl.PureContext
import com.wavesplatform.lang.v1.evaluator.{FunctionIds, Log}
import com.wavesplatform.lang.v1.traits.Environment
import com.wavesplatform.lang.{Common, ExecutionError, v1}
import org.openjdk.jmh.annotations._
import org.openjdk.jmh.annotations.*
import org.openjdk.jmh.infra.Blackhole

import scala.util.Random
Expand Down Expand Up @@ -217,7 +216,7 @@ class PureFunctionsRebenchmark {
}

object PureFunctionsRebenchmark {
val context: EvaluationContext[Environment, Id] =
val context: EvaluationContext[Id] =
lazyContexts(DirectiveSet(V5, Account, Expression).explicitGet() -> true)()
.evaluationContext(Common.emptyBlockchainEnvironment())

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,28 +7,27 @@ import cats.kernel.Monoid
import com.wavesplatform.common.state.ByteStr
import com.wavesplatform.common.utils.{Base58, EitherExt2}
import com.wavesplatform.crypto.Curve25519
import com.wavesplatform.lang.Global
import com.wavesplatform.lang.directives.values.{V1, V4}
import com.wavesplatform.lang.v1.EnvironmentFunctionsBenchmark.{curve25519, randomBytes}
import com.wavesplatform.lang.v1.FunctionHeader.Native
import com.wavesplatform.lang.v1.ScriptEvaluatorBenchmark.*
import com.wavesplatform.lang.v1.compiler.Terms.*
import com.wavesplatform.lang.v1.evaluator.Contextful.NoContext
import com.wavesplatform.lang.v1.evaluator.EvaluatorV1.*
import com.wavesplatform.lang.v1.evaluator.FunctionIds.{FROMBASE58, SIGVERIFY, TOBASE58}
import com.wavesplatform.lang.v1.evaluator.ctx.EvaluationContext
import com.wavesplatform.lang.v1.evaluator.ctx.impl.{CryptoContext, PureContext}
import com.wavesplatform.lang.v1.evaluator.{EvaluatorV1, FunctionIds}
import com.wavesplatform.lang.{Common, Global}
import org.openjdk.jmh.annotations.*
import org.openjdk.jmh.infra.Blackhole

import scala.util.Random

object ScriptEvaluatorBenchmark {
val version = V1
val pureEvalContext: EvaluationContext[NoContext, Id] =
PureContext.build(V1, useNewPowPrecision = true).evaluationContext
val evaluatorV1: EvaluatorV1[Id, NoContext] = new EvaluatorV1[Id, NoContext]()
val pureEvalContext: EvaluationContext[Id] =
PureContext.build(V1, useNewPowPrecision = true).evaluationContext(Common.emptyBlockchainEnvironment())
val evaluatorV1: EvaluatorV1[Id] = new EvaluatorV1[Id]()
}

@OutputTimeUnit(TimeUnit.MICROSECONDS)
Expand Down Expand Up @@ -93,7 +92,7 @@ class ScriptEvaluatorBenchmark {

@State(Scope.Benchmark)
class NestedBlocks {
val context: EvaluationContext[NoContext, Id] = pureEvalContext
val context: EvaluationContext[Id] = pureEvalContext

val expr: EXPR = {
val blockCount = 300
Expand All @@ -107,8 +106,9 @@ class NestedBlocks {

@State(Scope.Benchmark)
class Base58Perf {
val context: EvaluationContext[NoContext, Id] =
Monoid.combine(pureEvalContext, CryptoContext.build(Global, version).evaluationContext)
val context: EvaluationContext[Id] =
Monoid.combine(PureContext.build(V1, useNewPowPrecision = true), CryptoContext.build(Global, version))
.evaluationContext(Common.emptyBlockchainEnvironment())

val encode: EXPR = {
val base58Count = 120
Expand Down Expand Up @@ -150,8 +150,8 @@ class Base58Perf {

@State(Scope.Benchmark)
class Signatures {
val context: EvaluationContext[NoContext, Id] =
Monoid.combine(pureEvalContext, CryptoContext.build(Global, version).evaluationContext)
val context: EvaluationContext[Id] =
Monoid.combine(PureContext.build(V1, useNewPowPrecision = true), CryptoContext.build(Global, version)).evaluationContext(Common.emptyBlockchainEnvironment())

val expr: EXPR = {
val sigCount = 20
Expand Down Expand Up @@ -191,7 +191,7 @@ class Signatures {

@State(Scope.Benchmark)
class Concat {
val context: EvaluationContext[NoContext, Id] = pureEvalContext
val context: EvaluationContext[Id] = pureEvalContext

private val Steps = 180

Expand All @@ -218,7 +218,7 @@ class Concat {

@State(Scope.Benchmark)
class Median {
val context: EvaluationContext[NoContext, Id] = PureContext.build(V4, useNewPowPrecision = true).evaluationContext
val context: EvaluationContext[Id] = PureContext.build(V4, useNewPowPrecision = true).evaluationContext(Common.emptyBlockchainEnvironment())

val randomElements: Array[EXPR] =
(1 to 10000).map { _ =>
Expand Down Expand Up @@ -260,8 +260,8 @@ class Median {

@State(Scope.Benchmark)
class SigVerify32Kb {
val context: EvaluationContext[NoContext, Id] =
Monoid.combine(PureContext.build(V4, useNewPowPrecision = true).evaluationContext, CryptoContext.build(Global, V4).evaluationContext)
val context: EvaluationContext[Id] =
Monoid.combine(PureContext.build(V4, useNewPowPrecision = true), CryptoContext.build(Global, V4)).evaluationContext(Common.emptyBlockchainEnvironment())

val expr: EXPR = {
val (privateKey, publicKey) = curve25519.generateKeypair
Expand All @@ -281,11 +281,11 @@ class SigVerify32Kb {

@State(Scope.Benchmark)
class ListRemoveByIndex {
val context: EvaluationContext[NoContext, Id] =
val context: EvaluationContext[Id] =
Monoid.combine(
PureContext.build(V4, useNewPowPrecision = true).evaluationContext,
CryptoContext.build(Global, V4).evaluationContext
)
PureContext.build(V4, useNewPowPrecision = true),
CryptoContext.build(Global, V4)
).evaluationContext(Common.emptyBlockchainEnvironment())

val list: ARR = ARR(Vector.fill(1000)(CONST_LONG(Long.MaxValue)), limited = true).explicitGet()

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package com.wavesplatform.lang

import cats.Id
import com.wavesplatform.lang.directives.values.StdLibVersion
import com.wavesplatform.lang.miniev.{Ev, State}
import com.wavesplatform.lang.v1.FunctionHeader.Native
import com.wavesplatform.lang.v1.compiler.Terms
import com.wavesplatform.lang.v1.compiler.Terms.{CONST_BIGINT, CONST_LONG, EXPR, FUNCTION_CALL}
Expand All @@ -10,7 +11,6 @@ import com.wavesplatform.lang.v1.evaluator.FunctionIds.POW_BIGINT
import com.wavesplatform.lang.v1.evaluator.ctx.EvaluationContext
import com.wavesplatform.lang.v1.evaluator.ctx.impl.Rounding
import com.wavesplatform.lang.v1.evaluator.{EvaluatorV2, Log}
import com.wavesplatform.lang.v1.traits.Environment

package object v1 {
def pow(base: BigInt, basePrecision: Int, exponent: BigInt, exponentPrecision: Int, resultPrecision: Int): EXPR =
Expand All @@ -27,9 +27,12 @@ package object v1 {
)

def eval(
ctx: EvaluationContext[Environment, Id],
ctx: EvaluationContext[Id],
expr: EXPR,
stdLibVersion: StdLibVersion
): (Log[Id], Int, Either[ExecutionError, Terms.EVALUATED]) =
EvaluatorV2.applyCompleted(ctx, expr, LogExtraInfo(), stdLibVersion, newMode = true, correctFunctionCallScope = true)

def miniEv(expr: EXPR, ctx: EvaluationContext[Id], limit: Int = Int.MaxValue): (Log[Id], Int, Either[ExecutionError, Terms.EVALUATED]) =
Ev.run(expr, ctx)
}
10 changes: 4 additions & 6 deletions lang/jvm/src/main/scala/com/wavesplatform/lang/Global.scala
Original file line number Diff line number Diff line change
Expand Up @@ -105,13 +105,13 @@ object Global extends BaseGlobal {
} else {
BigDecimalMath.pow(baseBD, expBD, context)
}
if (useNewPrecision)
(if (useNewPrecision)
setScale(resultPrecision, round, context.getPrecision, result)
else {
val value = result.setScale(resultPrecision.toInt, round.mode).unscaledValue
val value = result.setScale(resultPrecision, round.mode).unscaledValue
Right(BigInt(value))
}
}.flatten.map(_.bigInteger.longValueExact())
}).map(_.bigInteger.longValueExact())
}.flatten

def log(b: Long, bp: Long, e: Long, ep: Long, rp: Long, round: Rounding): Either[String, Long] =
tryEither {
Expand All @@ -128,8 +128,6 @@ object Global extends BaseGlobal {
val base = toJBig(b, bp)
val exp = toJBig(e, ep)



val context = if (useNewPrecision) bigMathContext else oldBigMathContext
val res = if (exp == BigDecimal(0.5).bigDecimal) {
BigDecimalMath.sqrt(base, context)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
package com.wavesplatform.lang.utils

trait Logging {

}
Loading

0 comments on commit d5c6f17

Please sign in to comment.