src/main.rs

Thu, 19 Oct 2023 23:25:34 -0500

author
Tuomo Valkonen <tuomov@iki.fi>
date
Thu, 19 Oct 2023 23:25:34 -0500
changeset 6
de1cf8032322
parent 3
cec573b16b46
child 7
68538da191c7
permissions
-rw-r--r--

Implement a more expansible parser

2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
1 // The main documentation is in the README.
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
2 #![doc = include_str!("../README.md")]
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
3
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
4 #![feature(trait_upcasting)]
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
5
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
6 use std::io;
3
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
7 use std::fs::File;
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
8 use std::io::{BufWriter, BufRead, BufReader};
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
9 use std::io::Write;
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
10 use clap::Parser;
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
11
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
12 /// Command line parameters
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
13 #[derive(Parser, Debug)]
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
14 #[clap(
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
15 about = env!("CARGO_PKG_DESCRIPTION"),
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
16 author = env!("CARGO_PKG_AUTHORS"),
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
17 version = env!("CARGO_PKG_VERSION"),
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
18 )]
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
19 struct CommandLineArgs {
3
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
20 /// Input file (default is stdin)
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
21 input : Option<String>,
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
22
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
23 /// Output file (defalt is stdout)
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
24 #[arg(long, short = 'o')]
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
25 output : Option<String>,
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
26
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
27 #[clap(flatten)]
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
28 config : Config
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
29 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
30
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
31 #[derive(Parser, Debug)]
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
32 struct Config {
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
33 #[arg(long, short = 'c')]
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
34 /// Strip comments
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
35 strip_comments : bool,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
36
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
37 #[arg(long, short = 'w')]
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
38 /// Strip unnecessary whitespace
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
39 strip_whitespace : bool,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
40 }
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
41
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
42 struct Context {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
43 lineno : usize,
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
44 input_only_ws : bool,
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
45 cli : Config
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
46 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
47
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
48 type AnyChainRule = Box<dyn ChainRule>;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
49 type AnyNestedRule = Box<dyn NestedRule>;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
50
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
51 trait ChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
52 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
53 fn flush(self : Box<Self>, ctx : &Context);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
54 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
55
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
56 trait NestedRule : ChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
57 fn produce(&mut self, c : char, ctx : &Context);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
58 fn next(self : Box<Self>) -> AnyChainRule;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
59 fn produce_string(&mut self, s : String, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
60 s.chars().for_each(|c| self.produce(c, ctx));
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
61 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
62 fn start_ignored_comment(&mut self, c : char);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
63 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
64
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
65 impl<W : Write + 'static> ChainRule for Out<W> {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
66 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
67 basic_consume(self, c, ctx, true)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
68 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
69 fn flush(mut self : Box<Self>, _ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
70 self.output.flush().unwrap();
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
71 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
72 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
73
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
74 impl<W : Write + 'static> NestedRule for Out<W> {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
75 fn produce(&mut self, c : char, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
76 if c == '\n' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
77 self.line_end(ctx.cli.strip_whitespace, ctx.input_only_ws)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
78 } else if c.is_whitespace() {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
79 self.stored_whitespace.push(c);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
80 } else {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
81 write!(self.output, "{}{}", self.stored_whitespace, c).unwrap();
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
82 self.stored_whitespace.clear();
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
83 self.only_whitespace = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
84 self.whitespace_satisfied = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
85 self.par_satisfied = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
86 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
87 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
88
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
89 fn next(self : Box<Self>) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
90 self
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
91 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
92
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
93 fn start_ignored_comment(&mut self, c : char) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
94 if self.stored_whitespace.is_empty() && !self.only_whitespace {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
95 // The marker needs to be inserted if there is to be no whitespace inserted
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
96 write!(self.output, "{c}").unwrap();
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
97 self.whitespace_satisfied = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
98 self.par_satisfied = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
99 self.only_whitespace = false;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
100 } else if self.only_whitespace {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
101 self.ignored_comment_only_line = true
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
102 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
103 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
104 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
105
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
106 fn basic_consume(mut s : AnyNestedRule, c : char, ctx : &Context, print_end : bool)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
107 -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
108 match c {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
109 '{' => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
110 s.produce(c, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
111 Box::new(Group(s))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
112 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
113 '}' => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
114 if print_end {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
115 s.produce(c, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
116 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
117 s.next()
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
118 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
119 '\\' => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
120 Box::new(CommandName{parent : s, command : "\\".to_string()})
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
121 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
122 '%' => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
123 if !ctx.cli.strip_comments {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
124 s.produce(c, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
125 Box::new(Comment(s))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
126 } else {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
127 s.start_ignored_comment(c);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
128 Box::new(IgnoreComment(s))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
129 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
130 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
131 _ => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
132 s.produce(c, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
133 s
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
134 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
135 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
136 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
137
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
138 struct CommandName {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
139 parent : AnyNestedRule,
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
140 command : String
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
141 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
142
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
143 impl ChainRule for CommandName {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
144 fn consume(mut self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
145 match c {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
146 '}' | '{' | '\\' if self.command.len() <= 1 => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
147 self.command.push(c);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
148 self.handle(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
149 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
150 c if c.is_alphanumeric() => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
151 self.command.push(c);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
152 self
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
153 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
154 c => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
155 self.handle(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
156 .consume(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
157 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
158 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
159 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
160
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
161 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
162 self.handle(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
163 .flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
164 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
165 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
166
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
167 impl CommandName {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
168 fn handle(mut self, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
169 match self.command.as_str() {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
170 "\\added" => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
171 Scan::new(Added(self.parent))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
172 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
173 "\\replaced" => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
174 Scan::new(Replaced(self.parent))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
175 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
176 "\\deleted" => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
177 Scan::new(Deleted(self.parent))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
178 },
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
179 _ => {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
180 self.parent.produce_string(self.command, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
181 self.parent
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
182 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
183 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
184 }
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
185 }
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
186
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
187 struct Comment(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
188
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
189 impl ChainRule for Comment {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
190 fn consume(mut self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
191 if c == '\n' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
192 self.0.consume(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
193 } else {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
194 self.0.produce(c, ctx);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
195 self
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
196 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
197 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
198 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
199 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
200 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
201 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
202
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
203 struct IgnoreComment(AnyChainRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
204
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
205 impl ChainRule for IgnoreComment {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
206 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
207 if c == '\n' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
208 self.0.consume(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
209 } else {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
210 self
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
211 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
212 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
213 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
214 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
215 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
216 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
217
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
218 struct Group(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
219
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
220 impl ChainRule for Group {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
221 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
222 basic_consume(self, c, ctx, true)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
223 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
224 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
225 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
226 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
227 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
228
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
229 impl NestedRule for Group {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
230 fn produce(&mut self, c : char, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
231 self.0.produce(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
232 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
233 fn next(self : Box<Self>) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
234 self.0
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
235 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
236 fn start_ignored_comment(&mut self, c : char) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
237 self.0.start_ignored_comment(c)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
238 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
239 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
240
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
241 struct Added(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
242
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
243 impl ChainRule for Added {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
244 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
245 basic_consume(self, c, ctx, false)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
246 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
247 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
248 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
249 }
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
250 }
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
251
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
252 impl NestedRule for Added {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
253 fn produce(&mut self, c : char, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
254 self.0.produce(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
255 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
256 fn next(self : Box<Self>) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
257 self.0
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
258 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
259 fn start_ignored_comment(&mut self, c : char) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
260 self.0.start_ignored_comment(c)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
261 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
262 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
263 struct Deleted(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
264
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
265 impl ChainRule for Deleted {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
266 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
267 basic_consume(self, c, ctx, false)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
268 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
269 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
270 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
271 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
272 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
273
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
274 impl NestedRule for Deleted {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
275 fn produce(&mut self, _c : char, _ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
276 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
277 fn next(self : Box<Self>) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
278 self.0
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
279 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
280 fn start_ignored_comment(&mut self, c : char) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
281 self.0.start_ignored_comment(c)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
282 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
283 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
284
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
285 struct Replaced(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
286
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
287 impl ChainRule for Replaced {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
288 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
289 basic_consume(self, c, ctx, false)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
290 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
291 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
292 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
293 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
294 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
295
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
296 impl NestedRule for Replaced {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
297 fn produce(&mut self, c : char, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
298 self.0.produce(c, ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
299 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
300 fn next(self : Box<Self>) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
301 Scan::new(Deleted(self.0))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
302 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
303 fn start_ignored_comment(&mut self, c : char) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
304 self.0.start_ignored_comment(c)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
305 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
306 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
307
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
308 struct Scan(AnyNestedRule);
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
309
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
310 impl ChainRule for Scan {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
311 fn consume(self : Box<Self>, c : char, ctx : &Context) -> AnyChainRule {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
312 if c.is_whitespace() || c == '\n' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
313 self
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
314 } else if c == '{' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
315 self.0
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
316 } else if c == '%' {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
317 Box::new(IgnoreComment(self))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
318 } else {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
319 panic!("Non-whitespace character ({c}) separating arguments on \
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
320 line {lineno}", lineno = ctx.lineno)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
321 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
322 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
323 fn flush(self : Box<Self>, ctx : &Context) {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
324 self.0.flush(ctx)
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
325 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
326 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
327
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
328 impl Scan {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
329 fn new<R : NestedRule + 'static>(r : R) -> Box<dyn ChainRule> {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
330 Box::new(Scan(Box::new(r)))
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
331 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
332 }
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
333
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
334
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
335 struct Out<W : Write> {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
336 only_whitespace : bool,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
337 stored_whitespace : String,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
338 output : W,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
339 whitespace_satisfied : bool,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
340 par_satisfied : bool,
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
341 ignored_comment_only_line : bool
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
342 }
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
343
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
344 impl<W : Write> Out<W> {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
345 pub fn line_end(&mut self, strip_ws : bool, input_only_ws : bool) {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
346 let skip_linefeed = if input_only_ws {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
347 // Need a paragraph break
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
348 strip_ws && self.par_satisfied
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
349 } else if strip_ws {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
350 self.only_whitespace && self.whitespace_satisfied
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
351 } else {
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
352 // Skip comment-only lines if the comment is ignored
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
353 self.ignored_comment_only_line
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
354 };
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
355
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
356 if !skip_linefeed {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
357 if !strip_ws {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
358 write!(self.output, "{}", self.stored_whitespace).unwrap();
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
359 }
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
360 write!(self.output, "\n").unwrap();
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
361 self.whitespace_satisfied = true;
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
362 self.par_satisfied = self.only_whitespace;
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
363 }
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
364
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
365 self.stored_whitespace.clear();
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
366 self.only_whitespace = true;
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
367 self.ignored_comment_only_line = false;
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
368 }
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
369 }
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
370
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
371 fn main() {
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
372 let cli = CommandLineArgs::parse();
3
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
373 let input = cli.input.map_or_else(
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
374 || Box::new(BufReader::new(io::stdin())) as Box<dyn BufRead>,
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
375 |f| Box::new(BufReader::new(File::open(f).unwrap())) as Box<dyn BufRead>
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
376 );
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
377 let output = cli.output.map_or_else(
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
378 || Box::new(BufWriter::new(io::stdout())) as Box<dyn Write>,
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
379 |f| Box::new(BufWriter::new(File::create(f).unwrap())) as Box<dyn Write>
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
380 );
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
381
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
382 let mut rule : Box<dyn ChainRule> = Box::new(Out {
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
383 only_whitespace : true,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
384 stored_whitespace : String::new(),
3
cec573b16b46 Add command line options for input and output files
Tuomo Valkonen <tuomov@iki.fi>
parents: 2
diff changeset
385 output,
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
386 whitespace_satisfied : true,
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
387 par_satisfied : true,
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
388 ignored_comment_only_line : false
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
389 });
2
254e1e4bd795 Add whitespace and comment stripping
Tuomo Valkonen <tuomov@iki.fi>
parents: 0
diff changeset
390
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
391 let mut ctx = Context{ lineno : 0, cli : cli.config, input_only_ws : true};
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
392
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
393 for l in input.lines().map(|l| l.unwrap()) {
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
394 ctx.lineno += 1;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
395 ctx.input_only_ws = true;
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
396 for c in l.chars() {
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
397 ctx.input_only_ws = ctx.input_only_ws && c.is_whitespace();
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
398 rule = rule.consume(c, &ctx);
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
399 }
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
400 rule = rule.consume('\n', &ctx);
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
401 }
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
402
6
de1cf8032322 Implement a more expansible parser
Tuomo Valkonen <tuomov@iki.fi>
parents: 3
diff changeset
403 rule.flush(&ctx);
0
548bf3cc032e Initial rough version
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
404 }

mercurial