ISC DHCP  4.4.3-P1
A reference DHCPv4 and DHCPv6 implementation
print.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2017-2022 Internet Systems Consortium, Inc. ("ISC")
3  *
4  * Permission to use, copy, modify, and distribute this software for any
5  * purpose with or without fee is hereby granted, provided that the above
6  * copyright notice and this permission notice appear in all copies.
7  *
8  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
11  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
14  * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  *
16  * Internet Systems Consortium, Inc.
17  * PO Box 360
18  * Newmarket, NH 03857 USA
19  * <info@isc.org>
20  * https://www.isc.org/
21  *
22  */
23 
24 #include "keama.h"
25 
26 #include <sys/errno.h>
27 #include <sys/types.h>
28 #include <arpa/inet.h>
29 #include <ctype.h>
30 #include <netdb.h>
31 #include <stdarg.h>
32 #include <stdio.h>
33 #include <string.h>
34 #include <unistd.h>
35 
36 static void debug(const char* fmt, ...);
37 
38 const char *
40 {
41  if (expr->type == ELEMENT_BOOLEAN)
42  return print_boolean_expression(expr, lose);
43  if (expr->type == ELEMENT_INTEGER)
44  return print_numeric_expression(expr, lose);
45  if (expr->type == ELEMENT_STRING)
46  return print_data_expression(expr, lose);
47 
48  if (is_boolean_expression(expr))
49  return print_boolean_expression(expr, lose);
50  if (is_numeric_expression(expr))
51  return print_numeric_expression(expr, lose);
52  if (is_data_expression(expr))
53  return print_data_expression(expr, lose);
54  *lose = ISC_TRUE;
55  return "???";
56 }
57 
58 const char *
60 {
61  struct string *result;
62 
63  if (expr->type == ELEMENT_BOOLEAN) {
64  if (boolValue(expr))
65  return "true";
66  else
67  return "false";
68  }
69 
70  /*
71  * From is_boolean_expression
72  */
73  if (expr->type != ELEMENT_MAP) {
74  *lose = ISC_TRUE;
75  return "???";
76  }
77  result = allocString();
78 
79  /* check */
80  if (mapContains(expr, "check")) {
81  struct element *name;
82 
83  appendString(result, "check ");
84  name = mapGet(expr, "check");
85  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
86  *lose = ISC_TRUE;
87  appendString(result, "???");
88  } else
89  concatString(result, stringValue(name));
90  return result->content;
91  }
92 
93  /* exists */
94  if (mapContains(expr, "exists")) {
95  struct element *arg;
96  struct element *universe;
97  struct element *name;
98 
99  appendString(result, "exists ");
100  arg = mapGet(expr, "exists");
101  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
102  *lose = ISC_TRUE;
103  appendString(result, "???");
104  return result->content;
105  }
106  universe = mapGet(arg, "universe");
107  if ((universe == NULL) || (universe->type != ELEMENT_STRING)) {
108  *lose = ISC_TRUE;
109  appendString(result, "???");
110  return result->content;
111  }
113  appendString(result, ".");
114  name = mapGet(arg, "name");
115  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
116  *lose = ISC_TRUE;
117  appendString(result, "???");
118  return result->content;
119  }
120  concatString(result, stringValue(name));
121  return result->content;
122  }
123 
124  /* variable-exists */
125  if (mapContains(expr, "variable-exists")) {
126  struct element *name;
127 
128  appendString(result, "variable-exists ");
129  name = mapGet(expr, "variable-exists");
130  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
131  *lose = ISC_TRUE;
132  appendString(result, "???");
133  } else
134  concatString(result, stringValue(name));
135  return result->content;
136  }
137 
138  /* equal */
139  if (mapContains(expr, "equal")) {
140  struct element *arg;
141  struct element *left;
142  struct element *right;
143  isc_boolean_t add_parenthesis;
144 
145  appendString(result, "equal ");
146  arg = mapGet(expr, "equal");
147  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
148  *lose = ISC_TRUE;
149  appendString(result, "???");
150  return result->content;
151  }
152  left = mapGet(arg, "left");
153  if (left == NULL) {
154  *lose = ISC_TRUE;
155  appendString(result, "???");
156  return result->content;
157  }
158  result = allocString();
159  add_parenthesis = ISC_TF(expr_precedence(expr_equal,
160  left) < 0);
161  if (add_parenthesis)
162  appendString(result, "(");
163  appendString(result, print_expression(left, lose));
164  if (add_parenthesis)
165  appendString(result, ")");
166  appendString(result, " = ");
167  right = mapGet(arg, "right");
168  if (right == NULL) {
169  *lose = ISC_TRUE;
170  appendString(result, "???");
171  return result->content;
172  }
173  add_parenthesis = ISC_TF(expr_precedence(expr_equal,
174  right) < 0);
175  if (add_parenthesis)
176  appendString(result, "(");
177  appendString(result, print_expression(right, lose));
178  if (add_parenthesis)
179  appendString(result, ")");
180  return result->content;
181  }
182 
183  /* not-equal */
184  if (mapContains(expr, "not-equal")) {
185  struct element *arg;
186  struct element *left;
187  struct element *right;
188  isc_boolean_t add_parenthesis;
189 
190  appendString(result, "not-equal ");
191  arg = mapGet(expr, "not-equal");
192  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
193  *lose = ISC_TRUE;
194  appendString(result, "???");
195  return result->content;
196  }
197  left = mapGet(arg, "left");
198  if (left == NULL) {
199  *lose = ISC_TRUE;
200  appendString(result, "???");
201  return result->content;
202  }
203  result = allocString();
204  add_parenthesis = ISC_TF(expr_precedence(expr_not_equal,
205  left) < 0);
206  if (add_parenthesis)
207  appendString(result, "(");
208  appendString(result, print_expression(left, lose));
209  if (add_parenthesis)
210  appendString(result, ")");
211  appendString(result, " != ");
212  right = mapGet(arg, "right");
213  if (right == NULL) {
214  *lose = ISC_TRUE;
215  appendString(result, "???");
216  return result->content;
217  }
218  add_parenthesis = ISC_TF(expr_precedence(expr_not_equal,
219  right) < 0);
220  if (add_parenthesis)
221  appendString(result, "(");
222  appendString(result, print_expression(right, lose));
223  if (add_parenthesis)
224  appendString(result, ")");
225  return result->content;
226  }
227 
228  /* regex-match */
229  if (mapContains(expr, "regex-match")) {
230  struct element *arg;
231  struct element *left;
232  struct element *right;
233  isc_boolean_t add_parenthesis;
234 
235  appendString(result, "regex-match ");
236  arg = mapGet(expr, "regex-match");
237  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
238  *lose = ISC_TRUE;
239  appendString(result, "???");
240  return result->content;
241  }
242  left = mapGet(arg, "left");
243  if (left == NULL) {
244  *lose = ISC_TRUE;
245  appendString(result, "???");
246  return result->content;
247  }
248  result = allocString();
249  add_parenthesis = ISC_TF(expr_precedence(expr_regex_match,
250  left) < 0);
251  if (add_parenthesis)
252  appendString(result, "(");
253  appendString(result, print_expression(left, lose));
254  if (add_parenthesis)
255  appendString(result, ")");
256  appendString(result, " ~= ");
257  right = mapGet(arg, "right");
258  if (right == NULL) {
259  *lose = ISC_TRUE;
260  appendString(result, "???");
261  return result->content;
262  }
263  appendString(result, print_expression(right, lose));
264  return result->content;
265  }
266 
267  /* iregex-match */
268  if (mapContains(expr, "iregex-match")) {
269  struct element *arg;
270  struct element *left;
271  struct element *right;
272  isc_boolean_t add_parenthesis;
273 
274  appendString(result, "iregex-match ");
275  arg = mapGet(expr, "iregex-match");
276  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
277  *lose = ISC_TRUE;
278  appendString(result, "???");
279  return result->content;
280  }
281  left = mapGet(arg, "left");
282  if (left == NULL) {
283  *lose = ISC_TRUE;
284  appendString(result, "???");
285  return result->content;
286  }
287  result = allocString();
288  add_parenthesis = ISC_TF(expr_precedence(expr_iregex_match,
289  left) < 0);
290  if (add_parenthesis)
291  appendString(result, "(");
292  appendString(result, print_expression(left, lose));
293  if (add_parenthesis)
294  appendString(result, ")");
295  appendString(result, " ~~ ");
296  right = mapGet(arg, "right");
297  if (right == NULL) {
298  *lose = ISC_TRUE;
299  appendString(result, "???");
300  return result->content;
301  }
302  appendString(result, print_expression(right, lose));
303  return result->content;
304  }
305 
306  /* and */
307  if (mapContains(expr, "and")) {
308  struct element *arg;
309  struct element *left;
310  struct element *right;
311  isc_boolean_t add_parenthesis;
312 
313  appendString(result, "and ");
314  arg = mapGet(expr, "and");
315  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
316  *lose = ISC_TRUE;
317  appendString(result, "???");
318  return result->content;
319  }
320  left = mapGet(arg, "left");
321  if (left == NULL) {
322  *lose = ISC_TRUE;
323  appendString(result, "???");
324  return result->content;
325  }
326  result = allocString();
327  add_parenthesis = ISC_TF(expr_precedence(expr_and,
328  left) < 0);
329  if (add_parenthesis)
330  appendString(result, "(");
331  appendString(result, print_expression(left, lose));
332  if (add_parenthesis)
333  appendString(result, ")");
334  appendString(result, " and ");
335  right = mapGet(arg, "right");
336  if (right == NULL) {
337  *lose = ISC_TRUE;
338  appendString(result, "???");
339  return result->content;
340  }
341  add_parenthesis = ISC_TF(expr_precedence(expr_and,
342  right) < 0);
343  if (add_parenthesis)
344  appendString(result, "(");
345  appendString(result, print_expression(right, lose));
346  if (add_parenthesis)
347  appendString(result, ")");
348  return result->content;
349  }
350 
351  /* or */
352  if (mapContains(expr, "or")) {
353  struct element *arg;
354  struct element *left;
355  struct element *right;
356  isc_boolean_t add_parenthesis;
357 
358  appendString(result, "or ");
359  arg = mapGet(expr, "or");
360  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
361  *lose = ISC_TRUE;
362  appendString(result, "???");
363  return result->content;
364  }
365  left = mapGet(arg, "left");
366  if (left == NULL) {
367  *lose = ISC_TRUE;
368  appendString(result, "???");
369  return result->content;
370  }
371  result = allocString();
372  add_parenthesis = ISC_TF(expr_precedence(expr_or,
373  left) < 0);
374  if (add_parenthesis)
375  appendString(result, "(");
376  appendString(result, print_expression(left, lose));
377  if (add_parenthesis)
378  appendString(result, ")");
379  appendString(result, " or ");
380  right = mapGet(arg, "right");
381  if (right == NULL) {
382  *lose = ISC_TRUE;
383  appendString(result, "???");
384  return result->content;
385  }
386  add_parenthesis = ISC_TF(expr_precedence(expr_or,
387  right) < 0);
388  if (add_parenthesis)
389  appendString(result, "(");
390  appendString(result, print_expression(right, lose));
391  if (add_parenthesis)
392  appendString(result, ")");
393  return result->content;
394  }
395 
396  /* not */
397  if (mapContains(expr, "not")) {
398  struct element *arg;
399  isc_boolean_t add_parenthesis;
400 
401  appendString(result, "not ");
402  arg = mapGet(expr, "not");
403  if (arg == NULL) {
404  *lose = ISC_TRUE;
405  appendString(result, "???");
406  return result->content;
407  }
408  add_parenthesis = ISC_TF(expr_precedence(expr_not,
409  arg) < 0);
410  if (add_parenthesis)
411  appendString(result, "(");
412  appendString(result, print_expression(arg, lose));
413  if (add_parenthesis)
414  appendString(result, ")");
415  return result->content;
416  }
417 
418  /* known */
419  if (mapContains(expr, "known")) {
420  return "known";
421  }
422 
423  /* static */
424  if (mapContains(expr, "static")) {
425  return "static";
426  }
427 
428  /* variable-reference */
429  if (mapContains(expr, "variable-reference")) {
430  struct element *name;
431 
432  appendString(result, "variable-reference ");
433  name = mapGet(expr, "variable-reference");
434  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
435  *lose = ISC_TRUE;
436  appendString(result, "???");
437  return result->content;
438  }
439  return stringValue(name)->content;
440  }
441 
442  /* funcall */
443  if (mapContains(expr, "funcall")) {
444  struct element *arg;
445  struct element *name;
446  struct element *args;
447  size_t i;
448 
449  appendString(result, "funcall ");
450  arg = mapGet(expr, "funcall");
451  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
452  *lose = ISC_TRUE;
453  appendString(result, "???");
454  return result->content;
455  }
456  name = mapGet(arg, "name");
457  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
458  *lose = ISC_TRUE;
459  appendString(result, "???");
460  return result->content;
461  }
462  result = allocString();
463  concatString(result, stringValue(name));
464  appendString(result, "(");
465  args = mapGet(arg, "arguments");
466  if ((args == NULL) || (args->type != ELEMENT_LIST)) {
467  *lose = ISC_TRUE;
468  appendString(result, "???" ")");
469  return result->content;
470  }
471  for (i = 0; i < listSize(args); i++) {
472  struct element *item;
473 
474  if (i != 0)
475  appendString(result, ", ");
476  item = listGet(args, i);
477  if (item == NULL) {
478  debug("funcall null argument %u",
479  (unsigned)i);
480  *lose = ISC_TRUE;
481  appendString(result, "???");
482  continue;
483  }
484  appendString(result, print_expression(item, lose));
485  }
486  appendString(result, ")");
487  return result->content;
488  }
489 
490  *lose = ISC_TRUE;
491  appendString(result, "???");
492  return result->content;
493 }
494 
495 const char *
497 {
498  struct string *result;
499 
500  if (expr->type == ELEMENT_STRING)
501  return quote(stringValue(expr))->content;
502 
503  /*
504  * From is_data_expression
505  */
506  if (expr->type != ELEMENT_MAP) {
507  *lose = ISC_TRUE;
508  return "???";
509  }
510  result = allocString();
511 
512  /* substring */
513  if (mapContains(expr, "substring")) {
514  struct element *arg;
515  struct element *string;
516  struct element *offset;
517  struct element *length;
518 
519  appendString(result, "substring(");
520  arg = mapGet(expr, "substring");
521  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
522  *lose = ISC_TRUE;
523  appendString(result, "???" ")");
524  return result->content;
525  }
526  string = mapGet(arg, "expression");
527  if (string == NULL) {
528  *lose = ISC_TRUE;
529  appendString(result, "???" ")");
530  return result->content;
531  }
532  appendString(result, print_data_expression(string, lose));
533  appendString(result, ", ");
534  offset = mapGet(arg, "offset");
535  if (offset == NULL) {
536  *lose = ISC_TRUE;
537  appendString(result, "???" ")");
538  return result->content;
539  }
540  appendString(result, print_numeric_expression(offset, lose));
541  appendString(result, ", ");
542  length = mapGet(arg, "length");
543  if (length == NULL) {
544  *lose = ISC_TRUE;
545  appendString(result, "???" ")");
546  return result->content;
547  }
548  appendString(result, print_numeric_expression(length, lose));
549  appendString(result, ")");
550  return result->content;
551  }
552 
553  /* suffix */
554  if (mapContains(expr, "suffix")) {
555  struct element *arg;
556  struct element *string;
557  struct element *length;
558 
559  appendString(result, "suffix(");
560  arg = mapGet(expr, "suffix");
561  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
562  *lose = ISC_TRUE;
563  appendString(result, "???" ")");
564  return result->content;
565  }
566  string = mapGet(arg, "expression");
567  if (string == NULL) {
568  *lose = ISC_TRUE;
569  appendString(result, "???" ")");
570  return result->content;
571  }
572  appendString(result, print_data_expression(string, lose));
573  appendString(result, ", ");
574  length = mapGet(arg, "length");
575  if (length == NULL) {
576  *lose = ISC_TRUE;
577  appendString(result, "???" ")");
578  return result->content;
579  }
580  appendString(result, print_numeric_expression(length, lose));
581  appendString(result, ")");
582  return result->content;
583  }
584 
585  /* lowercase */
586  if (mapContains(expr, "lowercase")) {
587  struct element *arg;
588 
589  appendString(result, "lowercase(");
590  arg = mapGet(expr, "lowercase");
591  if (arg == NULL) {
592  *lose = ISC_TRUE;
593  appendString(result, "???" ")");
594  return result->content;
595  }
596  appendString(result, print_data_expression(arg, lose));
597  appendString(result, ")");
598  return result->content;
599  }
600 
601  /* uppercase */
602  if (mapContains(expr, "uppercase")) {
603  struct element *arg;
604 
605  appendString(result, "uppercase(");
606  arg = mapGet(expr, "uppercase");
607  if (arg == NULL) {
608  *lose = ISC_TRUE;
609  appendString(result, "???" ")");
610  return result->content;
611  }
612  appendString(result, print_data_expression(arg, lose));
613  appendString(result, ")");
614  return result->content;
615  }
616 
617  /* option */
618  if (mapContains(expr, "option")) {
619  struct element *arg;
620  struct element *universe;
621  struct element *name;
622 
623  appendString(result, "option ");
624  arg = mapGet(expr, "option");
625  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
626  *lose = ISC_TRUE;
627  appendString(result, "???");
628  return result->content;
629  }
630  universe = mapGet(arg, "universe");
631  if ((universe == NULL) || (universe->type != ELEMENT_STRING)) {
632  *lose = ISC_TRUE;
633  appendString(result, "???");
634  return result->content;
635  }
637  appendString(result, ".");
638  name = mapGet(arg, "name");
639  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
640  *lose = ISC_TRUE;
641  appendString(result, "???");
642  return result->content;
643  }
644  concatString(result, stringValue(name));
645  return result->content;
646  }
647 
648  /* hardware */
649  if (mapContains(expr, "hardware"))
650  return "hardware";
651 
652  /* hw-type */
653  if (mapContains(expr, "hw-type"))
654  return "hw-type";
655 
656  /* hw-address */
657  if (mapContains(expr, "hw-address"))
658  return "hw-address";
659 
660  /* const-data */
661  if (mapContains(expr, "const-data")) {
662  struct element *arg;
663 
664  arg = mapGet(expr, "const-data");
665  if ((arg == NULL) || (arg->type != ELEMENT_STRING)) {
666  *lose = ISC_TRUE;
667  appendString(result, "???");
668  return result->content;
669  }
670  concatString(result, stringValue(arg));
671  return result->content;
672  }
673 
674  /* packet */
675  if (mapContains(expr, "packet")) {
676  struct element *arg;
677  struct element *offset;
678  struct element *length;
679 
680  appendString(result, "packet(");
681  arg = mapGet(expr, "packet");
682  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
683  *lose = ISC_TRUE;
684  appendString(result, "???" ")");
685  return result->content;
686  }
687  offset = mapGet(arg, "offset");
688  if (offset == NULL) {
689  *lose = ISC_TRUE;
690  appendString(result, "???" ")");
691  return result->content;
692  }
693  appendString(result, print_numeric_expression(offset, lose));
694  appendString(result, ", ");
695  length = mapGet(arg, "length");
696  if (length == NULL) {
697  *lose = ISC_TRUE;
698  appendString(result, "???" ")");
699  return result->content;
700  }
701  appendString(result, print_numeric_expression(length, lose));
702  appendString(result, ")");
703  return result->content;
704  }
705 
706  /* concat */
707  if (mapContains(expr, "concat")) {
708  struct element *arg;
709  struct element *left;
710  struct element *right;
711 
712  appendString(result, "concat(");
713  arg = mapGet(expr, "concat");
714  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
715  *lose = ISC_TRUE;
716  appendString(result, "???" ")");
717  return result->content;
718  }
719  left = mapGet(arg, "left");
720  if (left == NULL) {
721  *lose = ISC_TRUE;
722  appendString(result, "???" ")");
723  return result->content;
724  }
725  appendString(result, print_data_expression(left, lose));
726  appendString(result, ", ");
727  right = mapGet(arg, "right");
728  if (right == NULL) {
729  *lose = ISC_TRUE;
730  appendString(result, "???" ")");
731  return result->content;
732  }
733  appendString(result, print_data_expression(right, lose));
734  appendString(result, ")");
735  return result->content;
736  }
737 
738  /* encapsulate */
739  if (mapContains(expr, "encapsulate")) {
740  struct element *arg;
741 
742  appendString(result, "encapsulate ");
743  arg = mapGet(expr, "encapsulate");
744  if (arg == NULL) {
745  *lose = ISC_TRUE;
746  appendString(result, "???");
747  return result->content;
748  }
749  appendString(result, print_data_expression(arg, lose));
750  return result->content;
751  }
752 
753  /* encode-int8 */
754  if (mapContains(expr, "encode-int8")) {
755  struct element *arg;
756 
757  appendString(result, "encode-int(");
758  arg = mapGet(expr, "encode-int8");
759  if (arg == NULL) {
760  *lose = ISC_TRUE;
761  appendString(result, "???, 8)");
762  return result->content;
763  }
764  appendString(result, print_numeric_expression(arg, lose));
765  appendString(result, ", 8)");
766  return result->content;
767  }
768 
769  /* encode-int16 */
770  if (mapContains(expr, "encode-int16")) {
771  struct element *arg;
772 
773  appendString(result, "encode-int(");
774  arg = mapGet(expr, "encode-int16");
775  if (arg == NULL) {
776  *lose = ISC_TRUE;
777  appendString(result, "???, 16)");
778  return result->content;
779  }
780  appendString(result, print_numeric_expression(arg, lose));
781  appendString(result, ", 16)");
782  return result->content;
783  }
784 
785  /* encode-int32 */
786  if (mapContains(expr, "encode-int32")) {
787  struct element *arg;
788 
789  appendString(result, "encode-int(");
790  arg = mapGet(expr, "encode-int32");
791  if (arg == NULL) {
792  *lose = ISC_TRUE;
793  appendString(result, "???, 32)");
794  return result->content;
795  }
796  appendString(result, print_numeric_expression(arg, lose));
797  appendString(result, ", 32)");
798  return result->content;
799  }
800 
801  /* gethostbyname */
802  if (mapContains(expr, "gethostbyname")) {
803  struct element *arg;
804 
805  appendString(result, "gethostbyname(");
806  arg = mapGet(expr, "gethostbyname");
807  if (arg == NULL) {
808  *lose = ISC_TRUE;
809  appendString(result, "???");
810  return result->content;
811  }
812  appendString(result, print_data_expression(arg, lose));
813  appendString(result, ")");
814  return result->content;
815  }
816 
817  /* binary-to-ascii */
818  if (mapContains(expr, "binary-to-ascii")) {
819  struct element *arg;
820  struct element *base;
821  struct element *width;
822  struct element *separator;
823  struct element *buffer;
824 
825  appendString(result, "binary-to-ascii(");
826  arg = mapGet(expr, "binary-to-ascii");
827  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
828  *lose = ISC_TRUE;
829  appendString(result, "???" ")");
830  return result->content;
831  }
832  base = mapGet(arg, "base");
833  if (base == NULL) {
834  *lose = ISC_TRUE;
835  appendString(result, "???" ")");
836  return result->content;
837  }
838  appendString(result, print_numeric_expression(base, lose));
839  appendString(result, ", ");
840  width = mapGet(arg, "width");
841  if (width == NULL) {
842  *lose = ISC_TRUE;
843  appendString(result, "???" ")");
844  return result->content;
845  }
846  appendString(result, print_numeric_expression(width, lose));
847  appendString(result, ", ");
848  separator = mapGet(arg, "separator");
849  if (separator == NULL) {
850  *lose = ISC_TRUE;
851  appendString(result, "???" ")");
852  return result->content;
853  }
854  appendString(result, print_data_expression(separator, lose));
855  appendString(result, ", ");
856  buffer = mapGet(arg, "buffer");
857  if (buffer == NULL) {
858  *lose = ISC_TRUE;
859  appendString(result, "???" ")");
860  return result->content;
861  }
862  appendString(result, print_data_expression(buffer, lose));
863  appendString(result, ")");
864  return result->content;
865  }
866 
867  /* filename */
868  if (mapContains(expr, "filename"))
869  return "filename";
870 
871  /* server-name */
872  if (mapContains(expr, "server-name"))
873  return "server-name";
874 
875  /* reverse */
876  if (mapContains(expr, "reverse")) {
877  struct element *arg;
878  struct element *width;
879  struct element *buffer;
880 
881  appendString(result, "reverse(");
882  arg = mapGet(expr, "reverse");
883  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
884  *lose = ISC_TRUE;
885  appendString(result, "???" ")");
886  return result->content;
887  }
888  width = mapGet(arg, "width");
889  if (width == NULL) {
890  *lose = ISC_TRUE;
891  appendString(result, "???" ")");
892  return result->content;
893  }
894  appendString(result, print_numeric_expression(width, lose));
895  appendString(result, ", ");
896  buffer = mapGet(arg, "buffer");
897  if (buffer == NULL) {
898  *lose = ISC_TRUE;
899  appendString(result, "???" ")");
900  return result->content;
901  }
902  appendString(result, print_data_expression(buffer, lose));
903  appendString(result, ")");
904  return result->content;
905  }
906 
907  /* pick-first-value */
908  if (mapContains(expr, "pick-first-value")) {
909  struct element *arg;
910  size_t i;
911 
912  appendString(result, "pick-first-value(");
913  arg = mapGet(expr, "pick-first-value");
914  if ((arg == NULL) || (arg->type != ELEMENT_LIST)) {
915  *lose = ISC_TRUE;
916  appendString(result, "???" ")");
917  return result->content;
918  }
919  for (i = 0; i < listSize(arg); i++) {
920  struct element *item;
921 
922  if (i != 0)
923  appendString(result, ", ");
924  item = listGet(arg, i);
925  if (item == NULL) {
926  *lose = ISC_TRUE;
927  appendString(result, "???");
928  continue;
929  }
930  appendString(result,
931  print_data_expression(item, lose));
932  }
933  appendString(result, ")");
934  return result->content;
935  }
936 
937  /* host-decl-name */
938  if (mapContains(expr, "host-decl-name"))
939  return "host-decl-name";
940 
941  /* leased-address */
942  if (mapContains(expr, "leased-address"))
943  return "leased-address";
944 
945  /* config-option */
946  if (mapContains(expr, "config-option")) {
947  struct element *arg;
948  struct element *universe;
949  struct element *name;
950 
951  appendString(result, "config-option ");
952  arg = mapGet(expr, "config-option");
953  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
954  *lose = ISC_TRUE;
955  appendString(result, "???");
956  return result->content;
957  }
958  universe = mapGet(arg, "universe");
959  if ((universe == NULL) || (universe->type != ELEMENT_STRING)) {
960  *lose = ISC_TRUE;
961  appendString(result, "???");
962  return result->content;
963  }
965  appendString(result, ".");
966  name = mapGet(arg, "name");
967  if ((name == NULL) || (name->type != ELEMENT_STRING)) {
968  *lose = ISC_TRUE;
969  appendString(result, "???");
970  return result->content;
971  }
972  concatString(result, stringValue(name));
973  return result->content;
974  }
975 
976  /* null */
977  if (mapContains(expr, "null"))
978  return "null";
979 
980  /* gethostname */
981  if (mapContains(expr, "gethostname"))
982  return "gethostname";
983 
984  /* v6relay */
985  if (mapContains(expr, "v6relay")) {
986  struct element *arg;
987  struct element *relay;
988  struct element *option;
989 
990 
991  appendString(result, "v6relay(");
992  arg = mapGet(expr, "v6relay");
993  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
994  *lose = ISC_TRUE;
995  appendString(result, "???" ")");
996  return result->content;
997  }
998  relay = mapGet(arg, "relay");
999  if (relay == NULL) {
1000  *lose = ISC_TRUE;
1001  appendString(result, "???" ")");
1002  return result->content;
1003  }
1004  appendString(result, print_numeric_expression(relay, lose));
1005  appendString(result, ", ");
1006  option = mapGet(arg, "relay-option");
1007  if (option == NULL) {
1008  *lose = ISC_TRUE;
1009  appendString(result, "???" ")");
1010  return result->content;
1011  }
1012  appendString(result, print_data_expression(option, lose));
1013  appendString(result, ")");
1014  return result->content;
1015  }
1016 
1017  *lose = ISC_TRUE;
1018  appendString(result, "???");
1019  return result->content;
1020 }
1021 
1022 const char *
1024 {
1025  struct string *result;
1026 
1027  if (expr->type == ELEMENT_INTEGER) {
1028  char buf[20];
1029 
1030  snprintf(buf, sizeof(buf), "%lld", (long long)intValue(expr));
1031  result = makeString(-1, buf);
1032  return result->content;
1033  }
1034 
1035  /*
1036  * From is_numeric_expression
1037  */
1038  if (expr->type != ELEMENT_MAP) {
1039  *lose = ISC_TRUE;
1040  return "???";
1041  }
1042  result = allocString();
1043 
1044  /* extract-int8 */
1045  if (mapContains(expr, "extract-int8")) {
1046  struct element *arg;
1047 
1048  appendString(result, "extract-int(");
1049  arg = mapGet(expr, "extract-int8");
1050  if (arg == NULL) {
1051  *lose = ISC_TRUE;
1052  appendString(result, "???, 8)");
1053  return result->content;
1054  }
1055  appendString(result, print_data_expression(arg, lose));
1056  appendString(result, ", 8)");
1057  return result->content;
1058  }
1059 
1060  /* extract-int16 */
1061  if (mapContains(expr, "extract-int16")) {
1062  struct element *arg;
1063 
1064  appendString(result, "extract-int(");
1065  arg = mapGet(expr, "extract-int16");
1066  if (arg == NULL) {
1067  *lose = ISC_TRUE;
1068  appendString(result, "???, 16)");
1069  return result->content;
1070  }
1071  appendString(result, print_data_expression(arg, lose));
1072  appendString(result, ", 16)");
1073  return result->content;
1074  }
1075 
1076  /* extract-int32 */
1077  if (mapContains(expr, "extract-int32")) {
1078  struct element *arg;
1079 
1080  appendString(result, "extract-int(");
1081  arg = mapGet(expr, "extract-int32");
1082  if (arg == NULL) {
1083  *lose = ISC_TRUE;
1084  appendString(result, "???, 32)");
1085  return result->content;
1086  }
1087  appendString(result, print_data_expression(arg, lose));
1088  appendString(result, ", 32)");
1089  return result->content;
1090  }
1091 
1092  /* const-int */
1093  if (mapContains(expr, "const-int")) {
1094  struct element *arg;
1095  char buf[20];
1096 
1097  arg = mapGet(expr, "const-int");
1098  if ((arg == NULL) || (arg->type != ELEMENT_INTEGER)) {
1099  *lose = ISC_TRUE;
1100  appendString(result, "???");
1101  return result->content;
1102  }
1103  snprintf(buf, sizeof(buf), "%lld", (long long)intValue(arg));
1104  result = makeString(-1, buf);
1105  return result->content;
1106  }
1107 
1108  /* lease-time */
1109  if (mapContains(expr, "lease-time"))
1110  return "lease-time";
1111 
1112  /* add */
1113  if (mapContains(expr, "add")) {
1114  struct element *arg;
1115  struct element *left;
1116  struct element *right;
1117  isc_boolean_t add_parenthesis;
1118 
1119  appendString(result, "add ");
1120  arg = mapGet(expr, "add");
1121  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1122  *lose = ISC_TRUE;
1123  appendString(result, "???");
1124  return result->content;
1125  }
1126  left = mapGet(arg, "left");
1127  if (left == NULL) {
1128  *lose = ISC_TRUE;
1129  appendString(result, "???");
1130  return result->content;
1131  }
1132  result = allocString();
1133  add_parenthesis = ISC_TF(expr_precedence(expr_add,
1134  left) < 0);
1135  if (add_parenthesis)
1136  appendString(result, "(");
1137  appendString(result, print_expression(left, lose));
1138  if (add_parenthesis)
1139  appendString(result, ")");
1140  appendString(result, " + ");
1141  right = mapGet(arg, "right");
1142  if (right == NULL) {
1143  *lose = ISC_TRUE;
1144  appendString(result, "???");
1145  return result->content;
1146  }
1147  add_parenthesis = ISC_TF(expr_precedence(expr_add,
1148  right) < 0);
1149  if (add_parenthesis)
1150  appendString(result, "(");
1151  appendString(result, print_expression(right, lose));
1152  if (add_parenthesis)
1153  appendString(result, ")");
1154  return result->content;
1155  }
1156 
1157  /* subtract */
1158  if (mapContains(expr, "subtract")) {
1159  struct element *arg;
1160  struct element *left;
1161  struct element *right;
1162  isc_boolean_t add_parenthesis;
1163 
1164  appendString(result, "subtract ");
1165  arg = mapGet(expr, "subtract");
1166  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1167  *lose = ISC_TRUE;
1168  appendString(result, "???");
1169  return result->content;
1170  }
1171  left = mapGet(arg, "left");
1172  if (left == NULL) {
1173  *lose = ISC_TRUE;
1174  appendString(result, "???");
1175  return result->content;
1176  }
1177  result = allocString();
1178  add_parenthesis = ISC_TF(expr_precedence(expr_subtract,
1179  left) < 0);
1180  if (add_parenthesis)
1181  appendString(result, "(");
1182  appendString(result, print_expression(left, lose));
1183  if (add_parenthesis)
1184  appendString(result, ")");
1185  appendString(result, " - ");
1186  right = mapGet(arg, "right");
1187  if (right == NULL) {
1188  *lose = ISC_TRUE;
1189  appendString(result, "???");
1190  return result->content;
1191  }
1192  add_parenthesis = ISC_TF(expr_precedence(expr_subtract,
1193  right) < 0);
1194  if (add_parenthesis)
1195  appendString(result, "(");
1196  appendString(result, print_expression(right, lose));
1197  if (add_parenthesis)
1198  appendString(result, ")");
1199  return result->content;
1200  }
1201 
1202  /* multiply */
1203  if (mapContains(expr, "multiply")) {
1204  struct element *arg;
1205  struct element *left;
1206  struct element *right;
1207  isc_boolean_t add_parenthesis;
1208 
1209  appendString(result, "multiply ");
1210  arg = mapGet(expr, "multiply");
1211  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1212  *lose = ISC_TRUE;
1213  appendString(result, "???");
1214  return result->content;
1215  }
1216  left = mapGet(arg, "left");
1217  if (left == NULL) {
1218  *lose = ISC_TRUE;
1219  appendString(result, "???");
1220  return result->content;
1221  }
1222  result = allocString();
1223  add_parenthesis = ISC_TF(expr_precedence(expr_multiply,
1224  left) < 0);
1225  if (add_parenthesis)
1226  appendString(result, "(");
1227  appendString(result, print_expression(left, lose));
1228  if (add_parenthesis)
1229  appendString(result, ")");
1230  appendString(result, " * ");
1231  right = mapGet(arg, "right");
1232  if (right == NULL) {
1233  *lose = ISC_TRUE;
1234  appendString(result, "???");
1235  return result->content;
1236  }
1237  add_parenthesis = ISC_TF(expr_precedence(expr_multiply,
1238  right) < 0);
1239  if (add_parenthesis)
1240  appendString(result, "(");
1241  appendString(result, print_expression(right, lose));
1242  if (add_parenthesis)
1243  appendString(result, ")");
1244  return result->content;
1245  }
1246 
1247  /* divide */
1248  if (mapContains(expr, "divide")) {
1249  struct element *arg;
1250  struct element *left;
1251  struct element *right;
1252  isc_boolean_t add_parenthesis;
1253 
1254  appendString(result, "divide ");
1255  arg = mapGet(expr, "divide");
1256  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1257  *lose = ISC_TRUE;
1258  appendString(result, "???");
1259  return result->content;
1260  }
1261  left = mapGet(arg, "left");
1262  if (left == NULL) {
1263  *lose = ISC_TRUE;
1264  appendString(result, "???");
1265  return result->content;
1266  }
1267  result = allocString();
1268  add_parenthesis = ISC_TF(expr_precedence(expr_divide,
1269  left) < 0);
1270  if (add_parenthesis)
1271  appendString(result, "(");
1272  appendString(result, print_expression(left, lose));
1273  if (add_parenthesis)
1274  appendString(result, ")");
1275  appendString(result, " / ");
1276  right = mapGet(arg, "right");
1277  if (right == NULL) {
1278  *lose = ISC_TRUE;
1279  appendString(result, "???");
1280  return result->content;
1281  }
1282  add_parenthesis = ISC_TF(expr_precedence(expr_divide,
1283  right) < 0);
1284  if (add_parenthesis)
1285  appendString(result, "(");
1286  appendString(result, print_expression(right, lose));
1287  if (add_parenthesis)
1288  appendString(result, ")");
1289  return result->content;
1290  }
1291 
1292  /* remainder */
1293  if (mapContains(expr, "remainder")) {
1294  struct element *arg;
1295  struct element *left;
1296  struct element *right;
1297  isc_boolean_t add_parenthesis;
1298 
1299  appendString(result, "remainder ");
1300  arg = mapGet(expr, "remainder");
1301  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1302  *lose = ISC_TRUE;
1303  appendString(result, "???");
1304  return result->content;
1305  }
1306  left = mapGet(arg, "left");
1307  if (left == NULL) {
1308  *lose = ISC_TRUE;
1309  appendString(result, "???");
1310  return result->content;
1311  }
1312  result = allocString();
1313  add_parenthesis = ISC_TF(expr_precedence(expr_remainder,
1314  left) < 0);
1315  if (add_parenthesis)
1316  appendString(result, "(");
1317  appendString(result, print_expression(left, lose));
1318  if (add_parenthesis)
1319  appendString(result, ")");
1320  appendString(result, " % ");
1321  right = mapGet(arg, "right");
1322  if (right == NULL) {
1323  *lose = ISC_TRUE;
1324  appendString(result, "???");
1325  return result->content;
1326  }
1327  add_parenthesis = ISC_TF(expr_precedence(expr_remainder,
1328  right) < 0);
1329  if (add_parenthesis)
1330  appendString(result, "(");
1331  appendString(result, print_expression(right, lose));
1332  if (add_parenthesis)
1333  appendString(result, ")");
1334  return result->content;
1335  }
1336 
1337  /* binary-and */
1338  if (mapContains(expr, "binary-and")) {
1339  struct element *arg;
1340  struct element *left;
1341  struct element *right;
1342  isc_boolean_t add_parenthesis;
1343 
1344  appendString(result, "binary-and ");
1345  arg = mapGet(expr, "binary-and");
1346  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1347  *lose = ISC_TRUE;
1348  appendString(result, "???");
1349  return result->content;
1350  }
1351  left = mapGet(arg, "left");
1352  if (left == NULL) {
1353  *lose = ISC_TRUE;
1354  appendString(result, "???");
1355  return result->content;
1356  }
1357  result = allocString();
1358  add_parenthesis = ISC_TF(expr_precedence(expr_binary_and,
1359  left) < 0);
1360  if (add_parenthesis)
1361  appendString(result, "(");
1362  appendString(result, print_expression(left, lose));
1363  if (add_parenthesis)
1364  appendString(result, ")");
1365  appendString(result, " & ");
1366  right = mapGet(arg, "right");
1367  if (right == NULL) {
1368  *lose = ISC_TRUE;
1369  appendString(result, "???");
1370  return result->content;
1371  }
1372  add_parenthesis = ISC_TF(expr_precedence(expr_binary_and,
1373  right) < 0);
1374  if (add_parenthesis)
1375  appendString(result, "(");
1376  appendString(result, print_expression(right, lose));
1377  if (add_parenthesis)
1378  appendString(result, ")");
1379  return result->content;
1380  }
1381 
1382  /* binary-or */
1383  if (mapContains(expr, "binary-or")) {
1384  struct element *arg;
1385  struct element *left;
1386  struct element *right;
1387  isc_boolean_t add_parenthesis;
1388 
1389  appendString(result, "binary-or ");
1390  arg = mapGet(expr, "binary-or");
1391  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1392  *lose = ISC_TRUE;
1393  appendString(result, "???");
1394  return result->content;
1395  }
1396  left = mapGet(arg, "left");
1397  if (left == NULL) {
1398  *lose = ISC_TRUE;
1399  appendString(result, "???");
1400  return result->content;
1401  }
1402  result = allocString();
1403  add_parenthesis = ISC_TF(expr_precedence(expr_binary_or,
1404  left) < 0);
1405  if (add_parenthesis)
1406  appendString(result, "(");
1407  appendString(result, print_expression(left, lose));
1408  if (add_parenthesis)
1409  appendString(result, ")");
1410  appendString(result, " | ");
1411  right = mapGet(arg, "right");
1412  if (right == NULL) {
1413  *lose = ISC_TRUE;
1414  appendString(result, "???");
1415  return result->content;
1416  }
1417  add_parenthesis = ISC_TF(expr_precedence(expr_binary_or,
1418  right) < 0);
1419  if (add_parenthesis)
1420  appendString(result, "(");
1421  appendString(result, print_expression(right, lose));
1422  if (add_parenthesis)
1423  appendString(result, ")");
1424  return result->content;
1425  }
1426 
1427  /* binary-xor */
1428  if (mapContains(expr, "binary-xor")) {
1429  struct element *arg;
1430  struct element *left;
1431  struct element *right;
1432  isc_boolean_t add_parenthesis;
1433 
1434  appendString(result, "binary-xor ");
1435  arg = mapGet(expr, "binary-xor");
1436  if ((arg == NULL) || (arg->type != ELEMENT_MAP)) {
1437  *lose = ISC_TRUE;
1438  appendString(result, "???");
1439  return result->content;
1440  }
1441  left = mapGet(arg, "left");
1442  if (left == NULL) {
1443  *lose = ISC_TRUE;
1444  appendString(result, "???");
1445  return result->content;
1446  }
1447  result = allocString();
1448  add_parenthesis = ISC_TF(expr_precedence(expr_binary_xor,
1449  left) < 0);
1450  if (add_parenthesis)
1451  appendString(result, "(");
1452  appendString(result, print_expression(left, lose));
1453  if (add_parenthesis)
1454  appendString(result, ")");
1455  appendString(result, " ^ ");
1456  right = mapGet(arg, "right");
1457  if (right == NULL) {
1458  *lose = ISC_TRUE;
1459  appendString(result, "???");
1460  return result->content;
1461  }
1462  add_parenthesis = ISC_TF(expr_precedence(expr_binary_xor,
1463  right) < 0);
1464  if (add_parenthesis)
1465  appendString(result, "(");
1466  appendString(result, print_expression(right, lose));
1467  if (add_parenthesis)
1468  appendString(result, ")");
1469  return result->content;
1470  }
1471 
1472  /* client-state */
1473  if (mapContains(expr, "client-state"))
1474  return "client-state";
1475 
1476  *lose = ISC_TRUE;
1477  appendString(result, "???");
1478  return result->content;
1479 }
1480 
1481 static void
1482 debug(const char* fmt, ...)
1483 {
1484  va_list list;
1485 
1486  va_start(list, fmt);
1487  vfprintf(stderr, fmt, list);
1488  fprintf(stderr, "\n");
1489  va_end(list);
1490 }
void print_expression(char *name, struct expression *expr) const
Definition: print.c:1171
struct string * quote(struct string *s)
Definition: data.c:356
void concatString(struct string *s, const struct string *a)
Definition: data.c:330
struct string * makeString(int l, const char *s)
Definition: data.c:44
isc_boolean_t boolValue(const struct element *e)
Definition: data.c:399
struct element * mapGet(struct element *m, const char *k)
Definition: data.c:759
struct string * stringValue(struct element *e)
Definition: data.c:408
void appendString(struct string *s, const char *a)
Definition: data.c:311
isc_boolean_t mapContains(const struct element *m, const char *k)
Definition: data.c:811
struct string * allocString(void)
Definition: data.c:32
struct element * listGet(struct element *l, int i)
Definition: data.c:646
size_t listSize(const struct element *l)
Definition: data.c:730
int64_t intValue(const struct element *e)
Definition: data.c:383
#define ELEMENT_INTEGER
Definition: data.h:162
#define ELEMENT_LIST
Definition: data.h:167
isc_boolean_t
Definition: data.h:150
#define ELEMENT_STRING
Definition: data.h:166
#define ISC_TF(x)
Definition: data.h:154
#define ELEMENT_BOOLEAN
Definition: data.h:164
#define ISC_TRUE
Definition: data.h:153
#define ELEMENT_MAP
Definition: data.h:168
const char * print_numeric_expression(struct element *expr, isc_boolean_t *lose)
Definition: print.c:1023
const char * print_data_expression(struct element *expr, isc_boolean_t *lose)
Definition: print.c:496
const char * print_boolean_expression(struct element *expr, isc_boolean_t *lose)
Definition: print.c:59
int expr_precedence(enum expr_op, struct element *)
Definition: parse.c:6135
Definition: tree.h:60
Definition: data.h:216
int type
Definition: data.h:217
Definition: tree.h:345
Definition: data.h:171
char * content
Definition: data.h:173
Definition: tree.h:301
int is_boolean_expression(struct expression *expr)
Definition: tree.c:3031
int is_numeric_expression(struct expression *expr)
Definition: tree.c:3078
int is_data_expression(struct expression *expr)
Definition: tree.c:3048
@ expr_binary_and
Definition: tree.h:184
@ expr_regex_match
Definition: tree.h:190
@ expr_equal
Definition: tree.h:135
@ expr_binary_or
Definition: tree.h:185
@ expr_remainder
Definition: tree.h:183
@ expr_not
Definition: tree.h:142
@ expr_add
Definition: tree.h:179
@ expr_divide
Definition: tree.h:182
@ expr_or
Definition: tree.h:141
@ expr_and
Definition: tree.h:140
@ expr_iregex_match
Definition: tree.h:191
@ expr_multiply
Definition: tree.h:181
@ expr_subtract
Definition: tree.h:180
@ expr_binary_xor
Definition: tree.h:186
@ expr_not_equal
Definition: tree.h:170