ocl_include/parse/
parser.rs1use super::context::Context;
2use crate::{node::Node, source::Source};
3use std::{
4 cell::RefCell,
5 collections::hash_map::HashMap,
6 io,
7 path::{Path, PathBuf},
8};
9
10pub struct FileCacheEntry {
11 pub occured: usize,
12}
13impl FileCacheEntry {
14 pub fn new() -> Self {
15 Self { occured: 1 }
16 }
17}
18pub type FileCache = HashMap<PathBuf, FileCacheEntry>;
19
20pub type Flags = HashMap<String, bool>;
21
22pub struct Parser {
23 source: Box<dyn Source>,
24 flags: Flags,
25 file_cache: RefCell<FileCache>,
26}
27
28#[derive(Default)]
29pub struct ParserBuilder {
30 sources: Vec<Box<dyn Source>>,
31 flags: Flags,
32}
33
34impl ParserBuilder {
35 pub fn add_source<S: Source + 'static>(mut self, source: S) -> Self {
36 self.sources.push(Box::new(source));
37 self
38 }
39
40 pub fn add_flag(mut self, name: String, value: bool) -> Self {
41 self.flags.insert(name, value);
42 self
43 }
44
45 pub fn build(self) -> Parser {
46 Parser::new(Box::new(self.sources), self.flags)
47 }
48}
49
50impl Parser {
51 pub fn new(source: Box<dyn Source>, flags: Flags) -> Self {
52 Self {
53 source,
54 flags,
55 file_cache: RefCell::new(HashMap::new()),
56 }
57 }
58
59 pub fn builder() -> ParserBuilder {
60 ParserBuilder::default()
61 }
62
63 pub fn parse(&self, main: &Path) -> io::Result<Node> {
67 let mut file_cache = self.file_cache.borrow_mut();
68 let mut context = Context::new(self.source.as_ref(), &self.flags, &mut file_cache);
69 context.build_tree(main, None).and_then(|root| {
70 root.ok_or_else(|| {
71 io::Error::new(
72 io::ErrorKind::NotFound,
73 format!("Root file {:?} not found", main),
74 )
75 })
76 })
77 }
78}