Skip to content

Commit 36707e3

Browse files
committed
ergotree-interpreter: add criterion benchmarks
1 parent 48e29f6 commit 36707e3

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

70 files changed

+315
-85
lines changed

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,7 @@ proptest-derive = "0.5.1"
100100
pretty_assertions = "1.3"
101101
wasm-bindgen-test = "0.3.37"
102102
expect-test = "1.4.1"
103+
criterion = { version = "0.5.1", features = ["default", "cargo_bench_support"] }
103104

104105
[profile.release]
105106
# Tell `rustc` to optimize for small code size.

ergotree-interpreter/Cargo.toml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ gf2_192 = { version = "^0.28.0", path = "../gf2_192" }
3939
miette = { workspace = true, optional = true }
4040
hashbrown = { workspace = true }
4141
core2 = { workspace = true }
42+
sigma-test-util = { workspace = true, optional = true }
4243
[features]
4344
json = [
4445
"serde",
@@ -57,6 +58,7 @@ arbitrary = [
5758
"ergotree-ir/arbitrary",
5859
"ergo-chain-types/arbitrary",
5960
"gf2_192/arbitrary",
61+
"sigma-test-util",
6062
]
6163

6264
[dev-dependencies]
@@ -65,3 +67,9 @@ ergoscript-compiler = { workspace = true }
6567
proptest = { workspace = true }
6668
sigma-test-util = { workspace = true }
6769
expect-test = { workspace = true }
70+
criterion = { workspace = true }
71+
72+
[[bench]]
73+
name = "eval_benches"
74+
harness = false
75+
required-features = ["arbitrary"]
Lines changed: 206 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,206 @@
1+
use std::str::FromStr;
2+
3+
use criterion::{criterion_group, criterion_main, BenchmarkId, Criterion};
4+
use ergo_chain_types::ec_point::{exponentiate, generator};
5+
use ergotree_interpreter::eval::test_util::eval_out_wo_ctx;
6+
use ergotree_ir::{
7+
bigint256::BigInt256,
8+
ergo_tree::{ErgoTree, ErgoTreeHeader},
9+
mir::{
10+
bin_op::{BinOp, BinOpKind, RelationOp},
11+
calc_blake2b256::CalcBlake2b256,
12+
calc_sha256::CalcSha256,
13+
coll_append::Append,
14+
coll_filter::Filter,
15+
constant::Constant,
16+
exponentiate::Exponentiate,
17+
expr::Expr,
18+
func_value::{FuncArg, FuncValue},
19+
method_call::MethodCall,
20+
sigma_and::SigmaAnd,
21+
subst_const::SubstConstants,
22+
val_use::ValUse,
23+
value::Value,
24+
},
25+
serialization::SigmaSerializable,
26+
sigma_protocol::sigma_boolean::{SigmaBoolean, SigmaProp},
27+
types::{scoll::FLATMAP_METHOD, stype::SType, stype_param::STypeVar},
28+
};
29+
30+
fn bench_blake2b256(c: &mut Criterion) {
31+
let mut group = c.benchmark_group("blake2b256");
32+
for size in (1..1024).step_by(200) {
33+
let arr = vec![0u8; size];
34+
let expr: Expr = CalcBlake2b256 {
35+
input: Box::new(Constant::from(arr).into()),
36+
}
37+
.into();
38+
group.bench_function(BenchmarkId::from_parameter(format!("{size:4}")), |b| {
39+
b.iter(|| eval_out_wo_ctx::<Vec<i8>>(&expr))
40+
});
41+
}
42+
}
43+
44+
fn bench_sha256(c: &mut Criterion) {
45+
let mut group = c.benchmark_group("sha256");
46+
for size in (1..1024).step_by(200) {
47+
let arr = vec![0u8; size];
48+
let expr: Expr = CalcSha256 {
49+
input: Box::new(Constant::from(arr).into()),
50+
}
51+
.into();
52+
group.bench_function(BenchmarkId::from_parameter(format!("{size:4}")), |b| {
53+
b.iter(|| eval_out_wo_ctx::<Vec<i8>>(&expr))
54+
});
55+
}
56+
}
57+
58+
fn bench_append(c: &mut Criterion) {
59+
let mut group = c.benchmark_group("Coll.append");
60+
for size in (1..1024).step_by(200) {
61+
let arr = vec![0u8; size];
62+
let expr: Expr = Append::new(
63+
Constant::from(arr.clone()).into(),
64+
Constant::from(arr).into(),
65+
)
66+
.unwrap()
67+
.into();
68+
group.bench_function(BenchmarkId::from_parameter(format!("{size:4}")), |b| {
69+
b.iter(|| eval_out_wo_ctx::<Value<'_>>(&expr));
70+
});
71+
}
72+
}
73+
74+
fn bench_substitute_constants(c: &mut Criterion) {
75+
let mut group = c.benchmark_group("substituteConstants");
76+
for size in (1..=101).step_by(10) {
77+
let tree_expr: Expr =
78+
SigmaAnd::new(vec![Constant::from(SigmaBoolean::from(true)).into(); size])
79+
.unwrap()
80+
.into();
81+
let tree_bytes = ErgoTree::new(ErgoTreeHeader::v1(true), &tree_expr)
82+
.unwrap()
83+
.sigma_serialize_bytes()
84+
.unwrap();
85+
let subst_expr = SubstConstants::new(
86+
tree_bytes.into(),
87+
Constant::from((0..size as i32).collect::<Vec<_>>()).into(),
88+
Constant::from(vec![SigmaProp::new(false.into()); size]).into(),
89+
)
90+
.unwrap()
91+
.into();
92+
group.bench_function(BenchmarkId::from_parameter(format!("{size:3}")), |b| {
93+
b.iter(|| eval_out_wo_ctx::<Value<'_>>(&subst_expr))
94+
});
95+
}
96+
}
97+
98+
fn bench_exponentiate(c: &mut Criterion) {
99+
c.bench_function("exponentiate(generator, a)", |b| {
100+
let a = BigInt256::from_str("1000").unwrap();
101+
let expr: Expr = Exponentiate::new(generator().into(), a.into())
102+
.unwrap()
103+
.into();
104+
b.iter(|| eval_out_wo_ctx::<Value<'_>>(&expr))
105+
});
106+
c.bench_function("exponentiate(point, a)", |b| {
107+
let a = BigInt256::from_str("1000").unwrap();
108+
let expr: Expr =
109+
Exponentiate::new((exponentiate(&generator(), &2u32.into())).into(), a.into())
110+
.unwrap()
111+
.into();
112+
b.iter(|| eval_out_wo_ctx::<Value<'_>>(&expr))
113+
});
114+
}
115+
116+
fn bench_filter(c: &mut Criterion) {
117+
let mut group = c.benchmark_group("filter");
118+
// v % 2 == 0
119+
let filter_lambda = BinOp {
120+
kind: BinOpKind::Relation(RelationOp::Eq),
121+
left: Box::new(
122+
BinOp {
123+
kind: BinOpKind::Arith(ergotree_ir::mir::bin_op::ArithOp::Modulo),
124+
left: Box::new(
125+
ValUse {
126+
val_id: 1.into(),
127+
tpe: SType::SInt,
128+
}
129+
.into(),
130+
),
131+
right: Box::new(Constant::from(2i32).into()),
132+
}
133+
.into(),
134+
),
135+
right: Box::new(Constant::from(0i32).into()),
136+
};
137+
for size in (1..=1001i32).step_by(100) {
138+
let arr: Expr = Constant::from((0..size).collect::<Vec<_>>()).into();
139+
let expr: Expr = Filter::new(
140+
arr,
141+
FuncValue::new(
142+
vec![FuncArg {
143+
idx: 1.into(),
144+
tpe: SType::SInt,
145+
}],
146+
filter_lambda.clone().into(),
147+
)
148+
.into(),
149+
)
150+
.unwrap()
151+
.into();
152+
group.bench_function(BenchmarkId::from_parameter(format!("{size:4}")), |b| {
153+
b.iter(|| eval_out_wo_ctx::<Value<'_>>(&expr))
154+
});
155+
}
156+
}
157+
158+
fn bench_flatmap(c: &mut Criterion) {
159+
let mut group = c.benchmark_group("flatMap");
160+
// flatten Coll[Coll[Byte]] into Coll[Byte]
161+
let flatmap_lambda: Expr = ValUse {
162+
val_id: 1.into(),
163+
tpe: SType::SColl(SType::SByte.into()),
164+
}
165+
.into();
166+
for size in (1..=1001).step_by(100) {
167+
let obj: Expr = Constant::from(vec![vec![0u8; 100]; size]).into();
168+
let mc: Expr = MethodCall::new(
169+
obj,
170+
FLATMAP_METHOD.clone().with_concrete_types(
171+
&[
172+
(STypeVar::iv(), SType::SColl(SType::SByte.into())),
173+
(STypeVar::ov(), SType::SByte),
174+
]
175+
.into_iter()
176+
.collect(),
177+
),
178+
vec![FuncValue::new(
179+
vec![FuncArg {
180+
idx: 1.into(),
181+
tpe: SType::SColl(SType::SByte.into()),
182+
}],
183+
flatmap_lambda.clone(),
184+
)
185+
.into()],
186+
)
187+
.unwrap()
188+
.into();
189+
group.bench_function(BenchmarkId::from_parameter(format!("{size:4}")), |b| {
190+
b.iter(|| assert_eq!(eval_out_wo_ctx::<Vec<i8>>(&mc).len(), 100 * size))
191+
});
192+
}
193+
}
194+
195+
criterion_group!(
196+
eval_benches,
197+
bench_blake2b256,
198+
bench_sha256,
199+
bench_append,
200+
bench_substitute_constants,
201+
bench_exponentiate,
202+
bench_filter,
203+
bench_flatmap
204+
);
205+
206+
criterion_main!(eval_benches);

ergotree-interpreter/src/contracts.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
mod tests {
44
use core::convert::TryInto;
55

6-
use crate::eval::tests::eval_out_wo_ctx;
6+
use crate::eval::test_util::eval_out_wo_ctx;
77
use ergotree_ir::chain::address::AddressEncoder;
88
use ergotree_ir::chain::address::NetworkPrefix;
99
use ergotree_ir::sigma_protocol::sigma_boolean::SigmaProp;

ergotree-interpreter/src/eval.rs

Lines changed: 26 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -387,27 +387,20 @@ fn smethod_eval_fn(method: &SMethod) -> Result<EvalFn, EvalError> {
387387
})
388388
}
389389

390-
#[cfg(test)]
391-
#[cfg(feature = "arbitrary")]
390+
#[doc(hidden)]
391+
#[allow(missing_docs)]
392392
#[allow(clippy::unwrap_used)]
393393
#[allow(clippy::todo)]
394-
pub(crate) mod tests {
394+
#[cfg(feature = "arbitrary")]
395+
pub mod test_util {
395396

396397
use super::env::Env;
397398
use super::*;
398-
use ergotree_ir::mir::bin_op::BinOp;
399-
use ergotree_ir::mir::bin_op::BinOpKind;
400-
use ergotree_ir::mir::bin_op::RelationOp;
401-
use ergotree_ir::mir::block::BlockValue;
402399
use ergotree_ir::mir::constant::TryExtractFrom;
403400
use ergotree_ir::mir::constant::TryExtractInto;
404-
use ergotree_ir::mir::val_def::ValDef;
405-
use ergotree_ir::mir::val_use::ValUse;
406401
use ergotree_ir::serialization::sigma_byte_reader::from_bytes;
407402
use ergotree_ir::serialization::sigma_byte_reader::SigmaByteRead;
408403
use ergotree_ir::serialization::SigmaSerializable;
409-
use ergotree_ir::types::stype::SType;
410-
use expect_test::expect;
411404
use sigma_test_util::force_any_val;
412405

413406
thread_local! {
@@ -477,6 +470,28 @@ pub(crate) mod tests {
477470
) -> Result<T, EvalError> {
478471
TEST_CTX.with(|ctx| try_eval_out(expr, ctx))
479472
}
473+
}
474+
475+
#[cfg(test)]
476+
#[allow(clippy::unwrap_used, clippy::expect_used)]
477+
mod test {
478+
use ergotree_ir::{
479+
chain::context::Context,
480+
ergo_tree::ErgoTree,
481+
mir::{
482+
bin_op::{BinOp, BinOpKind, RelationOp},
483+
block::BlockValue,
484+
expr::Expr,
485+
val_def::ValDef,
486+
val_use::ValUse,
487+
},
488+
sigma_protocol::sigma_boolean::SigmaBoolean,
489+
types::stype::SType,
490+
};
491+
use expect_test::expect;
492+
use sigma_test_util::force_any_val;
493+
494+
use crate::eval::reduce_to_crypto;
480495

481496
#[test]
482497
fn diag_on_reduced_to_false() {

ergotree-interpreter/src/eval/and.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ impl Evaluable for And {
2323
#[allow(clippy::panic)]
2424
#[cfg(test)]
2525
mod tests {
26-
use crate::eval::tests::eval_out;
26+
use crate::eval::test_util::eval_out;
2727
use ergotree_ir::chain::context::Context;
2828

2929
use super::*;

ergotree-interpreter/src/eval/apply.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ mod tests {
6868
use ergotree_ir::mir::val_use::ValUse;
6969
use ergotree_ir::types::stype::SType;
7070

71-
use crate::eval::tests::eval_out_wo_ctx;
71+
use crate::eval::test_util::eval_out_wo_ctx;
7272

7373
use super::*;
7474

ergotree-interpreter/src/eval/atleast.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -63,15 +63,15 @@ impl Evaluable for Atleast {
6363
mod tests {
6464
use alloc::sync::Arc;
6565

66-
use crate::eval::tests::try_eval_out_wo_ctx;
66+
use crate::eval::test_util::try_eval_out_wo_ctx;
6767
use ergotree_ir::mir::constant::Constant;
6868
use ergotree_ir::mir::constant::Literal;
6969
use ergotree_ir::mir::value::CollKind;
7070
use ergotree_ir::sigma_protocol::sigma_boolean::SigmaBoolean;
7171
use ergotree_ir::sigma_protocol::sigma_boolean::SigmaConjecture;
7272
use ergotree_ir::types::stype::SType;
7373

74-
use crate::eval::tests::eval_out;
74+
use crate::eval::test_util::eval_out;
7575
use ergotree_ir::chain::context::Context;
7676

7777
use super::*;

ergotree-interpreter/src/eval/bin_op.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -349,8 +349,8 @@ impl Evaluable for BinOp {
349349
#[allow(clippy::unwrap_used)]
350350
mod tests {
351351
use super::*;
352-
use crate::eval::tests::eval_out_wo_ctx;
353-
use crate::eval::tests::try_eval_out_wo_ctx;
352+
use crate::eval::test_util::eval_out_wo_ctx;
353+
use crate::eval::test_util::try_eval_out_wo_ctx;
354354
use alloc::boxed::Box;
355355
use ergotree_ir::mir::constant::Constant;
356356
use ergotree_ir::mir::expr::Expr;

ergotree-interpreter/src/eval/bit_inversion.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ impl Evaluable for BitInversion {
3232
mod tests {
3333

3434
use super::*;
35-
use crate::eval::tests::try_eval_out_wo_ctx;
35+
use crate::eval::test_util::try_eval_out_wo_ctx;
3636
use ergotree_ir::bigint256::BigInt256;
3737
use ergotree_ir::mir::constant::Constant;
3838
use ergotree_ir::mir::constant::TryExtractFrom;

0 commit comments

Comments
 (0)