Version 7.0
Copyright © 2021 Lowell D. Thomas
APG
… an ABNF Parser Generator
semantic-callbacks.c
Go to the documentation of this file.
1 /* *************************************************************************************
2  Copyright (c) 2021, Lowell D. Thomas
3  All rights reserved.
4 
5  This file is part of APG Version 7.0.
6  APG Version 7.0 may be used under the terms of the BSD 2-Clause License.
7 
8  Redistribution and use in source and binary forms, with or without
9  modification, are permitted provided that the following conditions are met:
10 
11  1. Redistributions of source code must retain the above copyright notice, this
12  list of conditions and the following disclaimer.
13 
14  2. Redistributions in binary form must reproduce the above copyright notice,
15  this list of conditions and the following disclaimer in the documentation
16  and/or other materials provided with the distribution.
17 
18  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
21  DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
22  FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23  DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24  SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
25  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
26  OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 
29 * *************************************************************************************/
36 #include "./api.h"
37 #include "./apip.h"
38 #include "../library/parserp.h"
39 #include "./semantics.h"
40 #include "sabnf-grammar.h"
41 
42 static const char* s_cpNoTab = "tab (\\t, 0x09) found. Not allowed in TLS strings (char-val RFC 5234).";
43 
44 static void vSemPushError(semantic_data* spData, aint uiCharIndex, const char* cpMsg) {
45  spData->uiErrorsFound++;
46  vLineError(spData->spApi, uiCharIndex, "semantic", cpMsg);
47  XTHROW(spData->spApi->spException, cpMsg);
48 }
49 
50 static aint uiRuleLookup(ast_data* spAstData){
51  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
52  if(spAstData->uiState == ID_AST_PRE){
53  spData->uiIncAlt = APG_FALSE;
54  }else{
55  // look up the rule name
56  char caName[RULENAME_MAX];
57  size_t iBufSize = 2 * RULENAME_MAX;
58  char caBuf[iBufSize];
59  semantic_rule* spRules = (semantic_rule*)vpVecFirst(spData->vpVecRules);
60  aint uiRuleCount = uiVecLen(spData->vpVecRules);
61  aint uiFound = uiFindRule(spRules, uiRuleCount, spData->cpName, spData->uiNameLength);
62  if(uiFound == APG_UNDEFINED){
63  if(spData->uiIncAlt){
64  // name not found, but incremental alternative specified
65  aint uiLen = spData->uiNameLength + 1;
66  if(uiLen > RULENAME_MAX){
67  uiLen = RULENAME_MAX;
68  }
69  snprintf(caName, uiLen, "%s", spData->cpName);
70  snprintf(caBuf, iBufSize,
71  "incremental alternative rule name \"%s\" used without previous definition", caName);
72  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
73  }else{
74  // name not found, push a new rule_op
75  semantic_rule sRule;
76  sRule.cpName = spData->cpName;
77  sRule.uiNameLength = spData->uiNameLength;
78 
79  // set up the ALT stack to remember which ALT op is current
81  sRule.vpVecAltStack = vpVecCtor(spData->vpMem, sizeof(aint), 100);
82  vpVecPush(sRule.vpVecAltStack, &sRule.uiCurrentAlt);
83 
84  // set up the CAT stack to remember which CAT op is current
86  sRule.vpVecCatStack = vpVecCtor(spData->vpMem, sizeof(aint), 100);
87  vpVecPush(sRule.vpVecCatStack, &sRule.uiCurrentCat);
88 
89  // set up the vector of opcodes for this rule
90  sRule.vpVecOps = vpVecCtor(spData->vpMem, sizeof(semantic_op), 500);
91 
92  // push the new rule on the rule vector
93  sRule.uiIndex = spData->uiRuleIndex++;
94  spData->spCurrentRule = (semantic_rule*)vpVecPush(spData->vpVecRules, (void*)&sRule);
95  }
96  }else{
97  if(spData->uiIncAlt){
98  // name found && IncAlt, reset current rule
99  spData->spCurrentRule = (semantic_rule*)vpVecAt(spData->vpVecRules, uiFound);
100  if(!spData->spCurrentRule){
101  XTHROW(spData->spApi->spException, "rule index out of range");
102  }
103  }else{
104  // if name found && not incAlt, error, rule defined multiple times
105  aint uiLen = spData->uiNameLength + 1;
106  if(uiLen > RULENAME_MAX){
107  uiLen = RULENAME_MAX;
108  }
109  snprintf(caName, uiLen, "%s", spData->cpName);
110  snprintf(caBuf, iBufSize, "rule name \"%s\" previously defined", caName);
111  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
112  }
113  }
114  }
115  return ID_AST_OK;
116 }
117 
118 static aint uiRuleName(ast_data* spAstData){
119  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
120  if(spAstData->uiState == ID_AST_PRE){
121  spData->cpName = &spData->spApi->cpInput[spAstData->uiPhraseOffset];
122  spData->uiNameLength = spAstData->uiPhraseLength;
123  }
124  return ID_AST_OK;
125 }
126 
127 static aint uiIncAlt(ast_data* spAstData){
128  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
129  if(spAstData->uiState == ID_AST_PRE){
130  spData->uiIncAlt = APG_TRUE;
131  }
132  return ID_AST_OK;
133 }
134 
135 static aint uiAlternation(ast_data* spAstData){
136  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
137  semantic_rule* spRule = spData->spCurrentRule;
138  if(spAstData->uiState == ID_AST_PRE){
139  // set up a new ALT opcode
140  semantic_op sOp = {ID_ALT};
141  sOp.vpVecChildList = vpVecCtor(spData->vpMem, sizeof(aint), 10);
142  spRule->uiCurrentAlt = uiVecLen(spRule->vpVecOps);
143  vpVecPush(spRule->vpVecOps, &sOp);
144 
145  // push the new, current ALT opcode index on the ALT stack
146  vpVecPush(spRule->vpVecAltStack, &spRule->uiCurrentAlt);
147  }else{
148  // reset the current ALT opcode index
149  vpVecPop(spRule->vpVecAltStack);
150  aint* uip = (aint*)vpVecLast(spRule->vpVecAltStack);
151  if(!uip){
152  XTHROW(spData->spApi->spException, "the ALT stack should never be empty");
153  }
154  spRule->uiCurrentAlt = *uip;
155  }
156  return ID_AST_OK;
157 }
158 
159 static aint uiConcatenation(ast_data* spAstData){
160  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
161  semantic_rule* spRule = spData->spCurrentRule;
162  if(spAstData->uiState == ID_AST_PRE){
163  // set up a new CAT opcode
164  semantic_op sOp = {ID_CAT};
165  spRule->uiCurrentCat = uiVecLen(spRule->vpVecOps);
166  sOp.vpVecChildList = vpVecCtor(spData->vpMem, sizeof(aint), 10);
167  vpVecPush(spRule->vpVecOps, &sOp);
168 
169  // report this CAT opcode as a child of the immediate Alt parent
170  semantic_op* spAlt = (semantic_op*)vpVecAt(spRule->vpVecOps, spRule->uiCurrentAlt);
171  if(!spAlt){
172  XTHROW(spData->spApi->spException, "the ALT stack should never be empty");
173  }
174  vpVecPush(spAlt->vpVecChildList, &spRule->uiCurrentCat);
175 
176  // push the new, current ALT opcode index on the ALT stack
177  vpVecPush(spRule->vpVecCatStack, &spRule->uiCurrentCat);
178  }else{
179  // reset the current CAT opcode index
180  vpVecPop(spRule->vpVecCatStack);
181  aint* uip = (aint*)vpVecLast(spRule->vpVecCatStack);
182  if(!uip){
183  XTHROW(spData->spApi->spException, "the CAT stack should never be empty");
184  }
185  spRule->uiCurrentCat = *uip;
186  }
187  return ID_AST_OK;
188 }
189 
190 static aint uiRepetition(ast_data* spAstData){
191  if(spAstData->uiState == ID_AST_PRE){
192  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
193  semantic_rule* spRule = spData->spCurrentRule;
194  semantic_op sOp = {ID_REP};
195  sOp.luiMin = (luint)1;
196  sOp.luiMax = (luint)1;
197  aint uiIndex = uiVecLen(spRule->vpVecOps);
198  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
199  semantic_op* spCat = (semantic_op*)vpVecAt(spRule->vpVecOps, spRule->uiCurrentCat);
200  if(!spCat){
201  XTHROW(spData->spApi->spException, "the CAT stack should never be empty");
202  }
203  vpVecPush(spCat->vpVecChildList, &uiIndex);
204  }
205  return ID_AST_OK;
206 }
207 
208 static aint uiBkaOp(ast_data* spAstData){
209  if(spAstData->uiState == ID_AST_PRE){
210  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
211  semantic_rule* spRule = spData->spCurrentRule;
212  semantic_op sOp = {ID_BKA};
213  vpVecPush(spRule->vpVecOps, &sOp);
214  }
215  return ID_AST_OK;
216 }
217 
218 static aint uiBknOp(ast_data* spAstData){
219  if(spAstData->uiState == ID_AST_PRE){
220  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
221  semantic_rule* spRule = spData->spCurrentRule;
222  semantic_op sOp = {ID_BKN};
223  vpVecPush(spRule->vpVecOps, &sOp);
224  }
225  return ID_AST_OK;
226 }
227 
228 static aint uiAndOp(ast_data* spAstData){
229  if(spAstData->uiState == ID_AST_PRE){
230  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
231  semantic_rule* spRule = spData->spCurrentRule;
232  semantic_op sOp = {ID_AND};
233  vpVecPush(spRule->vpVecOps, &sOp);
234  }
235  return ID_AST_OK;
236 }
237 
238 static aint uiNotOp(ast_data* spAstData){
239  if(spAstData->uiState == ID_AST_PRE){
240  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
241  semantic_rule* spRule = spData->spCurrentRule;
242  semantic_op sOp = {ID_NOT};
243  vpVecPush(spRule->vpVecOps, &sOp);
244  }
245  return ID_AST_OK;
246 }
247 
248 static aint uiRepOp(ast_data* spAstData){
249  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
250  semantic_rule* spRule = spData->spCurrentRule;
251  if(spAstData->uiState == ID_AST_PRE){
252  semantic_op sOp = {ID_REP};
253  sOp.luiMin = 0;
254  sOp.luiMax = (luint)-1;
255  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
256  }else{
257  semantic_op* spRep = (semantic_op*)vpVecLast(spRule->vpVecOps);
258  if(spRep->luiMin > spRep->luiMax){
259  char caBuf[128];
260  snprintf(caBuf, 128, "REP: minimum(%"PRIuMAX") must be <= maximum (%"PRIuMAX")",
261  spRule->spCurrentOp->luiMin, spRule->spCurrentOp->luiMax);
262  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
263  }
264  }
265  return ID_AST_OK;
266 }
267 
268 static aint uiRepMin(ast_data* spAstData){
269  if(spAstData->uiState == ID_AST_PRE){
270  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
271  semantic_rule* spRule = spData->spCurrentRule;
272  semantic_op* spRep = (semantic_op*)vpVecLast(spRule->vpVecOps);
273  aint ui;
274  luint luiTest, luiDigit;
275  spRep->luiMin = 0;
276  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
277  if(!bMultiplyLong(10, spRep->luiMin, &luiTest)){
278  goto fail;
279  }
280  luiDigit = (luint)(spAstData->acpString[spAstData->uiPhraseOffset + ui] - 48);
281  if(!bSumLong(luiTest, luiDigit, &spRep->luiMin)){
282  goto fail;
283  }
284  }
285  return ID_AST_OK;
286  fail:{
287  char caString[spAstData->uiPhraseLength + 1];
288  char caBuf[128];
289  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
290  caString[spAstData->uiPhraseLength] = 0;
291  snprintf(caBuf, 128,
292  "REP: n*m: n out of range: %s", caString);
293  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
294  }
295  }
296  return ID_AST_OK;
297 }
298 
299 static aint uiRepMax(ast_data* spAstData){
300  if(spAstData->uiState == ID_AST_PRE){
301  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
302  semantic_rule* spRule = spData->spCurrentRule;
303  semantic_op* spRep = (semantic_op*)vpVecLast(spRule->vpVecOps);
304  aint ui;
305  luint luiTest, luiDigit;
306  spRep->luiMax = 0;
307  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
308  if(!bMultiplyLong(10, spRep->luiMax, &luiTest)){
309  goto fail;
310  }
311  luiDigit = (luint)(spAstData->acpString[spAstData->uiPhraseOffset + ui] - 48);
312  if(!bSumLong(luiTest, luiDigit, &spRep->luiMax)){
313  goto fail;
314  }
315  }
316  return ID_AST_OK;
317  fail:{
318  char caString[spAstData->uiPhraseLength + 1];
319  char caBuf[128];
320  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
321  caString[spAstData->uiPhraseLength] = 0;
322  snprintf(caBuf, 128,
323  "REP: n*m: m out of range: %s", caString);
324  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
325  }
326  }
327  return ID_AST_OK;
328 }
329 
330 static aint uiRepMinMax(ast_data* spAstData){
331  if(spAstData->uiState == ID_AST_PRE){
332  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
333  semantic_rule* spRule = spData->spCurrentRule;
334  semantic_op* spRep = (semantic_op*)vpVecLast(spRule->vpVecOps);
335  aint ui;
336  luint luiTest, luiDigit;
337  spRep->luiMin = 0;
338  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
339  if(!bMultiplyLong(10, spRep->luiMin, &luiTest)){
340  goto fail;
341  }
342  luiDigit = (luint)(spAstData->acpString[spAstData->uiPhraseOffset + ui] - 48);
343  if(!bSumLong(luiTest, luiDigit, &spRep->luiMin)){
344  goto fail;
345  }
346  }
347  spRep->luiMax = spRep->luiMin;
348  return ID_AST_OK;
349  fail:{
350  char caString[spAstData->uiPhraseLength + 1];
351  char caBuf[128];
352  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
353  caString[spAstData->uiPhraseLength] = 0;
354  snprintf(caBuf, 128,
355  "REP: n or n*n: n out of range: %s", caString);
356  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
357  }
358  }
359  return ID_AST_OK;
360 }
361 
362 static aint uiOptionOpen(ast_data* spAstData){
363  if(spAstData->uiState == ID_AST_PRE){
364  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
365  semantic_rule* spRule = spData->spCurrentRule;
366  semantic_op sOp = {ID_REP};
367  sOp.luiMin = 0;
368  sOp.luiMax = 1;
369  vpVecPush(spRule->vpVecOps, &sOp);
370  }
371  return ID_AST_OK;
372 }
373 
374 static aint uiRnmOp(ast_data* spAstData){
375  if(spAstData->uiState == ID_AST_PRE){
376  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
377  semantic_rule* spRule = spData->spCurrentRule;
378  semantic_op sOp = {ID_RNM};
379 // sOp.cpName = (char*)&spAstData->acpString[spAstData->uiPhraseOffset];
380  sOp.cpName = &spData->spApi->cpInput[spAstData->uiPhraseOffset];
381  sOp.uiNameLength = spAstData->uiPhraseLength;
382  vpVecPush(spRule->vpVecOps, &sOp);
383  }
384  return ID_AST_OK;
385 }
386 
387 static aint uiUdtOp(ast_data* spAstData){
388  if(spAstData->uiState == ID_AST_PRE){
389  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
390  semantic_rule* spRule = spData->spCurrentRule;
391  semantic_op sOp = {ID_UDT};
392  sOp.uiEmpty = APG_FALSE;
393  sOp.cpName = &spData->spApi->cpInput[spAstData->uiPhraseOffset];
394  sOp.uiNameLength = spAstData->uiPhraseLength;
395  spRule->spCurrentOp = vpVecPush(spRule->vpVecOps, &sOp);
396  }
397  return ID_AST_OK;
398 }
399 
400 static aint uiUdtEmpty(ast_data* spAstData){
401  if(spAstData->uiState == ID_AST_PRE){
402  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
403  semantic_rule* spRule = spData->spCurrentRule;
404  spRule->spCurrentOp->uiEmpty = APG_TRUE;
405  }
406  return ID_AST_OK;
407 }
408 
409 static aint uiUdtNonEmpty(ast_data* spAstData){
410  if(spAstData->uiState == ID_AST_PRE){
411  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
412  semantic_rule* spRule = spData->spCurrentRule;
413  spRule->spCurrentOp->uiEmpty = APG_FALSE;
414  }
415  return ID_AST_OK;
416 }
417 
418 static aint uiBkrOp(ast_data* spAstData){
419  if(spAstData->uiState == ID_AST_PRE){
420  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
421  semantic_rule* spRule = spData->spCurrentRule;
422  semantic_op sOp = {ID_BKR};
423  sOp.uiCase = ID_BKR_CASE_I;
424  sOp.uiMode = ID_BKR_MODE_U;
425  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
426  }
427  return ID_AST_OK;
428 }
429 
430 static aint uiCs(ast_data* spAstData){
431  if(spAstData->uiState == ID_AST_PRE){
432  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
433  semantic_rule* spRule = spData->spCurrentRule;
434  spRule->spCurrentOp->uiCase = ID_BKR_CASE_S;
435  }
436  return ID_AST_OK;
437 }
438 
439 static aint uiCi(ast_data* spAstData){
440  if(spAstData->uiState == ID_AST_PRE){
441  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
442  semantic_rule* spRule = spData->spCurrentRule;
443  spRule->spCurrentOp->uiCase = ID_BKR_CASE_I;
444  }
445  return ID_AST_OK;
446 }
447 
448 static aint uiBkrUm(ast_data* spAstData){
449  if(spAstData->uiState == ID_AST_PRE){
450  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
451  semantic_rule* spRule = spData->spCurrentRule;
452  spRule->spCurrentOp->uiMode = ID_BKR_MODE_U;
453  }
454  return ID_AST_OK;
455 }
456 
457 static aint uiBkrPm(ast_data* spAstData){
458  if(spAstData->uiState == ID_AST_PRE){
459  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
460  semantic_rule* spRule = spData->spCurrentRule;
461  spRule->spCurrentOp->uiMode = ID_BKR_MODE_P;
462  }
463  return ID_AST_OK;
464 }
465 
466 static aint uiBkrName(ast_data* spAstData){
467  if(spAstData->uiState == ID_AST_PRE){
468  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
469  semantic_rule* spRule = spData->spCurrentRule;
470 // spRule->spCurrentOp->cpName = (char*)&spAstData->acpString[spAstData->uiPhraseOffset];
471  spRule->spCurrentOp->cpName = &spData->spApi->cpInput[spAstData->uiPhraseOffset];
472  spRule->spCurrentOp->uiNameLength = spAstData->uiPhraseLength;
473  }
474  return ID_AST_OK;
475 }
476 
477 static aint uiAbgOp(ast_data* spAstData){
478  if(spAstData->uiState == ID_AST_PRE){
479  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
480  semantic_rule* spRule = spData->spCurrentRule;
481  semantic_op sOp = {ID_ABG};
482  vpVecPush(spRule->vpVecOps, &sOp);
483  }
484  return ID_AST_OK;
485 }
486 
487 static aint uiAenOp(ast_data* spAstData){
488  if(spAstData->uiState == ID_AST_PRE){
489  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
490  semantic_rule* spRule = spData->spCurrentRule;
491  semantic_op sOp = {ID_AEN};
492  vpVecPush(spRule->vpVecOps, &sOp);
493  }
494  return ID_AST_OK;
495 }
496 
497 static aint uiClsOp(ast_data* spAstData){
498  if(spAstData->uiState == ID_AST_PRE){
499  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
500  semantic_rule* spRule = spData->spCurrentRule;
501  semantic_op sOp = {ID_TBS};
502  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
503  }
504  return ID_AST_OK;
505 }
506 
507 static aint uiClsString(ast_data* spAstData){
508  if(spAstData->uiState == ID_AST_PRE){
509  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
510  semantic_rule* spRule = spData->spCurrentRule;
512  spRule->spCurrentOp->uiStringLength = spAstData->uiPhraseLength;
513  if(!spAstData->uiPhraseLength){
514  vSemPushError(spData, spAstData->uiPhraseOffset,
515  "case-sensitive string may not be empty - use case-insensitive string (\"\") to represent an empty string");
516  }else{
517  // push the actual string into the character table for case sensitive compare
518  aint ui = 0;
519  for(; ui < spAstData->uiPhraseLength; ui++){
520  luint luiChar = (luint)spAstData->acpString[spAstData->uiPhraseOffset + ui];
521  vpVecPush(spData->vpVecAcharsTable, (void*)&luiChar);
522  }
523  }
524  }
525  return ID_AST_OK;
526 }
527 
528 static aint uiTlsOp(ast_data* spAstData){
529  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
530  semantic_rule* spRule = spData->spCurrentRule;
531  if(spAstData->uiState == ID_AST_PRE){
532  semantic_op sOp = {ID_TLS};
533  sOp.uiCase = ID_BKR_CASE_I;
534  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
535  }else{
536  luint luiChar;
537  aint ui = 0;
538  aint uiIndex = spRule->spCurrentOp->uiStringIndex;
539  if(spRule->spCurrentOp->uiCase == ID_BKR_CASE_I){
540  // push lower case string for case insensitive compare
541  luint* luipChars = (luint*)vpVecAt(spData->vpVecAcharsTable, uiIndex);
542  for(; ui < spRule->spCurrentOp->uiStringLength; ui++, luipChars++){
543  luiChar = *luipChars;
544  if((luiChar >= 65) && (luiChar <= 90)){
545  *luipChars += 32;
546  }
547  }
548 
549  }else{
550  // push actual string for case sensitive compare
551  spRule->spCurrentOp->uiId = ID_TBS;
552  }
553  }
554  return ID_AST_OK;
555 }
556 
557 static aint uiTbsOp(ast_data* spAstData){
558  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
559  semantic_rule* spRule = spData->spCurrentRule;
560  if(spAstData->uiState == ID_AST_PRE){
561  semantic_op sOp = {ID_TBS};
562  sOp.uiStringIndex = uiVecLen(spData->vpVecAcharsTable);
563  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
564  }else{
565  spRule->spCurrentOp->uiStringLength = uiVecLen(spData->vpVecAcharsTable) - spRule->spCurrentOp->uiStringIndex;
566  }
567  return ID_AST_OK;
568 }
569 
570 static aint uiDstring(ast_data* spAstData){
571  if(spAstData->uiState == ID_AST_POST){
572  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
573  vpVecPush(spData->vpVecAcharsTable, (void*)&spData->luiNum);
574  }
575  return ID_AST_OK;
576 }
577 
578 static aint uiTrgOp(ast_data* spAstData){
579  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
580  semantic_rule* spRule = spData->spCurrentRule;
581  if(spAstData->uiState == ID_AST_PRE){
582  semantic_op sOp = {ID_TRG};
583  spRule->spCurrentOp = (semantic_op*)vpVecPush(spRule->vpVecOps, &sOp);
584  }else{
585  if(spRule->spCurrentOp->luiMin > spRule->spCurrentOp->luiMax){
586  char caBuf[128];
587  snprintf(caBuf, 128, "TRG: minimum character (%"PRIuMAX") must be <= maximum character (%"PRIuMAX")",
588  spRule->spCurrentOp->luiMin, spRule->spCurrentOp->luiMax);
589  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
590  }
591  }
592  return ID_AST_OK;
593 }
594 
595 static aint uiTlsString(ast_data* spAstData){
596  if(spAstData->uiState == ID_AST_PRE){
597  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
598  semantic_rule* spRule = spData->spCurrentRule;
600  spRule->spCurrentOp->uiStringLength = spAstData->uiPhraseLength;
601 
602  // push the string into the achar table
603  aint ui = 0;
604  for(; ui < spAstData->uiPhraseLength; ui++){
605  luint luiChar = (luint)spAstData->acpString[spAstData->uiPhraseOffset + ui];
606  vpVecPush(spData->vpVecAcharsTable, (void*)&luiChar);
607  }
608  }
609  return ID_AST_OK;
610 }
611 
612 static aint uiStringTab(ast_data* spAstData){
613  if(spAstData->uiState == ID_AST_PRE){
614  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
615  vSemPushError(spData, spAstData->uiPhraseOffset, s_cpNoTab);
616  }
617  return ID_AST_OK;
618 }
619 
620 static aint uiDnum(ast_data* spAstData){
621  if(spAstData->uiState == ID_AST_PRE){
622  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
623  spData->luiNum = (luint)(spAstData->acpString[spAstData->uiPhraseOffset] - 48);
624  aint ui = 1;
625  luint luiTest, luiDigit;
626  spData->luiNum = 0;
627  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
628  if(!bMultiplyLong(10, spData->luiNum, &luiTest)){
629  goto fail;
630  }
631  luiDigit = (luint)(spAstData->acpString[spAstData->uiPhraseOffset + ui] - 48);
632  if(!bSumLong(luiTest, luiDigit, &spData->luiNum)){
633  goto fail;
634  }
635  }
636  return ID_AST_OK;
637  fail:{
638  char caString[spAstData->uiPhraseLength + 1];
639  char caBuf[128];
640  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
641  caString[spAstData->uiPhraseLength] = 0;
642  snprintf(caBuf, 128,
643  "decimal number out of range: %s", caString);
644  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
645  }
646  }
647  return ID_AST_OK;
648 }
649 
650 static aint uiBnum(ast_data* spAstData){
651  if(spAstData->uiState == ID_AST_PRE){
652  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
653  spData->luiNum = (luint)(spAstData->acpString[spAstData->uiPhraseOffset] - 48);
654  aint ui;
655  luint luiTest, luiDigit;
656  spData->luiNum = 0;
657  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
658  if(!bMultiplyLong(2, spData->luiNum, &luiTest)){
659  goto fail;
660  }
661  luiDigit = (luint)(spAstData->acpString[spAstData->uiPhraseOffset + ui] - 48);
662  if(!bSumLong(luiTest, luiDigit, &spData->luiNum)){
663  goto fail;
664  }
665  }
666  return ID_AST_OK;
667  fail:{
668  char caString[spAstData->uiPhraseLength + 1];
669  char caBuf[128];
670  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
671  caString[spAstData->uiPhraseLength] = 0;
672  snprintf(caBuf, 128,
673  "binary number out of range: %s", caString);
674  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
675  }
676 }
677  return ID_AST_OK;
678 }
679 
680 static luint luiGetNum(luint luiChar){
681  luint luiNum;
682  if(luiChar >= 48 && luiChar <= 57){
683  luiNum = luiChar - 48;
684  }else if(luiChar >= 65 && luiChar <= 70){
685  luiNum = luiChar - 55;
686  }else{
687  luiNum = luiChar - 87;
688  }
689  return luiNum;
690 }
691 static aint uiXnum(ast_data* spAstData){
692  if(spAstData->uiState == ID_AST_PRE){
693  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
694  spData->luiNum = luiGetNum((luint)spAstData->acpString[spAstData->uiPhraseOffset]);
695  aint ui;
696  luint luiTest, luiDigit;
697  spData->luiNum = 0;
698  for(ui = 0; ui < spAstData->uiPhraseLength; ui++){
699  if(!bMultiplyLong(16, spData->luiNum, &luiTest)){
700  goto fail;
701  }
702  luiDigit = luiGetNum((luint)spAstData->acpString[spAstData->uiPhraseOffset + ui]);
703  if(!bSumLong(luiTest, luiDigit, &spData->luiNum)){
704  goto fail;
705  }
706  }
707  return ID_AST_OK;
708  fail:{
709  char caString[spAstData->uiPhraseLength + 1];
710  char caBuf[128];
711  memcpy((void*)caString, (void*)&spAstData->acpString[spAstData->uiPhraseOffset], spAstData->uiPhraseLength);
712  caString[spAstData->uiPhraseLength] = 0;
713  snprintf(caBuf, 128,
714  "hexidecimal number out of range: %s", caString);
715  vSemPushError(spData, spAstData->uiPhraseOffset, caBuf);
716  }
717  }
718  return ID_AST_OK;
719 }
720 
721 static aint uiDmin(ast_data* spAstData){
722  if(spAstData->uiState == ID_AST_POST){
723  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
724  spData->spCurrentRule->spCurrentOp->luiMin = spData->luiNum;
725  }
726  return ID_AST_OK;
727 }
728 
729 static aint uiDmax(ast_data* spAstData){
730  if(spAstData->uiState == ID_AST_POST){
731  semantic_data* spData = (semantic_data*)spAstData->vpUserData;
732  spData->spCurrentRule->spCurrentOp->luiMax = spData->luiNum;
733  }
734  return ID_AST_OK;
735 }
736 
740 void vSabnfGrammarAstCallbacks(void* vpAstCtx) {
741  aint ui;
743  cb[SABNF_GRAMMAR_ABGOP] = uiAbgOp;
744  cb[SABNF_GRAMMAR_AENOP] = uiAenOp;
745  cb[SABNF_GRAMMAR_ALPHANUM] = NULL;
746  cb[SABNF_GRAMMAR_ALTERNATION] = uiAlternation;
747  cb[SABNF_GRAMMAR_ALTOP] = NULL;
748  cb[SABNF_GRAMMAR_ANDOP] = uiAndOp;
749  cb[SABNF_GRAMMAR_BASICELEMENT] = NULL;
751  cb[SABNF_GRAMMAR_BIN] = NULL;
752  cb[SABNF_GRAMMAR_BKAOP] = uiBkaOp;
753  cb[SABNF_GRAMMAR_BKNOP] = uiBknOp;
754  cb[SABNF_GRAMMAR_BKR_NAME] = uiBkrName;
755  cb[SABNF_GRAMMAR_BKRMODIFIER] = NULL;
756  cb[SABNF_GRAMMAR_BKROP] = uiBkrOp;
757  cb[SABNF_GRAMMAR_BLANKLINE] = NULL;
758  cb[SABNF_GRAMMAR_BMAX] = uiDmax;
759  cb[SABNF_GRAMMAR_BMIN] = uiDmin;
760  cb[SABNF_GRAMMAR_BNUM] = uiBnum;
761  cb[SABNF_GRAMMAR_BSTRING] = uiDstring;
762  cb[SABNF_GRAMMAR_CATOP] = NULL;
763  cb[SABNF_GRAMMAR_CI] = uiCi;
764  cb[SABNF_GRAMMAR_CLSCLOSE] = NULL;
765  cb[SABNF_GRAMMAR_CLSOP] = uiClsOp;
766  cb[SABNF_GRAMMAR_CLSOPEN] = NULL;
767  cb[SABNF_GRAMMAR_CLSSTRING] = uiClsString;
768  cb[SABNF_GRAMMAR_COMMENT] = NULL;
769  cb[SABNF_GRAMMAR_CONCATENATION] = uiConcatenation;
770  cb[SABNF_GRAMMAR_CS] = uiCs;
771  cb[SABNF_GRAMMAR_DEC] = NULL;
772  cb[SABNF_GRAMMAR_DEFINED] = NULL;
773  cb[SABNF_GRAMMAR_DEFINEDAS] = NULL;
774  cb[SABNF_GRAMMAR_DEFINEDASERROR] = NULL;
775  cb[SABNF_GRAMMAR_DEFINEDASTEST] = NULL;
776  cb[SABNF_GRAMMAR_DMAX] = uiDmax;
777  cb[SABNF_GRAMMAR_DMIN] = uiDmin;
778  cb[SABNF_GRAMMAR_DNUM] = uiDnum;
779  cb[SABNF_GRAMMAR_DSTRING] = uiDstring;
780  cb[SABNF_GRAMMAR_ENAME] = NULL;
781  cb[SABNF_GRAMMAR_FILE] = NULL;
782  cb[SABNF_GRAMMAR_GROUP] = NULL;
783  cb[SABNF_GRAMMAR_GROUPCLOSE] = NULL;
784  cb[SABNF_GRAMMAR_GROUPERROR] = NULL;
785  cb[SABNF_GRAMMAR_GROUPOPEN] = NULL;
786  cb[SABNF_GRAMMAR_HEX] = NULL;
787  cb[SABNF_GRAMMAR_INCALT] = uiIncAlt;
788  cb[SABNF_GRAMMAR_LINECONTINUE] = NULL;
789  cb[SABNF_GRAMMAR_LINEEND] = NULL;
790  cb[SABNF_GRAMMAR_LINEENDERROR] = NULL;
791  cb[SABNF_GRAMMAR_MODIFIER] = NULL;
792  cb[SABNF_GRAMMAR_NOTOP] = uiNotOp;
793  cb[SABNF_GRAMMAR_OPTION] = NULL;
794  cb[SABNF_GRAMMAR_OPTIONCLOSE] = NULL;
795  cb[SABNF_GRAMMAR_OPTIONERROR] = NULL;
796  cb[SABNF_GRAMMAR_OPTIONOPEN] = uiOptionOpen;
797  cb[SABNF_GRAMMAR_OWSP] = NULL;
798  cb[SABNF_GRAMMAR_PM] = uiBkrPm;
799  cb[SABNF_GRAMMAR_PREDICATE] = NULL;
800  cb[SABNF_GRAMMAR_PROSVAL] = NULL;
801  cb[SABNF_GRAMMAR_PROSVALCLOSE] = NULL;
802  cb[SABNF_GRAMMAR_PROSVALOPEN] = NULL;
803  cb[SABNF_GRAMMAR_PROSVALSTRING] = NULL;
804  cb[SABNF_GRAMMAR_REP_MAX] = uiRepMax;
805  cb[SABNF_GRAMMAR_REP_MIN] = uiRepMin;
806  cb[SABNF_GRAMMAR_REP_MIN_MAX] = uiRepMinMax;
807  cb[SABNF_GRAMMAR_REP_NUM] = NULL;
808  cb[SABNF_GRAMMAR_REPETITION] = uiRepetition;
809  cb[SABNF_GRAMMAR_REPOP] = uiRepOp;
810  cb[SABNF_GRAMMAR_RNAME] = NULL;
811  cb[SABNF_GRAMMAR_RNMOP] = uiRnmOp;
812  cb[SABNF_GRAMMAR_RULE] = NULL;
813  cb[SABNF_GRAMMAR_RULEERROR] = NULL;
814  cb[SABNF_GRAMMAR_RULELOOKUP] = uiRuleLookup;
815  cb[SABNF_GRAMMAR_RULENAME] = uiRuleName;
816  cb[SABNF_GRAMMAR_RULENAMEERROR] = NULL;
817  cb[SABNF_GRAMMAR_RULENAMETEST] = NULL;
818  cb[SABNF_GRAMMAR_SPACE] = NULL;
819  cb[SABNF_GRAMMAR_STRINGTAB] = uiStringTab;
820  cb[SABNF_GRAMMAR_TBSOP] = uiTbsOp;
821  cb[SABNF_GRAMMAR_TLSCASE] = NULL;
822  cb[SABNF_GRAMMAR_TLSCLOSE] = NULL;
823  cb[SABNF_GRAMMAR_TLSOP] = uiTlsOp;
824  cb[SABNF_GRAMMAR_TLSOPEN] = NULL;
825  cb[SABNF_GRAMMAR_TLSSTRING] = uiTlsString;
826  cb[SABNF_GRAMMAR_TRGOP] = uiTrgOp;
827  cb[SABNF_GRAMMAR_UDT_EMPTY] = uiUdtEmpty;
828  cb[SABNF_GRAMMAR_UDT_NON_EMPTY] = uiUdtNonEmpty;
829  cb[SABNF_GRAMMAR_UDTOP] = uiUdtOp;
830  cb[SABNF_GRAMMAR_UM] = uiBkrUm;
831  cb[SABNF_GRAMMAR_UNAME] = NULL;
832  cb[SABNF_GRAMMAR_WSP] = NULL;
833  cb[SABNF_GRAMMAR_XMAX] = uiDmax;
834  cb[SABNF_GRAMMAR_XMIN] = uiDmin;
835  cb[SABNF_GRAMMAR_XNUM] = uiXnum;
836  cb[SABNF_GRAMMAR_XSTRING] = uiDstring;
837  for (ui = 0; ui < (aint) RULE_COUNT_SABNF_GRAMMAR; ui += 1) {
838  vAstSetRuleCallback(vpAstCtx, ui, cb[ui]);
839  }
840 }
SABNF_GRAMMAR_TLSCASE
#define SABNF_GRAMMAR_TLSCASE
Definition: sabnf-grammar.h:117
SABNF_GRAMMAR_TLSCLOSE
#define SABNF_GRAMMAR_TLSCLOSE
Definition: sabnf-grammar.h:118
SABNF_GRAMMAR_RULE
#define SABNF_GRAMMAR_RULE
Definition: sabnf-grammar.h:108
ID_BKR_CASE_I
#define ID_BKR_CASE_I
the back reference is case insensitive
Definition: parser.h:121
semantic_data::uiNameLength
aint uiNameLength
Definition: semantics.h:93
SABNF_GRAMMAR_REP_NUM
#define SABNF_GRAMMAR_REP_NUM
Definition: sabnf-grammar.h:103
SABNF_GRAMMAR_NOTOP
#define SABNF_GRAMMAR_NOTOP
Definition: sabnf-grammar.h:88
semantic_rule::uiIndex
aint uiIndex
Definition: semantics.h:72
semantic_op::uiNameLength
aint uiNameLength
Definition: semantics.h:61
semantic_op::luiMin
luint luiMin
Definition: semantics.h:53
ID_RNM
#define ID_RNM
rule name
Definition: parser.h:46
semantic_op::vpVecChildList
void * vpVecChildList
Definition: semantics.h:52
SABNF_GRAMMAR_RULENAMEERROR
#define SABNF_GRAMMAR_RULENAMEERROR
Definition: sabnf-grammar.h:112
api::cpInput
char * cpInput
Definition: apip.h:139
semantic_data
User data passed to the AST translator for use by the AST callback functions.
Definition: semantics.h:83
ast_data::uiPhraseOffset
aint uiPhraseOffset
Definition: ast.h:72
vAstSetRuleCallback
void vAstSetRuleCallback(void *vpCtx, aint uiRuleIndex, ast_callback pfnCallback)
Define a callback function for a single rule on the AST.
Definition: ast.c:243
SABNF_GRAMMAR_COMMENT
#define SABNF_GRAMMAR_COMMENT
Definition: sabnf-grammar.h:64
SABNF_GRAMMAR_GROUPERROR
#define SABNF_GRAMMAR_GROUPERROR
Definition: sabnf-grammar.h:80
SABNF_GRAMMAR_UDTOP
#define SABNF_GRAMMAR_UDTOP
Definition: sabnf-grammar.h:125
semantic_rule::vpVecOps
void * vpVecOps
Definition: semantics.h:78
SABNF_GRAMMAR_XSTRING
#define SABNF_GRAMMAR_XSTRING
Definition: sabnf-grammar.h:132
ID_AST_POST
#define ID_AST_POST
indicates post-node-traversal AST callback state (up the tree)
Definition: parser.h:92
semantic_op::cpName
char * cpName
Definition: semantics.h:60
SABNF_GRAMMAR_TLSOPEN
#define SABNF_GRAMMAR_TLSOPEN
Definition: sabnf-grammar.h:120
ID_ALT
#define ID_ALT
alternation
Definition: parser.h:43
SABNF_GRAMMAR_OPTIONERROR
#define SABNF_GRAMMAR_OPTIONERROR
Definition: sabnf-grammar.h:91
SABNF_GRAMMAR_ALPHANUM
#define SABNF_GRAMMAR_ALPHANUM
Definition: sabnf-grammar.h:41
SABNF_GRAMMAR_REPETITION
#define SABNF_GRAMMAR_REPETITION
Definition: sabnf-grammar.h:104
SABNF_GRAMMAR_WSP
#define SABNF_GRAMMAR_WSP
Definition: sabnf-grammar.h:128
semantics.h
Header file for the semantic translation functions.
ID_BKR
#define ID_BKR
back reference to a previously matched rule or UDT name
Definition: parser.h:58
semantic_data::luiNum
luint luiNum
Definition: semantics.h:89
SABNF_GRAMMAR_DEC
#define SABNF_GRAMMAR_DEC
Definition: sabnf-grammar.h:67
ID_UDT
#define ID_UDT
user-defined terminal
Definition: parser.h:55
semantic_rule::uiCurrentCat
aint uiCurrentCat
Definition: semantics.h:74
ID_AST_OK
#define ID_AST_OK
normal AST callback function return
Definition: parser.h:93
apip.h
Private header file for the APG API suite of functions.
ID_AST_PRE
#define ID_AST_PRE
indicates pre-node-traversal AST callback state (down the tree)
Definition: parser.h:91
ast_data
Input data to the AST callback functions.
Definition: ast.h:69
semantic_data::vpVecRules
void * vpVecRules
Definition: semantics.h:99
SABNF_GRAMMAR_DEFINEDASERROR
#define SABNF_GRAMMAR_DEFINEDASERROR
Definition: sabnf-grammar.h:70
SABNF_GRAMMAR_OPTIONCLOSE
#define SABNF_GRAMMAR_OPTIONCLOSE
Definition: sabnf-grammar.h:90
bSumLong
abool bSumLong(luint uiL, luint uiR, luint *uipA)
Add two long unsigned integers with overflow notification.
Definition: tools.c:131
SABNF_GRAMMAR_INCALT
#define SABNF_GRAMMAR_INCALT
Definition: sabnf-grammar.h:83
SABNF_GRAMMAR_GROUP
#define SABNF_GRAMMAR_GROUP
Definition: sabnf-grammar.h:78
ast_data::uiPhraseLength
aint uiPhraseLength
Definition: ast.h:73
SABNF_GRAMMAR_CLSOP
#define SABNF_GRAMMAR_CLSOP
Definition: sabnf-grammar.h:61
SABNF_GRAMMAR_HEX
#define SABNF_GRAMMAR_HEX
Definition: sabnf-grammar.h:82
ID_NOT
#define ID_NOT
negative look ahead
Definition: parser.h:57
ID_AND
#define ID_AND
positive look ahead
Definition: parser.h:56
vpVecAt
void * vpVecAt(void *vpCtx, aint uiIndex)
Get a the indexed vector element. The vector is not altered.
Definition: vector.c:362
SABNF_GRAMMAR_ALTOP
#define SABNF_GRAMMAR_ALTOP
Definition: sabnf-grammar.h:43
ID_BKR_CASE_S
#define ID_BKR_CASE_S
the back reference is case sensitive
Definition: parser.h:120
SABNF_GRAMMAR_GROUPCLOSE
#define SABNF_GRAMMAR_GROUPCLOSE
Definition: sabnf-grammar.h:79
SABNF_GRAMMAR_DMIN
#define SABNF_GRAMMAR_DMIN
Definition: sabnf-grammar.h:73
SABNF_GRAMMAR_RULENAMETEST
#define SABNF_GRAMMAR_RULENAMETEST
Definition: sabnf-grammar.h:113
semantic_rule::uiCurrentAlt
aint uiCurrentAlt
Definition: semantics.h:73
XTHROW
#define XTHROW(ctx, msg)
Exception throw macro.
Definition: exception.h:67
semantic_op::uiMode
aint uiMode
Definition: semantics.h:57
semantic_rule::vpVecAltStack
void * vpVecAltStack
Definition: semantics.h:76
semantic_rule::spCurrentOp
semantic_op * spCurrentOp
Definition: semantics.h:75
vpVecPop
void * vpVecPop(void *vpCtx)
Pops one element from the end of the array.
Definition: vector.c:250
semantic_op::uiCase
aint uiCase
Definition: semantics.h:56
aint
uint_fast32_t aint
The APG parser's unsigned integer type.
Definition: apg.h:79
vpVecLast
void * vpVecLast(void *vpCtx)
Get the last element one the vector. The vector is not altered.
Definition: vector.c:343
semantic_data::vpVecAcharsTable
void * vpVecAcharsTable
Definition: semantics.h:96
SABNF_GRAMMAR_BKROP
#define SABNF_GRAMMAR_BKROP
Definition: sabnf-grammar.h:52
semantic_rule::vpVecCatStack
void * vpVecCatStack
Definition: semantics.h:77
ID_CAT
#define ID_CAT
concatenation
Definition: parser.h:44
sabnf-grammar.h
SABNF_GRAMMAR_OPTIONOPEN
#define SABNF_GRAMMAR_OPTIONOPEN
Definition: sabnf-grammar.h:92
SABNF_GRAMMAR_BASICELEMENT
#define SABNF_GRAMMAR_BASICELEMENT
Definition: sabnf-grammar.h:45
semantic_data::uiRuleIndex
aint uiRuleIndex
Definition: semantics.h:94
SABNF_GRAMMAR_UNAME
#define SABNF_GRAMMAR_UNAME
Definition: sabnf-grammar.h:127
uiVecLen
aint uiVecLen(void *vpCtx)
Get the vector length. That is, the number of elements on the vector.
Definition: vector.c:385
SABNF_GRAMMAR_SPACE
#define SABNF_GRAMMAR_SPACE
Definition: sabnf-grammar.h:114
vpVecCtor
void * vpVecCtor(void *vpMem, aint uiElementSize, aint uiInitialAlloc)
The vector object constructor.
Definition: vector.c:118
SABNF_GRAMMAR_REPOP
#define SABNF_GRAMMAR_REPOP
Definition: sabnf-grammar.h:105
ID_TRG
#define ID_TRG
terminal range
Definition: parser.h:47
semantic_data::uiIncAlt
aint uiIncAlt
Definition: semantics.h:87
SABNF_GRAMMAR_BMAX
#define SABNF_GRAMMAR_BMAX
Definition: sabnf-grammar.h:54
SABNF_GRAMMAR_CLSCLOSE
#define SABNF_GRAMMAR_CLSCLOSE
Definition: sabnf-grammar.h:60
ID_REP
#define ID_REP
repetition
Definition: parser.h:45
SABNF_GRAMMAR_CI
#define SABNF_GRAMMAR_CI
Definition: sabnf-grammar.h:59
SABNF_GRAMMAR_STRINGTAB
#define SABNF_GRAMMAR_STRINGTAB
Definition: sabnf-grammar.h:115
ast_data::uiState
aint uiState
Definition: ast.h:74
SABNF_GRAMMAR_DEFINEDAS
#define SABNF_GRAMMAR_DEFINEDAS
Definition: sabnf-grammar.h:69
ast_callback
aint(* ast_callback)(ast_data *spData)
The prototype for AST translation callback functions.
Definition: ast.h:91
SABNF_GRAMMAR_RULENAME
#define SABNF_GRAMMAR_RULENAME
Definition: sabnf-grammar.h:111
SABNF_GRAMMAR_DSTRING
#define SABNF_GRAMMAR_DSTRING
Definition: sabnf-grammar.h:75
SABNF_GRAMMAR_PM
#define SABNF_GRAMMAR_PM
Definition: sabnf-grammar.h:94
SABNF_GRAMMAR_BKNOP
#define SABNF_GRAMMAR_BKNOP
Definition: sabnf-grammar.h:49
RULENAME_MAX
#define RULENAME_MAX
Definition: semantics.h:37
luint
uintmax_t luint
luint is used to cast integers suitable for the %"PRIuMAX" printf format.
Definition: apg.h:133
SABNF_GRAMMAR_UM
#define SABNF_GRAMMAR_UM
Definition: sabnf-grammar.h:126
SABNF_GRAMMAR_BKRMODIFIER
#define SABNF_GRAMMAR_BKRMODIFIER
Definition: sabnf-grammar.h:51
semantic_op
Generalized opcode for first-pass semantic processing.
Definition: semantics.h:50
RULE_COUNT_SABNF_GRAMMAR
#define RULE_COUNT_SABNF_GRAMMAR
Definition: sabnf-grammar.h:133
SABNF_GRAMMAR_CONCATENATION
#define SABNF_GRAMMAR_CONCATENATION
Definition: sabnf-grammar.h:65
SABNF_GRAMMAR_BNUM
#define SABNF_GRAMMAR_BNUM
Definition: sabnf-grammar.h:56
APG_UNDEFINED
#define APG_UNDEFINED
Definition: apg.h:318
SABNF_GRAMMAR_TLSSTRING
#define SABNF_GRAMMAR_TLSSTRING
Definition: sabnf-grammar.h:121
SABNF_GRAMMAR_PROSVALSTRING
#define SABNF_GRAMMAR_PROSVALSTRING
Definition: sabnf-grammar.h:99
SABNF_GRAMMAR_GROUPOPEN
#define SABNF_GRAMMAR_GROUPOPEN
Definition: sabnf-grammar.h:81
ast_data::acpString
const achar * acpString
Definition: ast.h:70
semantic_rule::uiNameLength
aint uiNameLength
Definition: semantics.h:71
vpVecFirst
void * vpVecFirst(void *vpCtx)
Get the first element one the vector. The vector is not altered.
Definition: vector.c:326
ID_BKA
#define ID_BKA
positive look behind
Definition: parser.h:59
SABNF_GRAMMAR_MODIFIER
#define SABNF_GRAMMAR_MODIFIER
Definition: sabnf-grammar.h:87
semantic_data::spApi
api * spApi
Definition: semantics.h:84
SABNF_GRAMMAR_ABGOP
#define SABNF_GRAMMAR_ABGOP
Definition: sabnf-grammar.h:39
SABNF_GRAMMAR_RULELOOKUP
#define SABNF_GRAMMAR_RULELOOKUP
Definition: sabnf-grammar.h:110
semantic_rule::cpName
char * cpName
Definition: semantics.h:69
SABNF_GRAMMAR_LINEENDERROR
#define SABNF_GRAMMAR_LINEENDERROR
Definition: sabnf-grammar.h:86
semantic_op::luiMax
luint luiMax
Definition: semantics.h:54
vSabnfGrammarAstCallbacks
void vSabnfGrammarAstCallbacks(void *vpAstCtx)
Set the callback functions for the AST translation of the semantic phase parse to opcodes.
Definition: semantic-callbacks.c:740
SABNF_GRAMMAR_DMAX
#define SABNF_GRAMMAR_DMAX
Definition: sabnf-grammar.h:72
SABNF_GRAMMAR_LINEEND
#define SABNF_GRAMMAR_LINEEND
Definition: sabnf-grammar.h:85
SABNF_GRAMMAR_LINECONTINUE
#define SABNF_GRAMMAR_LINECONTINUE
Definition: sabnf-grammar.h:84
SABNF_GRAMMAR_BASICELEMENTERR
#define SABNF_GRAMMAR_BASICELEMENTERR
Definition: sabnf-grammar.h:46
semantic_data::spCurrentRule
semantic_rule * spCurrentRule
Definition: semantics.h:90
uiFindRule
aint uiFindRule(semantic_rule *spRules, aint uiRuleCount, const char *cpName, aint uiNameLength)
Find the index of the named rule in the rule list.
Definition: semantics.c:160
SABNF_GRAMMAR_TLSOP
#define SABNF_GRAMMAR_TLSOP
Definition: sabnf-grammar.h:119
ID_TLS
#define ID_TLS
terminal literal string
Definition: parser.h:49
APG_TRUE
#define APG_TRUE
Definition: apg.h:291
SABNF_GRAMMAR_PROSVALOPEN
#define SABNF_GRAMMAR_PROSVALOPEN
Definition: sabnf-grammar.h:98
SABNF_GRAMMAR_CLSOPEN
#define SABNF_GRAMMAR_CLSOPEN
Definition: sabnf-grammar.h:62
SABNF_GRAMMAR_CS
#define SABNF_GRAMMAR_CS
Definition: sabnf-grammar.h:66
SABNF_GRAMMAR_UDT_NON_EMPTY
#define SABNF_GRAMMAR_UDT_NON_EMPTY
Definition: sabnf-grammar.h:124
SABNF_GRAMMAR_BSTRING
#define SABNF_GRAMMAR_BSTRING
Definition: sabnf-grammar.h:57
SABNF_GRAMMAR_OPTION
#define SABNF_GRAMMAR_OPTION
Definition: sabnf-grammar.h:89
SABNF_GRAMMAR_TRGOP
#define SABNF_GRAMMAR_TRGOP
Definition: sabnf-grammar.h:122
SABNF_GRAMMAR_FILE
#define SABNF_GRAMMAR_FILE
Definition: sabnf-grammar.h:77
SABNF_GRAMMAR_RULEERROR
#define SABNF_GRAMMAR_RULEERROR
Definition: sabnf-grammar.h:109
SABNF_GRAMMAR_DNUM
#define SABNF_GRAMMAR_DNUM
Definition: sabnf-grammar.h:74
SABNF_GRAMMAR_XMIN
#define SABNF_GRAMMAR_XMIN
Definition: sabnf-grammar.h:130
semantic_op::uiStringIndex
int uiStringIndex
Definition: semantics.h:58
bMultiplyLong
abool bMultiplyLong(luint luiL, luint luiR, luint *luipA)
Multiply two long unsigned integers with overflow notification.
Definition: tools.c:110
ast_data::vpUserData
void * vpUserData
Definition: ast.h:80
SABNF_GRAMMAR_CATOP
#define SABNF_GRAMMAR_CATOP
Definition: sabnf-grammar.h:58
ID_BKN
#define ID_BKN
negative look behind
Definition: parser.h:60
SABNF_GRAMMAR_REP_MAX
#define SABNF_GRAMMAR_REP_MAX
Definition: sabnf-grammar.h:100
SABNF_GRAMMAR_ALTERNATION
#define SABNF_GRAMMAR_ALTERNATION
Definition: sabnf-grammar.h:42
SABNF_GRAMMAR_BIN
#define SABNF_GRAMMAR_BIN
Definition: sabnf-grammar.h:47
SABNF_GRAMMAR_BKAOP
#define SABNF_GRAMMAR_BKAOP
Definition: sabnf-grammar.h:48
SABNF_GRAMMAR_PREDICATE
#define SABNF_GRAMMAR_PREDICATE
Definition: sabnf-grammar.h:95
SABNF_GRAMMAR_BKR_NAME
#define SABNF_GRAMMAR_BKR_NAME
Definition: sabnf-grammar.h:50
semantic_data::cpName
char * cpName
Definition: semantics.h:91
SABNF_GRAMMAR_REP_MIN
#define SABNF_GRAMMAR_REP_MIN
Definition: sabnf-grammar.h:101
SABNF_GRAMMAR_ANDOP
#define SABNF_GRAMMAR_ANDOP
Definition: sabnf-grammar.h:44
semantic_rule
Generalized rule for first-pass semantic processing.
Definition: semantics.h:68
SABNF_GRAMMAR_XNUM
#define SABNF_GRAMMAR_XNUM
Definition: sabnf-grammar.h:131
ID_ABG
#define ID_ABG
anchor - beginning of string
Definition: parser.h:61
SABNF_GRAMMAR_OWSP
#define SABNF_GRAMMAR_OWSP
Definition: sabnf-grammar.h:93
api::spException
exception * spException
Definition: apip.h:125
SABNF_GRAMMAR_RNMOP
#define SABNF_GRAMMAR_RNMOP
Definition: sabnf-grammar.h:107
SABNF_GRAMMAR_BMIN
#define SABNF_GRAMMAR_BMIN
Definition: sabnf-grammar.h:55
SABNF_GRAMMAR_DEFINEDASTEST
#define SABNF_GRAMMAR_DEFINEDASTEST
Definition: sabnf-grammar.h:71
vLineError
void vLineError(api *spCtx, aint uiCharIndex, const char *cpSrc, const char *cpMsg)
Finds the grammar line associated with a character index and formats an error message to the error lo...
Definition: input.c:383
SABNF_GRAMMAR_TBSOP
#define SABNF_GRAMMAR_TBSOP
Definition: sabnf-grammar.h:116
SABNF_GRAMMAR_PROSVAL
#define SABNF_GRAMMAR_PROSVAL
Definition: sabnf-grammar.h:96
SABNF_GRAMMAR_XMAX
#define SABNF_GRAMMAR_XMAX
Definition: sabnf-grammar.h:129
SABNF_GRAMMAR_ENAME
#define SABNF_GRAMMAR_ENAME
Definition: sabnf-grammar.h:76
SABNF_GRAMMAR_RNAME
#define SABNF_GRAMMAR_RNAME
Definition: sabnf-grammar.h:106
ID_BKR_MODE_U
#define ID_BKR_MODE_U
the back reference is universal mode
Definition: parser.h:118
ID_TBS
#define ID_TBS
terminal binary string
Definition: parser.h:48
vpVecPush
void * vpVecPush(void *vpCtx, void *vpElement)
Adds one element to the end of the array.
Definition: vector.c:193
SABNF_GRAMMAR_BLANKLINE
#define SABNF_GRAMMAR_BLANKLINE
Definition: sabnf-grammar.h:53
ID_BKR_MODE_P
#define ID_BKR_MODE_P
the back reference is parent mode
Definition: parser.h:119
SABNF_GRAMMAR_CLSSTRING
#define SABNF_GRAMMAR_CLSSTRING
Definition: sabnf-grammar.h:63
SABNF_GRAMMAR_PROSVALCLOSE
#define SABNF_GRAMMAR_PROSVALCLOSE
Definition: sabnf-grammar.h:97
semantic_op::uiEmpty
aint uiEmpty
Definition: semantics.h:55
SABNF_GRAMMAR_DEFINED
#define SABNF_GRAMMAR_DEFINED
Definition: sabnf-grammar.h:68
SABNF_GRAMMAR_AENOP
#define SABNF_GRAMMAR_AENOP
Definition: sabnf-grammar.h:40
ID_AEN
#define ID_AEN
anchor - end of string
Definition: parser.h:62
api.h
Public header file for the APG API suite of functions.
SABNF_GRAMMAR_REP_MIN_MAX
#define SABNF_GRAMMAR_REP_MIN_MAX
Definition: sabnf-grammar.h:102
semantic_data::vpMem
void * vpMem
Definition: semantics.h:85
APG_FALSE
#define APG_FALSE
Definition: apg.h:292
SABNF_GRAMMAR_UDT_EMPTY
#define SABNF_GRAMMAR_UDT_EMPTY
Definition: sabnf-grammar.h:123
semantic_data::uiErrorsFound
aint uiErrorsFound
Definition: semantics.h:88
APG Version 7.0 is licensed under the 2-Clause BSD License,
an Open Source Initiative Approved License.