1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
|
#ifndef PARSER_FUNCTIONS_H
#define PARSER_FUNCTIONS_H
#include "ast/ast.h"
#include "lexer/lexer.h"
#include "parser/parser_utils.h"
#define QUICK_CLEANUP \
cleanup(NULL, state); \
return NULL;
#define TST_REDIR next.type == TOKEN_IONUMBER || next.type == TOKEN_REDIR
/**
* @brief This function parses the list grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `list = and_or { ';' and_or } [ ';' ] ;`
*/
struct ast *parse_list(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the and_or grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `and_or = pipeline { ( '&&' | '||' ) {'\\n'} pipeline } ;`
*/
struct ast *parse_and_or(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the pipeline grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `pipeline = ['!'] command { '|' {'\\n'} command } ;`
*/
struct ast *parse_pipeline(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the command grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `command = simple_command
* | shell command { redirection }
* | fundec { redirection }
* ;`
*/
struct ast *parse_command(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the simple_command grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `simple_command = prefix { prefix }
* | { prefix } WORD { element }
* ;`
*/
struct ast *parse_simple_command(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the element grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form (different from subject):
*
* `element = { (WORD | redirection) };`
*/
struct ast *parse_element(struct lexer *lexer, enum parser_state *state,
struct ast *lst, struct ast *up);
/**
* @brief This function parses the shell_command grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `shell_command = rule_if
* | rule_while
* | rule_until
* | rule_for
* | '{' compound_list '}'
* | '(' compound_list ')'
* ;`
*/
struct ast *parse_shell_command(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the rule_if grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `rule_if = 'if' compound_list 'then' compound_list [else_clause] 'fi' ;`
*/
struct ast *parse_rule_if(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the else_clause grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `else_clause = 'else' compound_list
* | 'elif' compound_list 'then' compound_list [else_clause]`
*/
struct ast *parse_else_clause(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the rule_while grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `rule_while = 'while' compound_list 'do' compound_list 'done' ;`
*/
struct ast *parse_rule_while(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the rule_until grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `rule_until = 'until' compound_list 'do' compound_list 'done' ;`
*/
struct ast *parse_rule_until(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the rule_for grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `rule_for = 'for' WORD ( [';'] | [ {'\\n'} 'in' { WORD } ( ';' | '\\n' ) ] )
* {'\\n'} 'do' compound_list 'done'
* ;`
*/
struct ast *parse_rule_for(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the prefix grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `prefix = ASSIGNMENT_WORD
* | redirection
* ;`
*/
struct ast *parse_prefix(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the redirection grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `redirection = [IONUMBER] ( '>' | '<' | '>>' | '>&' | '<&' | '>|' | '<>' )
* WORD
* ;`
*/
struct ast *parse_redirection(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the compound_list grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @note Here is the Extended Backus-Naur form:
*
* `compound_list = { '\\n' } and_or { ( ';' | '\\n' ) { '\\n' } and_or } [ ';'
* ] { '\\n' } ;`
*/
struct ast *parse_compound_list(struct lexer *lexer, enum parser_state *state);
/**
* @brief This function parses the funcdec grammar
* @param lexer The lexer used to parse the current expression.
* @param state Current state of the parser. Set to `ERROR` when needed.
* @param txt The string to use as the name of the function. NULL means it must
* be fetched from the lexer.
* @note This change in declaration is to accomodate for the way we manage the
* conflict between the simple_command and the fundec rules (both start w/ WORD)
* @note Here is the Extended Backus-Naur form:
*
* funcdec = WORD '(' ')' {'\n'} shell_command ;
*/
struct ast *parse_funcdec(struct lexer *lexer, enum parser_state *state,
struct string *txt);
#endif /* ! PARSER_FUNCTIONS_H */
|