1use crate::data::{ast::*, tokens::*};
2use nom::{
3 bytes::complete::take_while1,
4 error::{ContextError, ErrorKind, ParseError},
5 *,
6};
7
8fn position<'a, E: ParseError<Span<'a>> + ContextError<Span<'a>>, T>(s: T) -> IResult<T, T, E>
13where
14 T: InputIter + InputTake,
15 E: nom::error::ParseError<T>,
16{
17 nom::bytes::complete::take(0usize)(s)
18}
19
20fn set_escape(s: &str, index: usize, escape: &mut bool) {
21 if let Some(c) = s.chars().nth(index) {
22 if c == '\\' {
23 return match escape {
24 true => {
25 *escape = false;
26 }
27 false => {
28 *escape = true;
29 }
30 };
31 }
32
33 *escape = false;
34 }
35}
36
37fn set_substring(s: &str, index: usize, escape: bool, expand: bool, substring: &mut bool) {
38 if let Some(c) = s.chars().nth(index) {
39 if c == '"' && escape && expand {
40 match substring {
41 true => {
42 *substring = false;
43 }
44 false => {
45 *substring = true;
46 }
47 }
48 }
49 }
50}
51
52fn set_open_expand(s: &str, index: usize, escape: bool, substring: bool, expand: &mut bool) {
53 if let Some(c) = s.chars().nth(index) {
54 if c == '{' && !escape && !substring {
55 if let Some(c) = s.chars().nth(index + 1) {
56 if c == '{' && !escape {
57 *expand = true;
58 }
59 }
60 }
61 }
62}
63
64fn set_close_expand(s: &str, index: usize, escape: bool, substring: bool, expand: &mut bool) {
65 if let Some(c) = s.chars().nth(index) {
66 if c == '}' && !escape && !substring {
67 if let Some(c) = s.chars().nth(index + 1) {
68 if c == '}' && !escape {
69 *expand = false;
70 }
71 }
72 }
73 }
74}
75
76pub fn get_interval<'a, E>(s: Span<'a>) -> IResult<Span<'a>, Interval, E>
81where
82 E: ParseError<Span<'a>> + ContextError<Span<'a>>,
83{
84 let (s, pos) = position(s)?;
85 Ok((s, Interval::new_as_span(pos)))
86}
87
88pub fn get_range_interval(vector_interval: &[Interval]) -> Interval {
89 let mut start = Interval::new_as_u32(0, 0, 0, None, None);
90 let mut end = Interval::new_as_u32(0, 0, 0, None, None);
91
92 for (index, interval) in vector_interval.iter().enumerate() {
93 if index == 0 {
94 start = *interval;
95 }
96
97 end = *interval;
98 }
99
100 start.add_end(end);
101 start
102}
103
104pub fn parse_error<'a, O, E, F>(
106 start: Span<'a>,
107 span: Span<'a>,
108 mut func: F,
109) -> IResult<Span<'a>, O, E>
110where
111 E: ParseError<Span<'a>> + ContextError<Span<'a>>,
112 F: FnMut(Span<'a>) -> IResult<Span<'a>, O, E>,
113{
114 match func(span) {
115 Ok(value) => Ok(value),
116 Err(Err::Error(e)) => Err(Err::Error(e)),
117 Err(Err::Failure(e)) => Err(Err::Failure(E::append(start, ErrorKind::Tag, e))),
118 Err(Err::Incomplete(needed)) => Err(Err::Incomplete(needed)),
119 }
120}
121
122pub fn get_string<'a, E>(s: Span<'a>) -> IResult<Span<'a>, String, E>
123where
124 E: ParseError<Span<'a>> + ContextError<Span<'a>>,
125{
126 let (rest, string) =
127 take_while1(|c: char| c == '-' || c == '_' || c == '\\' || c.is_alphanumeric())(s)?;
128
129 Ok((rest, (*string.fragment()).to_string()))
130}
131
132pub fn get_tag<I, E: ParseError<I>>(
133 var: String,
134 tag: &str,
135) -> impl FnMut(I) -> IResult<I, (), E> + '_ {
136 move |input: I| {
137 if var == tag {
138 Ok((input, ()))
139 } else {
140 Err(Err::Error(E::from_error_kind(input, ErrorKind::Tag)))
141 }
142 }
143}
144
145pub fn get_distance_brace(s: &Span, key: char) -> Option<usize> {
146 let mut escape: bool = false;
147 let mut expand: bool = false;
148 let mut substring: bool = false;
149 let mut distance = 0;
150
151 for (i, c) in s.chars().enumerate() {
152 if c == key && !escape && !substring {
153 if let Some(c) = s.chars().nth(i + 1) {
154 if c == key {
155 return Some(distance);
156 }
157 }
158 }
159
160 distance += c.len_utf8();
161
162 set_open_expand(s.fragment(), i, escape, substring, &mut expand);
163 set_close_expand(s.fragment(), i, escape, substring, &mut expand);
164 set_substring(s.fragment(), i, escape, expand, &mut substring);
165 set_escape(s.fragment(), i, &mut escape);
166 }
167
168 None
169}