Skip to content

Commit 56deeb9

Browse files
committed
Migrate execution to dynamic dispatch
1 parent 41685f6 commit 56deeb9

37 files changed

Lines changed: 749 additions & 748 deletions

fuzz/fuzz_lib/program.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,8 @@ impl Extractor<'_> {
4949
&mut self,
5050
ctx: &types::Context<'brand>,
5151
force_control: Option<ProgramControl>,
52-
) -> Option<Arc<ConstructNode<'brand, Core>>> {
53-
type ArcNode<'brand> = Arc<ConstructNode<'brand, Core>>;
52+
) -> Option<Arc<ConstructNode<'brand>>> {
53+
type ArcNode<'brand> = Arc<ConstructNode<'brand>>;
5454

5555
let mut stack: Vec<ArcNode> = vec![];
5656

@@ -165,7 +165,7 @@ impl Extractor<'_> {
165165
_ => {
166166
let extra_bits = usize::from(control >> 6);
167167
let idx = (extra_bits << 8) + usize::from(self.extract_u8()?);
168-
stack.push(ArcNode::jet(ctx, Core::ALL[idx % Core::ALL.len()]));
168+
stack.push(ArcNode::jet(ctx, &Core::ALL[idx % Core::ALL.len()]));
169169
}
170170
}
171171
}

