pub use middle::typing::ast::*;
use back::compiler::rule::*;
use quote::quote;
pub struct GrammarCompiler
{
grammar: TGrammar
}
impl GrammarCompiler
{
pub fn compile(grammar: TGrammar) -> proc_macro2::TokenStream {
let compiler = GrammarCompiler::new(grammar);
let mod_content = compiler.compile_mod_content();
let result = compiler.compile_grammar_module(mod_content);
result
}
fn new(grammar: TGrammar) -> GrammarCompiler {
GrammarCompiler {
grammar: grammar
}
}
fn compile_grammar_module(&self, module_content: Vec<syn::Item>) -> proc_macro2::TokenStream {
quote!(
#[allow(unused_imports)]
use oak_runtime::stream::*;
#[allow(unused_imports)]
use oak_runtime::str_stream::StrStream;
#[allow(unused_imports)]
use std::ops::Range;
#(#module_content)*
)
}
fn compile_mod_content(&self) -> Vec<syn::Item> {
let mut mod_content = self.grammar.rust_items.clone();
mod_content.extend(self.compile_rules().into_iter());
mod_content.extend(self.grammar.rust_functions.values().cloned()
.map(syn::Item::Fn));
mod_content
}
fn compile_rules(&self) -> Vec<syn::Item> {
self.grammar.rules.iter()
.flat_map(|rule| RuleCompiler::compile(&self.grammar, rule.clone()).into_iter())
.collect()
}
}