add instruction to set the degree

This commit is contained in:
schaeff
2023-03-27 15:57:15 +02:00
committed by chriseth
parent 07b5e65eea
commit 7a24d59da8
10 changed files with 56 additions and 70 deletions

View File

@@ -7,17 +7,13 @@ use crate::parser::asm_ast::*;
use crate::parser::ast::*;
use crate::utils::ParseError;
pub fn compile<'a>(
file_name: Option<&str>,
input: &'a str,
row_count: DegreeType,
) -> Result<PILFile, ParseError<'a>> {
// TODO define the row count / poly degree in the assembly file.
parser::parse_asm(file_name, input).map(|ast| ASMPILConverter::new().convert(ast, row_count))
pub fn compile<'a>(file_name: Option<&str>, input: &'a str) -> Result<PILFile, ParseError<'a>> {
parser::parse_asm(file_name, input).map(|ast| ASMPILConverter::new().convert(ast))
}
#[derive(Default)]
struct ASMPILConverter {
degree_exponent: u32,
pil: Vec<Statement>,
pc_name: Option<String>,
registers: BTreeMap<String, Register>,
@@ -34,11 +30,34 @@ impl ASMPILConverter {
Default::default()
}
fn convert(&mut self, input: ASMFile, max_steps: DegreeType) -> PILFile {
fn set_degree(&mut self, degree: DegreeType) {
// check the degree is a power of 2
assert!(
degree.is_power_of_two(),
"Degree should be a power of two, found {}",
degree
);
self.degree_exponent = degree.ilog2();
}
fn degree(&self) -> DegreeType {
1 << self.degree_exponent
}
fn convert(&mut self, input: ASMFile) -> PILFile {
self.set_degree(1024);
let mut statements = input.0.iter().peekable();
if let Some(ASMStatement::Degree(_, degree)) = statements.peek() {
self.set_degree(crate::number::abstract_to_degree(degree));
statements.next();
}
self.pil.push(Statement::Namespace(
0,
"Assembly".to_string(),
Expression::Number(AbstractNumberType::from(max_steps)),
Expression::Number(AbstractNumberType::from(self.degree())),
));
self.pil.push(Statement::PolynomialConstantDefinition(
0,
@@ -46,8 +65,11 @@ impl ASMPILConverter {
FunctionDefinition::Array(vec![build_number(1.into())]),
));
for statement in &input.0 {
for statement in statements {
match statement {
ASMStatement::Degree(..) => {
panic!("The degree statement is only supported at the start of the asm source");
}
ASMStatement::RegisterDeclaration(start, name, flags) => {
self.handle_register_declaration(flags, name, start);
}
@@ -850,7 +872,7 @@ pol constant p_reg_write_X_CNT = [1, 0, 0, 0, 0, 0, 0, 0, 0];
"#;
let file_name = "tests/asm_data/simple_sum.asm";
let contents = fs::read_to_string(file_name).unwrap();
let pil = compile(Some(file_name), &contents, 1024).unwrap();
let pil = compile(Some(file_name), &contents).unwrap();
assert_eq!(format!("{pil}").trim(), expectation.trim());
}
}

View File

@@ -24,11 +24,6 @@ enum Commands {
#[arg(default_value_t = String::new())]
inputs: String,
/// Number of rows (degree of the polynomials).
#[arg(short, long)]
#[arg(default_value_t = 1024)]
rows: u64,
/// Directory for output files.
#[arg(short, long)]
#[arg(default_value_t = String::from("."))]
@@ -56,11 +51,6 @@ enum Commands {
#[arg(default_value_t = String::new())]
inputs: String,
/// Number of rows (degree of the polynomials).
#[arg(short, long)]
#[arg(default_value_t = 1024)]
rows: u64,
/// Directory for output files.
#[arg(short, long)]
#[arg(default_value_t = String::from("."))]
@@ -87,11 +77,6 @@ enum Commands {
#[arg(default_value_t = String::new())]
inputs: String,
/// Number of rows (degree of the polynomials).
#[arg(short, long)]
#[arg(default_value_t = 1024)]
rows: u64,
/// Output directory for PIL file, json file and fixed and witness column data.
#[arg(short, long)]
#[arg(default_value_t = String::from("."))]
@@ -140,7 +125,6 @@ fn main() {
Commands::Rust {
file,
inputs,
rows,
output_directory,
force,
verbose,
@@ -148,7 +132,6 @@ fn main() {
powdr::riscv::compile_rust(
&file,
split_inputs(&inputs),
rows,
Path::new(&output_directory),
force,
verbose,
@@ -157,7 +140,6 @@ fn main() {
Commands::RiscvAsm {
file,
inputs,
rows,
output_directory,
force,
verbose,
@@ -166,7 +148,6 @@ fn main() {
&file,
&file,
split_inputs(&inputs),
rows,
Path::new(&output_directory),
force,
verbose,
@@ -175,7 +156,6 @@ fn main() {
Commands::Asm {
file,
inputs,
rows,
output_directory,
force,
verbose,
@@ -183,7 +163,6 @@ fn main() {
powdr::compiler::compile_asm(
&file,
split_inputs(&inputs),
rows,
Path::new(&output_directory),
force,
verbose,

View File

@@ -54,7 +54,6 @@ pub fn compile_pil_ast(
pub fn compile_asm(
file_name: &str,
inputs: Vec<AbstractNumberType>,
rows: u64,
output_dir: &Path,
force_overwrite: bool,
verbose: bool,
@@ -64,7 +63,6 @@ pub fn compile_asm(
file_name,
&contents,
inputs,
rows,
output_dir,
force_overwrite,
verbose,
@@ -77,12 +75,11 @@ pub fn compile_asm_string(
file_name: &str,
contents: &str,
inputs: Vec<AbstractNumberType>,
rows: u64,
output_dir: &Path,
force_overwrite: bool,
verbose: bool,
) {
let pil = asm_compiler::compile(Some(file_name), contents, rows).unwrap_or_else(|err| {
let pil = asm_compiler::compile(Some(file_name), contents).unwrap_or_else(|err| {
eprintln!("Error parsing .asm file:");
err.output_to_stderr();
panic!();

View File

@@ -1,3 +1,5 @@
use crate::number::AbstractNumberType;
use super::ast::{Expression, SelectedExpressions, Statement};
#[derive(Debug, PartialEq, Eq)]
@@ -5,6 +7,7 @@ pub struct ASMFile(pub Vec<ASMStatement>);
#[derive(Debug, PartialEq, Eq, Clone)]
pub enum ASMStatement {
Degree(usize, AbstractNumberType),
RegisterDeclaration(usize, String, Option<RegisterFlag>),
InstructionDeclaration(
usize,

View File

@@ -138,6 +138,7 @@ ConstantFixed = {
ASMStatement: ASMStatement = {
Degree,
RegisterDeclaration,
InstructionDeclaration,
InlinePil,
@@ -146,6 +147,10 @@ ASMStatement: ASMStatement = {
Label,
}
Degree: ASMStatement = {
<@L> "degree" <Number> ";" => ASMStatement::Degree(<>)
}
RegisterDeclaration: ASMStatement = {
// TODO default update
<@L> "reg" <Identifier> <( "[" <RegisterFlag> "]" )?> ";" => ASMStatement::RegisterDeclaration(<>)

View File

@@ -13,7 +13,6 @@ pub mod parser;
pub fn compile_rust(
file_name: &str,
inputs: Vec<AbstractNumberType>,
rows: u64,
output_dir: &Path,
force_overwrite: bool,
verbose: bool,
@@ -37,7 +36,6 @@ pub fn compile_rust(
file_name,
riscv_asm_file_name.to_str().unwrap(),
inputs,
rows,
output_dir,
force_overwrite,
verbose,
@@ -51,7 +49,6 @@ pub fn compile_riscv_asm(
original_file_name: &str,
file_name: &str,
inputs: Vec<AbstractNumberType>,
rows: u64,
output_dir: &Path,
force_overwrite: bool,
verbose: bool,
@@ -80,7 +77,6 @@ pub fn compile_riscv_asm(
powdr_asm_file_name.to_str().unwrap(),
&powdr_asm,
inputs,
rows,
output_dir,
force_overwrite,
verbose,

View File

@@ -1,12 +1,12 @@
use common::verify_asm_string;
use powdr::number::{AbstractNumberType, DegreeType};
use powdr::number::AbstractNumberType;
use std::fs;
mod common;
fn verify_asm(file_name: &str, inputs: Vec<AbstractNumberType>, row_count: Option<DegreeType>) {
fn verify_asm(file_name: &str, inputs: Vec<AbstractNumberType>) {
let contents = fs::read_to_string(format!("./tests/asm_data/{file_name}")).unwrap();
verify_asm_string(file_name, &contents, inputs, row_count)
verify_asm_string(file_name, &contents, inputs)
}
#[test]
@@ -14,7 +14,6 @@ fn simple_sum_asm() {
verify_asm(
"simple_sum.asm",
[16, 4, 1, 2, 8, 5].iter().map(|&x| x.into()).collect(),
None,
);
}
@@ -23,31 +22,22 @@ fn palindrome() {
verify_asm(
"palindrome.asm",
[7, 1, 7, 3, 9, 3, 7, 1].iter().map(|&x| x.into()).collect(),
None,
);
}
#[test]
fn test_mem_read_write() {
verify_asm("mem_read_write.asm", Default::default(), None);
verify_asm("mem_read_write.asm", Default::default());
}
#[test]
fn test_multi_assign() {
verify_asm(
"multi_assign.asm",
[7].iter().map(|&x| x.into()).collect(),
None,
);
verify_asm("multi_assign.asm", [7].iter().map(|&x| x.into()).collect());
}
#[test]
fn test_bit_access() {
verify_asm(
"bit_access.asm",
[20].iter().map(|&x| x.into()).collect(),
None,
);
verify_asm("bit_access.asm", [20].iter().map(|&x| x.into()).collect());
}
#[test]
@@ -55,6 +45,5 @@ fn functional_instructions() {
verify_asm(
"functional_instructions.asm",
[20].iter().map(|&x| x.into()).collect(),
None,
);
}

View File

@@ -1,6 +1,8 @@
// Verfies that the input is a palindrome.
// Input: length, x_1, x_2, ..., x_length
degree 1024;
reg pc[@pc];
reg X[<=];
reg A;

View File

@@ -2,17 +2,11 @@ use std::{fs, path::Path, process::Command};
use itertools::Itertools;
use powdr::compiler;
use powdr::number::{AbstractNumberType, DegreeType};
use powdr::number::AbstractNumberType;
#[allow(unused)]
pub fn verify_asm_string(
file_name: &str,
contents: &str,
inputs: Vec<AbstractNumberType>,
row_count: Option<DegreeType>,
) {
let pil =
powdr::asm_compiler::compile(Some(file_name), contents, row_count.unwrap_or(1024)).unwrap();
pub fn verify_asm_string(file_name: &str, contents: &str, inputs: Vec<AbstractNumberType>) {
let pil = powdr::asm_compiler::compile(Some(file_name), contents).unwrap();
let pil_file_name = "asm.pil";
let temp_dir = mktemp::Temp::new_dir().unwrap();
assert!(compiler::compile_pil_ast(

View File

@@ -1,5 +1,5 @@
use common::verify_asm_string;
use powdr::number::{AbstractNumberType, DegreeType};
use powdr::number::AbstractNumberType;
mod common;
@@ -9,13 +9,12 @@ fn test_sum() {
verify(
case,
[16, 4, 1, 2, 8, 5].iter().map(|&x| x.into()).collect(),
None,
);
}
fn verify(case: &str, inputs: Vec<AbstractNumberType>, row_count: Option<DegreeType>) {
fn verify(case: &str, inputs: Vec<AbstractNumberType>) {
let riscv_asm = powdr::riscv::compile_rust_to_riscv_asm(&format!("tests/riscv_data/{case}"));
let powdr_asm = powdr::riscv::compiler::compile_riscv_asm(&riscv_asm);
verify_asm_string(&format!("{case}.asm"), &powdr_asm, inputs, row_count);
verify_asm_string(&format!("{case}.asm"), &powdr_asm, inputs);
}