]> git.ipfire.org Git - thirdparty/pdns.git/blob - pdns/bindparser.yy
auth: add bind primary, secondary and primaries keywords
[thirdparty/pdns.git] / pdns / bindparser.yy
1 %{
2
3 #include <stdio.h>
4 #include <string.h>
5 #include <stdlib.h>
6 #include <string>
7 #include <iostream>
8 #include <utility>
9 #include <errno.h>
10 #include "misc.hh"
11 #include "pdnsexception.hh"
12 #include "namespaces.hh"
13 #include "iputils.hh"
14 #define YYDEBUG 1
15 extern int yydebug;
16 #include "bindparserclasses.hh"
17
18 #define YYSTYPE char *
19
20 extern "C"
21 {
22 int yyparse(void);
23 int yylex(void);
24 void yyrestart(FILE *);
25 int yywrap(void);
26 int yywrap(void)
27 {
28 return 1;
29 }
30 }
31
32
33 extern int yydebug;
34 const char *bind_directory;
35 extern int linenumber;
36 static void yyerror(const char *str)
37 {
38 extern char *current_filename;
39 throw PDNSException("Error in bind configuration '"+string(current_filename)+"' on line "+std::to_string(linenumber)+": "+str);
40 }
41
42 extern FILE *yyin;
43 static BindParser *parent;
44 BindDomainInfo s_di;
45
46 void BindParser::parse(const string &fname)
47 {
48 yydebug=0;
49 yyin=fopen(fname.c_str(),"r");
50 yyrestart(yyin);
51 if(!yyin)
52 throw PDNSException("Unable to open '"+fname+"': "+strerror(errno));
53
54 linenumber=1;
55 parent=this;
56 extern char *current_filename;
57 extern char *original_filename;
58
59 current_filename=original_filename=(char*)fname.c_str();
60
61 yyparse();
62
63 // cerr<<"Need to parse "<<d_zonedomains.size()<<" zone statements"<<endl;
64 }
65
66 void BindParser::setDirectory(const string &dir)
67 {
68 d_dir=dir;
69 if (d_dir.back() == '/') {
70 d_dir.pop_back();
71 }
72 bind_directory=d_dir.c_str();
73 }
74
75 void BindParser::addAlsoNotify(const string & host)
76 {
77 alsoNotify.insert(host);
78 }
79
80 const string &BindParser::getDirectory()
81 {
82 return d_dir;
83 }
84
85 const vector<BindDomainInfo>& BindParser::getDomains()
86 {
87 return d_zonedomains;
88 }
89
90 void BindParser::setVerbose(bool verbose)
91 {
92 d_verbose=verbose;
93 }
94
95 void BindParser::commit(BindDomainInfo DI)
96 {
97 DI.hadFileDirective = (DI.filename != "");
98
99 if(DI.filename[0]!='/')
100 DI.filename=d_dir+"/"+DI.filename;
101
102 if(d_verbose)
103 cerr<<"Domain "<<DI.name.toStringNoDot()<<" lives in file '"<<DI.filename<<"'"<<endl;
104
105 d_zonedomains.push_back(DI);
106 }
107
108 %}
109
110 %token AWORD QUOTEDWORD OBRACE EBRACE SEMICOLON ZONETOK FILETOK OPTIONSTOK
111 %token DIRECTORYTOK ACLTOK LOGGINGTOK CLASSTOK TYPETOK PRIMARYTOK ALSONOTIFYTOK
112
113 %%
114
115 root_commands:
116 |
117 root_commands root_command SEMICOLON
118 ;
119
120 root_command: command | acl_command | global_zone_command | global_options_command
121 ;
122
123 commands:
124 |
125 commands command SEMICOLON
126 ;
127
128 command:
129 terms
130 ;
131
132 global_zone_command:
133 ZONETOK quotedname zone_block
134 {
135 s_di.name=DNSName($2);
136 free($2);
137 parent->commit(s_di);
138 s_di.clear();
139 }
140 |
141 ZONETOK quotedname AWORD zone_block
142 {
143 s_di.name=DNSName($2);
144 free($2);
145 parent->commit(s_di);
146 s_di.clear();
147 }
148 ;
149
150
151 global_options_command:
152 OPTIONSTOK OBRACE options_commands EBRACE
153 |
154 LOGGINGTOK OBRACE options_commands EBRACE
155 ;
156
157
158 acl_command:
159 ACLTOK quotedname acl_block | ACLTOK filename acl_block
160 ;
161
162 acl_block: OBRACE acls EBRACE
163 ;
164
165 acls:
166 |
167 acl SEMICOLON acls
168 ;
169
170 acl:
171 AWORD
172 ;
173
174 options_commands:
175 |
176 options_command SEMICOLON options_commands
177 ;
178
179 options_command: command | global_options_command
180 ;
181
182 global_options_command: options_directory_command | also_notify_command
183 ;
184
185 options_directory_command: DIRECTORYTOK quotedname
186 {
187 parent->setDirectory($2);
188 free($2);
189 }
190 ;
191
192 also_notify_command: ALSONOTIFYTOK OBRACE also_notify_list EBRACE
193 ;
194
195 also_notify_list:
196 |
197 also_notify SEMICOLON also_notify_list
198 ;
199
200 also_notify: AWORD
201 {
202 parent->addAlsoNotify($1);
203 free($1);
204 }
205 ;
206 terms: /* empty */
207 |
208 terms term
209 ;
210
211 term: AWORD | block | quotedname
212 ;
213 block:
214 OBRACE commands EBRACE
215 ;
216
217 zone_block:
218 OBRACE zone_commands EBRACE
219 ;
220
221 zone_commands:
222 |
223 zone_commands zone_command SEMICOLON
224 ;
225
226 /* commands in zone
227 * in global scope also_notify_command is used instead of zone_also_notify_command
228 */
229 zone_command: command | global_zone_command | zone_also_notify_command
230 ;
231
232 /* zone commands that also are available at global scope */
233 global_zone_command: zone_file_command | zone_type_command | zone_primaries_command
234 ;
235
236 zone_primaries_command: PRIMARYTOK OBRACE primaries EBRACE
237 ;
238
239 zone_also_notify_command: ALSONOTIFYTOK OBRACE zone_also_notify_list EBRACE
240 ;
241
242 zone_also_notify_list:
243 |
244 zone_also_notify SEMICOLON zone_also_notify_list
245 ;
246
247 zone_also_notify: AWORD
248 {
249 s_di.alsoNotify.insert($1);
250 free($1);
251 }
252 ;
253
254 primaries: /* empty */
255 |
256 primaries primary SEMICOLON
257 ;
258
259 primary: AWORD
260 {
261 s_di.masters.push_back(ComboAddress($1, 53));
262 free($1);
263 }
264 ;
265
266 zone_file_command:
267 FILETOK quotedname
268 {
269 // printf("Found a filename: '%s'\n",$2);
270 s_di.filename=$2;
271 free($2);
272 }
273 ;
274
275 zone_type_command:
276 TYPETOK AWORD
277 {
278 s_di.type=$2;
279 free($2);
280 }
281 ;
282
283
284 quotedname:
285 QUOTEDWORD
286 {
287 $$=$1;
288 }
289 ;
290
291 filename: AWORD
292 ;