fuzz/fuzz_targets/c_rust_merkle.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ fn do_test(data: &[u8]) {
3636

3737
let prog_iter = BitIter::from(program);
3838
let wit_iter = BitIter::from(witness);
39-
let rust_result = RedeemNode::<Elements>::decode(prog_iter, wit_iter);
39+
let rust_result = RedeemNode::decode::<_, _, Elements>(prog_iter, wit_iter);
4040

4141
match (c_result, rust_result) {
4242
(Ok(_), Err(e)) => panic!("C accepted code that Rust rejected: {}", e),

fuzz/fuzz_targets/decode_program.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ fn do_test(data: &[u8]) {
99

1010
let prog_iter = BitIter::new(data.iter().cloned());
1111
let wit_iter = BitIter::new(core::iter::repeat(0));
12-
if let Ok(program) = RedeemNode::<Core>::decode(prog_iter, wit_iter) {
12+
if let Ok(program) = RedeemNode::decode::<_, _, Core>(prog_iter, wit_iter) {
1313
let mut prog_reser = Vec::<u8>::new();
1414
let mut wit_reser = Vec::<u8>::new();
1515

fuzz/fuzz_targets/parse_human.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,9 @@ fn do_test(data: &[u8]) {
1212
Err(_) => return,
1313
};
1414

15-
if let Ok(program) = Forest::<Elements>::parse(s) {
15+
if let Ok(program) = Forest::parse::<Elements>(s) {
1616
let reserialize = program.string_serialize();
17-
let round_trip = Forest::<Elements>::parse(&reserialize).unwrap();
17+
let round_trip = Forest::parse::<Elements>(&reserialize).unwrap();
1818
assert_eq!(program, round_trip);
1919
}
2020
}

fuzz/fuzz_targets/regression_286.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@ fn do_test(data: &[u8]) {
3232
let prog = finalized.encode_to_vec();
3333
//println!("{}", simplicity::bitcoin::hex::DisplayHex::as_hex(&prog));
3434
let prog = BitIter::from(prog);
35-
let decode = CommitNode::<Core>::decode(prog).unwrap();
35+
let decode = CommitNode::decode::<_, Core>(prog).unwrap();
3636
assert_eq!(
3737
finalized, decode,
3838
"Constructed committed LHS; encoded and decoded to get RHS",

simpcli/src/main.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -75,9 +75,9 @@ impl Command {
7575
}
7676
}
7777

78-
fn parse_file(name: &str) -> Result<Forest<DefaultJet>, String> {
78+
fn parse_file(name: &str) -> Result<Forest, String> {
7979
let s = fs::read_to_string(name).map_err(|e| format!("failed to read file {}: {}", name, e))?;
80-
match Forest::parse(&s) {
80+
match Forest::parse::<DefaultJet>(&s) {
8181
Ok(prog) => Ok(prog),
8282
Err(mut errs) => {
8383
errs.add_context(std::sync::Arc::from(s));
@@ -154,16 +154,16 @@ fn main() -> Result<(), String> {
154154
let v = simplicity::base64::Engine::decode(&STANDARD, first_arg.as_bytes())
155155
.map_err(|e| format!("failed to parse base64: {}", e))?;
156156
let iter = BitIter::from(v.into_iter());
157-
let commit =
158-
CommitNode::decode(iter).map_err(|e| format!("failed to decode program: {}", e))?;
159-
let prog = Forest::<DefaultJet>::from_program(commit);
157+
let commit = CommitNode::decode::<_, DefaultJet>(iter)
158+
.map_err(|e| format!("failed to decode program: {}", e))?;
159+
let prog = Forest::from_program(commit);
160160
println!("{}", prog.string_serialize());
161161
}
162162
Command::Graph => {
163163
let v = simplicity::base64::Engine::decode(&STANDARD, first_arg.as_bytes())
164164
.map_err(|e| format!("failed to parse base64: {}", e))?;
165165
let iter = BitIter::from(v.into_iter());
166-
let commit = CommitNode::<DefaultJet>::decode(iter)
166+
let commit = CommitNode::decode::<_, DefaultJet>(iter)
167167
.map_err(|e| format!("failed to decode program: {}", e))?;
168168
println!("{}", commit.display_as_dot());
169169
}

src/analysis.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -370,7 +370,7 @@ impl NodeBounds {
370370
}
371371

372372
/// Node bounds for an arbitrary jet node
373-
pub fn jet<J: Jet>(jet: J) -> NodeBounds {
373+
pub fn jet(jet: &dyn Jet) -> NodeBounds {
374374
NodeBounds {
375375
extra_cells: 0,
376376
extra_frames: 0,

src/bit_encoding/bitwriter.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,6 @@ where
115115
#[cfg(test)]
116116
mod tests {
117117
use super::*;
118-
use crate::jet::Core;
119118
use crate::node::CoreConstructible;
120119
use crate::types;
121120
use crate::ConstructNode;
@@ -124,7 +123,7 @@ mod tests {
124123
#[test]
125124
fn vec() {
126125
types::Context::with_context(|ctx| {
127-
let program = Arc::<ConstructNode<Core>>::unit(&ctx);
126+
let program = Arc::<ConstructNode>::unit(&ctx);
128127
let _ = write_to_vec(|w| program.encode_without_witness(w));
129128
})
130129
}

src/bit_encoding/decode.rs

Lines changed: 32 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ use std::{cmp, error, fmt};
2121

2222
use super::bititer::{u2, DecodeNaturalError};
2323

24-
type ArcNode<'brand, J> = Arc<ConstructNode<'brand, J>>;
24+
type ArcNode<'brand> = Arc<ConstructNode<'brand>>;
2525

2626
/// Decoding error
2727
#[non_exhaustive]
@@ -104,7 +104,7 @@ impl error::Error for Error {
104104
}
105105

106106
#[derive(Debug)]
107-
enum DecodeNode<J: Jet> {
107+
enum DecodeNode {
108108
Iden,
109109
Unit,
110110
InjL(usize),
@@ -119,14 +119,14 @@ enum DecodeNode<J: Jet> {
119119
Witness,
120120
Fail(FailEntropy),
121121
Hidden(Cmr),
122-
Jet(J),
122+
Jet(Box<dyn Jet>),
123123
Word(Word),
124124
}
125125

126-
impl<J: Jet> DagLike for (usize, &'_ [DecodeNode<J>]) {
127-
type Node = DecodeNode<J>;
126+
impl DagLike for (usize, &'_ [DecodeNode]) {
127+
type Node = DecodeNode;
128128

129-
fn data(&self) -> &DecodeNode<J> {
129+
fn data(&self) -> &DecodeNode {
130130
&self.1[self.0]
131131
}
132132

@@ -156,14 +156,14 @@ impl<J: Jet> DagLike for (usize, &'_ [DecodeNode<J>]) {
156156
pub fn decode_expression<'brand, I: Iterator<Item = u8>, J: Jet>(
157157
ctx: &types::Context<'brand>,
158158
bits: &mut BitIter<I>,
159-
) -> Result<ArcNode<'brand, J>, Error> {
160-
enum Converted<'brand, J: Jet> {
161-
Node(ArcNode<'brand, J>),
159+
) -> Result<ArcNode<'brand>, Error> {
160+
enum Converted<'brand> {
161+
Node(ArcNode<'brand>),
162162
Hidden(Cmr),
163163
}
164164
use Converted::{Hidden, Node};
165-
impl<'brand, J: Jet> Converted<'brand, J> {
166-
fn get(&self) -> Result<&ArcNode<'brand, J>, Error> {
165+
impl<'brand> Converted<'brand> {
166+
fn get(&self) -> Result<&ArcNode<'brand>, Error> {
167167
match self {
168168
Node(arc) => Ok(arc),
169169
Hidden(_) => Err(Error::HiddenNode),
@@ -176,57 +176,57 @@ pub fn decode_expression<'brand, I: Iterator<Item = u8>, J: Jet>(
176176

177177
let mut nodes = Vec::with_capacity(cmp::min(len, 10_000));
178178
for _ in 0..len {
179-
let new_node = decode_node(bits, nodes.len())?;
179+
let new_node = decode_node::<I, J>(bits, nodes.len())?;
180180
nodes.push(new_node);
181181
}
182182

183183
// It is a sharing violation for any hidden node to be repeated. Track them in this set.
184184
let mut hidden_set = HashSet::<Cmr>::new();
185185
// Convert the DecodeNode structure into a CommitNode structure
186-
let mut converted = Vec::<Converted<J>>::with_capacity(len);
186+
let mut converted = Vec::<Converted>::with_capacity(len);
187187
for data in (nodes.len() - 1, &nodes[..]).post_order_iter::<InternalSharing>() {
188188
// Check canonical order as we go
189189
if data.index != data.node.0 {
190190
return Err(Error::NotInCanonicalOrder);
191191
}
192192

193-
let new = match nodes[data.node.0] {
193+
let new = match &nodes[data.node.0] {
194194
DecodeNode::Unit => Node(ArcNode::unit(ctx)),
195195
DecodeNode::Iden => Node(ArcNode::iden(ctx)),
196-
DecodeNode::InjL(i) => Node(ArcNode::injl(converted[i].get()?)),
197-
DecodeNode::InjR(i) => Node(ArcNode::injr(converted[i].get()?)),
198-
DecodeNode::Take(i) => Node(ArcNode::take(converted[i].get()?)),
199-
DecodeNode::Drop(i) => Node(ArcNode::drop_(converted[i].get()?)),
196+
DecodeNode::InjL(i) => Node(ArcNode::injl(converted[*i].get()?)),
197+
DecodeNode::InjR(i) => Node(ArcNode::injr(converted[*i].get()?)),
198+
DecodeNode::Take(i) => Node(ArcNode::take(converted[*i].get()?)),
199+
DecodeNode::Drop(i) => Node(ArcNode::drop_(converted[*i].get()?)),
200200
DecodeNode::Comp(i, j) => {
201-
Node(ArcNode::comp(converted[i].get()?, converted[j].get()?)?)
201+
Node(ArcNode::comp(converted[*i].get()?, converted[*j].get()?)?)
202202
}
203203
DecodeNode::Case(i, j) => {
204204
// Case is a special case, since it uniquely is allowed to have hidden
205205
// children (but only one!) in which case it becomes an assertion.
206-
match (&converted[i], &converted[j]) {
206+
match (&converted[*i], &converted[*j]) {
207207
(Node(left), Node(right)) => Node(ArcNode::case(left, right)?),
208208
(Node(left), Hidden(cmr)) => Node(ArcNode::assertl(left, *cmr)?),
209209
(Hidden(cmr), Node(right)) => Node(ArcNode::assertr(*cmr, right)?),
210210
(Hidden(_), Hidden(_)) => return Err(Error::BothChildrenHidden),
211211
}
212212
}
213213
DecodeNode::Pair(i, j) => {
214-
Node(ArcNode::pair(converted[i].get()?, converted[j].get()?)?)
214+
Node(ArcNode::pair(converted[*i].get()?, converted[*j].get()?)?)
215215
}
216-
DecodeNode::Disconnect1(i) => Node(ArcNode::disconnect(converted[i].get()?, &None)?),
216+
DecodeNode::Disconnect1(i) => Node(ArcNode::disconnect(converted[*i].get()?, &None)?),
217217
DecodeNode::Disconnect(i, j) => Node(ArcNode::disconnect(
218-
converted[i].get()?,
219-
&Some(Arc::clone(converted[j].get()?)),
218+
converted[*i].get()?,
219+
&Some(Arc::clone(converted[*j].get()?)),
220220
)?),
221221
DecodeNode::Witness => Node(ArcNode::witness(ctx, None)),
222-
DecodeNode::Fail(entropy) => Node(ArcNode::fail(ctx, entropy)),
222+
DecodeNode::Fail(entropy) => Node(ArcNode::fail(ctx, *entropy)),
223223
DecodeNode::Hidden(cmr) => {
224-
if !hidden_set.insert(cmr) {
224+
if !hidden_set.insert(*cmr) {
225225
return Err(Error::SharingNotMaximal);
226226
}
227-
Hidden(cmr)
227+
Hidden(*cmr)
228228
}
229-
DecodeNode::Jet(j) => Node(ArcNode::jet(ctx, j)),
229+
DecodeNode::Jet(j) => Node(ArcNode::jet(ctx, j.as_ref())),
230230
DecodeNode::Word(ref w) => Node(ArcNode::const_word(ctx, w.shallow_clone())),
231231
};
232232
converted.push(new);
@@ -240,12 +240,12 @@ pub fn decode_expression<'brand, I: Iterator<Item = u8>, J: Jet>(
240240
fn decode_node<I: Iterator<Item = u8>, J: Jet>(
241241
bits: &mut BitIter<I>,
242242
index: usize,
243-
) -> Result<DecodeNode<J>, Error> {
243+
) -> Result<DecodeNode, Error> {
244244
// First bit: 1 for jets/words, 0 for normal combinators
245245
if bits.read_bit()? {
246246
// Second bit: 1 for jets, 0 for words
247247
if bits.read_bit()? {
248-
J::decode(bits).map(|jet| DecodeNode::Jet(jet))
248+
J::decode(bits).map(|jet| DecodeNode::Jet(Box::new(jet)))
249249
} else {
250250
let n = bits.read_natural(Some(32))?;
251251
let word = Word::from_bits(bits, n - 1)?;
@@ -321,10 +321,10 @@ mod tests {
321321
});
322322
// ...but NOT as a CommitNode
323323
let iter = BitIter::from(&justjet[..]);
324-
CommitNode::<Core>::decode(iter).unwrap_err();
324+
CommitNode::decode::<_, Core>(iter).unwrap_err();
325325
// ...or as a RedeemNode
326326
let iter = BitIter::from(&justjet[..]);
327-
RedeemNode::<Core>::decode(iter, BitIter::from(&[][..])).unwrap_err();
327+
RedeemNode::decode::<_, _, Core>(iter, BitIter::from(&[][..])).unwrap_err();
328328
}
329329

330330
#[test]

src/bit_encoding/encode.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
//! to read it visually the way you can with Bitcoin Script.
99
1010
use crate::dag::{Dag, DagLike, PostOrderIterItem, SharingTracker};
11-
use crate::jet::Jet;
1211
use crate::node::{self, Disconnectable};
1312
use crate::{BitWriter, Cmr, Value};
1413

0 commit comments

Comments
 (0)