Skip to content

Commit 4b8e628

Browse files
committed
intermediate bytecode: mv intermediate instruction
1 parent a834a6e commit 4b8e628

File tree

2 files changed

+225
-222
lines changed

2 files changed

+225
-222
lines changed
Lines changed: 205 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,205 @@
1+
use std::fmt;
2+
3+
use super::{HighLevelOperation, IntermediaryMemOrFpOrConstant, IntermediateValue};
4+
use crate::{bytecode::operation::Operation, lang::ConstExpression};
5+
6+
#[derive(Debug, Clone)]
7+
pub enum IntermediateInstruction {
8+
Computation {
9+
operation: Operation,
10+
arg_a: IntermediateValue,
11+
arg_c: IntermediateValue,
12+
res: IntermediateValue,
13+
},
14+
Deref {
15+
shift_0: ConstExpression,
16+
shift_1: ConstExpression,
17+
res: IntermediaryMemOrFpOrConstant,
18+
}, // res = m[m[fp + shift_0]]
19+
Panic,
20+
Jump {
21+
dest: IntermediateValue,
22+
updated_fp: Option<IntermediateValue>,
23+
},
24+
JumpIfNotZero {
25+
condition: IntermediateValue,
26+
dest: IntermediateValue,
27+
updated_fp: Option<IntermediateValue>,
28+
},
29+
Poseidon2_16 {
30+
arg_a: IntermediateValue, // vectorized pointer, of size 1
31+
arg_b: IntermediateValue, // vectorized pointer, of size 1
32+
res: IntermediateValue, // vectorized pointer, of size 2
33+
},
34+
Poseidon2_24 {
35+
arg_a: IntermediateValue, // vectorized pointer, of size 2 (2 first inputs)
36+
arg_b: IntermediateValue, // vectorized pointer, of size 1 (3rd = last input)
37+
res: IntermediateValue, // vectorized pointer, of size 1 (3rd = last output)
38+
},
39+
DotProduct {
40+
arg0: IntermediateValue, // vectorized pointer
41+
arg1: IntermediateValue, // vectorized pointer
42+
res: IntermediateValue, // vectorized pointer
43+
size: ConstExpression,
44+
},
45+
MultilinearEval {
46+
coeffs: IntermediateValue, // vectorized pointer, chunk size = 2^n_vars
47+
point: IntermediateValue, // vectorized pointer, of size `n_vars`
48+
res: IntermediateValue, // vectorized pointer, of size 1
49+
n_vars: ConstExpression,
50+
},
51+
// HINTS (does not appears in the final bytecode)
52+
Inverse {
53+
// If the value is zero, it will return zero.
54+
arg: IntermediateValue, // the value to invert
55+
res_offset: usize, // m[fp + res_offset] will contain the result
56+
},
57+
RequestMemory {
58+
offset: ConstExpression, // m[fp + offset] where the hint will be stored
59+
size: IntermediateValue, // the hint
60+
vectorized: bool, // if true, will be 8-alligned, and the returned pointer will be "divied" by 8 (i.e. everything is in chunks of 8 field elements)
61+
},
62+
DecomposeBits {
63+
res_offset: usize, // m[fp + res_offset..fp + res_offset + 31] will contain the decomposed bits
64+
to_decompose: IntermediateValue,
65+
},
66+
Print {
67+
line_info: String, // information about the line where the print occurs
68+
content: Vec<IntermediateValue>, // values to print
69+
},
70+
}
71+
72+
impl IntermediateInstruction {
73+
#[must_use]
74+
pub fn computation(
75+
operation: HighLevelOperation,
76+
arg_a: IntermediateValue,
77+
arg_c: IntermediateValue,
78+
res: IntermediateValue,
79+
) -> Self {
80+
match operation {
81+
HighLevelOperation::Add => Self::Computation {
82+
operation: Operation::Add,
83+
arg_a,
84+
arg_c,
85+
res,
86+
},
87+
HighLevelOperation::Mul => Self::Computation {
88+
operation: Operation::Mul,
89+
arg_a,
90+
arg_c,
91+
res,
92+
},
93+
HighLevelOperation::Sub => Self::Computation {
94+
operation: Operation::Add,
95+
arg_a: res,
96+
arg_c,
97+
res: arg_a,
98+
},
99+
HighLevelOperation::Div => Self::Computation {
100+
operation: Operation::Mul,
101+
arg_a: res,
102+
arg_c,
103+
res: arg_a,
104+
},
105+
HighLevelOperation::Exp => unreachable!(),
106+
}
107+
}
108+
109+
#[must_use]
110+
pub const fn equality(left: IntermediateValue, right: IntermediateValue) -> Self {
111+
Self::Computation {
112+
operation: Operation::Add,
113+
arg_a: left,
114+
arg_c: IntermediateValue::Constant(ConstExpression::zero()),
115+
res: right,
116+
}
117+
}
118+
}
119+
120+
impl fmt::Display for IntermediateInstruction {
121+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
122+
match self {
123+
Self::Deref {
124+
shift_0,
125+
shift_1,
126+
res,
127+
} => write!(f, "{res} = m[m[fp + {shift_0}] + {shift_1}]"),
128+
Self::DotProduct {
129+
arg0,
130+
arg1,
131+
res,
132+
size,
133+
} => write!(f, "dot_product({arg0}, {arg1}, {res}, {size})"),
134+
Self::MultilinearEval {
135+
coeffs,
136+
point,
137+
res,
138+
n_vars,
139+
} => write!(f, "multilinear_eval({coeffs}, {point}, {res}, {n_vars})"),
140+
Self::DecomposeBits {
141+
res_offset,
142+
to_decompose,
143+
} => {
144+
write!(f, "m[fp + {res_offset}..] = decompose_bits({to_decompose})")
145+
}
146+
Self::Computation {
147+
operation,
148+
arg_a,
149+
arg_c,
150+
res,
151+
} => {
152+
write!(f, "{res} = {arg_a} {operation} {arg_c}")
153+
}
154+
Self::Panic => write!(f, "panic"),
155+
Self::Jump { dest, updated_fp } => {
156+
if let Some(fp) = updated_fp {
157+
write!(f, "jump {dest} with fp = {fp}")
158+
} else {
159+
write!(f, "jump {dest}")
160+
}
161+
}
162+
Self::JumpIfNotZero {
163+
condition,
164+
dest,
165+
updated_fp,
166+
} => {
167+
if let Some(fp) = updated_fp {
168+
write!(f, "jump_if_not_zero {condition} to {dest} with fp = {fp}")
169+
} else {
170+
write!(f, "jump_if_not_zero {condition} to {dest}")
171+
}
172+
}
173+
Self::Poseidon2_16 { arg_a, arg_b, res } => {
174+
write!(f, "{arg_a} = poseidon2_16({arg_b}, {res})")
175+
}
176+
Self::Poseidon2_24 { arg_a, arg_b, res } => {
177+
write!(f, "{res} = poseidon2_24({arg_a}, {arg_b})")
178+
}
179+
Self::Inverse { arg, res_offset } => {
180+
write!(f, "m[fp + {res_offset}] = inverse({arg})")
181+
}
182+
Self::RequestMemory {
183+
offset,
184+
size,
185+
vectorized,
186+
} => write!(
187+
f,
188+
"m[fp + {}] = {}({})",
189+
offset,
190+
if *vectorized { "malloc_vec" } else { "malloc" },
191+
size,
192+
),
193+
Self::Print { line_info, content } => write!(
194+
f,
195+
"print {}: {}",
196+
line_info,
197+
content
198+
.iter()
199+
.map(ToString::to_string)
200+
.collect::<Vec<_>>()
201+
.join(", ")
202+
),
203+
}
204+
}
205+
}

0 commit comments

Comments
 (0)