mirror of
https://github.com/ProvableHQ/leo.git
synced 2024-11-23 15:15:47 +03:00
refactor compiler methods
This commit is contained in:
parent
52810588ff
commit
46f585e2ff
@ -59,6 +59,9 @@ pub struct Compiler<F: Field + PrimeField, G: GroupType<F>> {
|
||||
}
|
||||
|
||||
impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
///
|
||||
/// Returns a new Leo program compiler.
|
||||
///
|
||||
pub fn new(package_name: String, main_file_path: PathBuf, output_directory: PathBuf) -> Self {
|
||||
Self {
|
||||
package_name: package_name.clone(),
|
||||
@ -72,8 +75,51 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
}
|
||||
}
|
||||
|
||||
///
|
||||
/// Parses program files.
|
||||
///
|
||||
/// Returns a compiler struct that stores the typed program abstract syntax trees (ast).
|
||||
///
|
||||
pub fn parse_program_without_input(
|
||||
package_name: String,
|
||||
main_file_path: PathBuf,
|
||||
output_directory: PathBuf,
|
||||
) -> Result<Self, CompilerError> {
|
||||
let mut compiler = Self::new(package_name, main_file_path, output_directory);
|
||||
|
||||
compiler.parse_and_check_program()?;
|
||||
|
||||
Ok(compiler)
|
||||
}
|
||||
|
||||
///
|
||||
/// Parses input, state, and program files.
|
||||
///
|
||||
/// Returns a compiler struct that stores the typed input and typed program abstract syntax trees (ast).
|
||||
///
|
||||
pub fn parse_program_with_input(
|
||||
package_name: String,
|
||||
main_file_path: PathBuf,
|
||||
output_directory: PathBuf,
|
||||
input_string: &str,
|
||||
input_path: &Path,
|
||||
state_string: &str,
|
||||
state_path: &Path,
|
||||
) -> Result<Self, CompilerError> {
|
||||
let mut compiler = Self::new(package_name, main_file_path, output_directory);
|
||||
|
||||
compiler.parse_input(input_string, input_path, state_string, state_path)?;
|
||||
|
||||
compiler.parse_and_check_program()?;
|
||||
|
||||
Ok(compiler)
|
||||
}
|
||||
|
||||
///
|
||||
/// Parse the input and state files.
|
||||
///
|
||||
/// Stores a typed ast of all input variables to the program.
|
||||
///
|
||||
pub fn parse_input(
|
||||
&mut self,
|
||||
input_string: &str,
|
||||
@ -106,51 +152,59 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Parses program files.
|
||||
/// Returns a compiler struct that stores the typed program abstract syntax trees (ast).
|
||||
pub fn parse_program_without_input(
|
||||
package_name: String,
|
||||
main_file_path: PathBuf,
|
||||
output_directory: PathBuf,
|
||||
) -> Result<Self, CompilerError> {
|
||||
let mut compiler = Self::new(package_name, main_file_path, output_directory);
|
||||
///
|
||||
/// Runs program parser and program checker consecutively.
|
||||
///
|
||||
pub(crate) fn parse_and_check_program(&mut self) -> Result<(), CompilerError> {
|
||||
self.parse_program()?;
|
||||
|
||||
compiler.parse_program()?;
|
||||
|
||||
Ok(compiler)
|
||||
}
|
||||
|
||||
/// Parses input, state, and program files.
|
||||
/// Returns a compiler struct that stores the typed input and typed program abstract syntax trees (ast).
|
||||
pub fn parse_program_with_input(
|
||||
package_name: String,
|
||||
main_file_path: PathBuf,
|
||||
output_directory: PathBuf,
|
||||
input_string: &str,
|
||||
input_path: &Path,
|
||||
state_string: &str,
|
||||
state_path: &Path,
|
||||
) -> Result<Self, CompilerError> {
|
||||
let mut compiler = Self::new(package_name, main_file_path, output_directory);
|
||||
|
||||
compiler.parse_input(input_string, input_path, state_string, state_path)?;
|
||||
|
||||
compiler.parse_program()?;
|
||||
|
||||
Ok(compiler)
|
||||
self.check_program()
|
||||
}
|
||||
|
||||
///
|
||||
/// Parses the Leo program file, constructs a syntax tree, and generates a program.
|
||||
#[allow(deprecated)]
|
||||
///
|
||||
pub(crate) fn parse_program(&mut self) -> Result<(), CompilerError> {
|
||||
// Use the parser to construct the abstract syntax tree.
|
||||
// Load the program file.
|
||||
let program_string = LeoAst::load_file(&self.main_file_path)?;
|
||||
|
||||
self.parse_program_from_string(&program_string)
|
||||
// Use the parser to construct the abstract syntax tree.
|
||||
let ast = LeoAst::new(&self.main_file_path, &program_string).map_err(|mut e| {
|
||||
e.set_path(&self.main_file_path);
|
||||
|
||||
e
|
||||
})?;
|
||||
|
||||
// Use the typed parser to construct the typed syntax tree.
|
||||
let typed_tree = LeoTypedAst::new(&self.package_name, &ast);
|
||||
|
||||
self.program = typed_tree.into_repr();
|
||||
self.imported_programs = ImportParser::parse(&self.program)?;
|
||||
|
||||
tracing::debug!("Program parsing complete\n{:#?}", self.program);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
///
|
||||
/// Runs static and dynamic type checks on the program, imports, and input.
|
||||
///
|
||||
pub(crate) fn check_program(&self) -> Result<(), CompilerError> {
|
||||
// Run static check on program.
|
||||
let symbol_table = StaticCheck::new(&self.program, &self.imported_programs, &self.program_input)?;
|
||||
|
||||
// Run dynamic check on program.
|
||||
DynamicCheck::new(&self.program, symbol_table)?;
|
||||
|
||||
tracing::debug!("Program checks complete");
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
///
|
||||
/// Parses the Leo program string, constructs a syntax tree, and generates a program.
|
||||
/// Used for testing only.
|
||||
///
|
||||
#[deprecated(note = "Please use the 'parse_program' method instead.")]
|
||||
pub fn parse_program_from_string(&mut self, program_string: &str) -> Result<(), CompilerError> {
|
||||
// Use the given bytes to construct the abstract syntax tree.
|
||||
@ -180,12 +234,16 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
///
|
||||
/// Manually sets main function input
|
||||
///
|
||||
pub fn set_main_input(&mut self, input: MainInput) {
|
||||
self.program_input.set_main_input(input);
|
||||
}
|
||||
|
||||
///
|
||||
/// Verifies the input to the program
|
||||
///
|
||||
pub fn verify_local_data_commitment(
|
||||
&self,
|
||||
system_parameters: &SystemParameters<Components>,
|
||||
@ -195,6 +253,9 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
Ok(result)
|
||||
}
|
||||
|
||||
///
|
||||
/// Returns a Sha256 checksum of the program file.
|
||||
///
|
||||
pub fn checksum(&self) -> Result<String, CompilerError> {
|
||||
// Read in the main file as string
|
||||
let unparsed_file = fs::read_to_string(&self.main_file_path)
|
||||
@ -208,7 +269,9 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
Ok(hex::encode(hash))
|
||||
}
|
||||
|
||||
///
|
||||
/// Synthesizes the circuit without program input to verify correctness.
|
||||
///
|
||||
pub fn compile_constraints<CS: ConstraintSystem<F>>(self, cs: &mut CS) -> Result<OutputBytes, CompilerError> {
|
||||
let path = self.main_file_path;
|
||||
|
||||
@ -245,26 +308,6 @@ impl<F: Field + PrimeField, G: GroupType<F>> Compiler<F, G> {
|
||||
},
|
||||
)
|
||||
}
|
||||
|
||||
pub fn to_bytes(&self) -> Result<Vec<u8>, CompilerError> {
|
||||
Ok(bincode::serialize(&self.program)?)
|
||||
}
|
||||
|
||||
pub fn from_bytes(bytes: &[u8]) -> Result<Self, CompilerError> {
|
||||
let program: Program = bincode::deserialize(bytes)?;
|
||||
let program_input = Input::new();
|
||||
|
||||
Ok(Self {
|
||||
package_name: program.name.clone(),
|
||||
main_file_path: PathBuf::new(),
|
||||
output_directory: PathBuf::new(),
|
||||
program,
|
||||
program_input,
|
||||
imported_programs: ImportParser::new(),
|
||||
_engine: PhantomData,
|
||||
_group: PhantomData,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: Field + PrimeField, G: GroupType<F>> ConstraintSynthesizer<F> for Compiler<F, G> {
|
||||
|
@ -199,13 +199,6 @@ pub(crate) fn expect_static_check_error(error: CompilerError) {
|
||||
assert!(is_static_check)
|
||||
}
|
||||
|
||||
// pub(crate) fn expect_synthesis_error(program: EdwardsTestCompiler) {
|
||||
// let mut cs = TestConstraintSystem::<Fq>::new();
|
||||
// let _output = program.generate_constraints_helper(&mut cs).unwrap();
|
||||
//
|
||||
// assert!(!cs.is_satisfied());
|
||||
// }
|
||||
|
||||
pub(crate) fn generate_main_input(input: Vec<(&str, Option<InputValue>)>) -> MainInput {
|
||||
let mut main_input = MainInput::new();
|
||||
|
||||
|
@ -4,7 +4,7 @@ version = "1.0.3"
|
||||
authors = [ "The Aleo Team <hello@aleo.org>" ]
|
||||
description = "Checks that a program is correct using type inference"
|
||||
homepage = "https://aleo.org"
|
||||
respository = "https://github.com/AleoHQ/leo"
|
||||
repository = "https://github.com/AleoHQ/leo"
|
||||
keywords = [
|
||||
"aleo",
|
||||
"cryptography",
|
||||
|
@ -4,7 +4,7 @@ version = "1.0.3"
|
||||
authors = [ "The Aleo Team <hello@aleo.org>"]
|
||||
description = "Import parser for Leo program package dependencies"
|
||||
homepage = "https://aleo.org"
|
||||
respository = "https://github.com/AleoHQ/leo"
|
||||
repository = "https://github.com/AleoHQ/leo"
|
||||
keywords = [
|
||||
"aleo",
|
||||
"cryptography",
|
||||
|
@ -4,7 +4,7 @@ version = "1.0.3"
|
||||
authors = [ "The Aleo Team <hello@aleo.org>" ]
|
||||
description = "Stores user-defined variables during type resolution"
|
||||
homepage = "https://aleo.org"
|
||||
respository = "https://github.com/AleoHQ/leo"
|
||||
repository = "https://github.com/AleoHQ/leo"
|
||||
keywords = [
|
||||
"aleo",
|
||||
"cryptography",
|
||||
|
Loading…
Reference in New Issue
Block a user