]> git.ipfire.org Git - thirdparty/bird.git/commitdiff
Filter: Better syntax for function return types
authorOndrej Zajicek <santiago@crfreenet.org>
Tue, 4 Jul 2023 17:07:30 +0000 (19:07 +0200)
committerOndrej Zajicek <santiago@crfreenet.org>
Tue, 12 Sep 2023 14:31:52 +0000 (16:31 +0200)
The C-style syntax does not really fit into rest of our syntax.

conf/cf-lex.l
conf/confbase.Y
doc/bird.sgml
filter/config.Y
filter/f-inst.c
filter/test.conf

index dcd54b8134e55c8b1f8a655842deab36c67c73a2..cee0e63e90afa7b577c540cf2d474b4778522fb5 100644 (file)
@@ -380,6 +380,7 @@ else: {
 \>\= return GEQ;
 \&\& return AND;
 \|\| return OR;
+\-\> return IMP;
 
 \[\= return PO;
 \=\] return PC;
index 2efeb29f9b7e6daae06a2868b1130bbfaf68602c..7b368fc6d82cb20fd7aefd708a9642455c2265d6 100644 (file)
@@ -98,7 +98,7 @@ CF_DECLS
 }
 
 %token END CLI_MARKER INVALID_TOKEN ELSECOL DDOT
-%token GEQ LEQ NEQ AND OR
+%token GEQ LEQ NEQ AND OR IMP
 %token PO PC
 %token <i> NUM ENUM
 %token <ip4> IP4
@@ -125,7 +125,7 @@ CF_DECLS
 
 %nonassoc PREFIX_DUMMY
 %left AND OR
-%nonassoc '=' '<' '>' '~' GEQ LEQ NEQ NMA PO PC
+%nonassoc '=' '<' '>' '~' GEQ LEQ NEQ NMA IMP PO PC
 %left '+' '-'
 %left '*' '/' '%'
 %left '!'
index 3fcf0025d03e3ed8f05d9132a63df5708ef694bf..3be266cbf3516f139af6932a52d9e30d99da3efd 100644 (file)
@@ -539,7 +539,7 @@ include "tablename.conf";;
        Define a filter. You can learn more about filters in the following
        chapter.
 
-       <tag><label id="opt-function">function <m/type/ <m/name/ (<m/parameters/) <m/local variables/ { <m/commands/ }</tag>
+       <tag><label id="opt-function">function <m/name/ (<m/parameters/) [ -&gt; <m/return type/ ] <m/local variables/ { <m/commands/ }</tag>
        Define a function. You can learn more about functions in the following chapter.
 
        <tag><label id="opt-protocol">protocol rip|ospf|bgp|<m/.../ [<m/name/ [from <m/name2/]] { <m>protocol options</m> }</tag>
@@ -1294,21 +1294,21 @@ can group several statements to a single compound statement by using braces
 (<cf>{ <M>statements</M> }</cf>) which is useful if you want to make a bigger
 block of code conditional.
 
-<p>BIRD supports functions, so that you don't have to repeat the same blocks of
-code over and over. Functions can have zero or more parameters and they can have
-local variables. You should always specify the function return type and always
-return it. No-return functions and multiple-type returning functions are deprecated.
-Direct recursion is possible. Function definitions look like this:
+<p>BIRD supports functions, so that you don not have to repeat the same blocks
+of code over and over. Functions can have zero or more parameters and they can
+have local variables. If the function returns value, then you should always
+specify its return type. Direct recursion is possible. Function definitions look
+like this:
 
 <code>
-function int name ()
+function name() -> int
 {
        int local_variable;
        int another_variable = 5;
        return 42;
 }
 
-function pair with_parameters (int parameter)
+function with_parameters(int parameter) -> pair
 {
        print parameter;
        return (1, 2);
index 7cc6f88235a8d64c4a49ccd52e6fc61521fa727c..f856924c1445211bad196a537e22f0813afa6f63 100644 (file)
@@ -380,7 +380,7 @@ CF_KEYWORDS(FUNCTION, PRINT, PRINTN, UNSET, RETURN,
 %type <f> filter where_filter
 %type <fl> filter_body function_body
 %type <flv> lvalue
-%type <i> type maybe_type function_vars
+%type <i> type function_vars function_type
 %type <fa> function_argsn function_args
 %type <ecs> ec_kind
 %type <fret> break_command
@@ -513,6 +513,11 @@ function_vars:
    }
  ;
 
+function_type:
+   /* EMPTY */ { $$ = T_VOID; }
+ | IMP type { $$ = $2; }
+ ;
+
 filter_body: function_body ;
 
 filter:
@@ -547,28 +552,23 @@ function_body:
  ;
 
 conf: function_def ;
-maybe_type:
-   /* EMPTY */ { $$ = T_VOID; }
- | type { $$ = $1; }
- ;
 
 function_def:
-   FUNCTION maybe_type symbol {
-     DBG( "Beginning of function %s\n", $3->name );
-     this_function = cf_define_symbol(new_config, $3, SYM_FUNCTION, function, NULL);
-/*   if ($2 == T_VOID) cf_warn("Support for functions without explicit return type will be removed soon" ); */
+   FUNCTION symbol {
+     DBG( "Beginning of function %s\n", $2->name );
+     this_function = cf_define_symbol(new_config, $2, SYM_FUNCTION, function, NULL);
      cf_push_scope(new_config, this_function);
-   } function_args {
+   } function_args function_type {
      /* Make dummy f_line for storing function prototype */
      struct f_line *dummy = cfg_allocz(sizeof(struct f_line));
      this_function->function = dummy;
 
-     dummy->return_type = $2;
+     dummy->return_type = $5;
 
      /* Revert the args */
-     while ($5) {
-       struct f_arg *tmp = $5;
-       $5 = $5->next;
+     while ($4) {
+       struct f_arg *tmp = $4;
+       $4 = $4->next;
 
        tmp->next = dummy->arg_list;
        dummy->arg_list = tmp;
@@ -578,7 +578,7 @@ function_def:
      $7->args = this_function->function->args;
      $7->arg_list = this_function->function->arg_list;
      $7->return_type = this_function->function->return_type;
-     $3->function = $7;
+     $2->function = $7;
      cf_pop_scope(new_config);
    }
  ;
index a9de0960f2916b3c8e6218182607488d28f09dd5..be22acccb9fadd9d4da4a6f919a8b7aad3832216 100644 (file)
     NEVER_CONSTANT;
     VARARG;
     SYMBOL;
-
-    /* Fake result type declaration */
     RESULT_TYPE(sym->function->return_type);
 
     FID_NEW_BODY()
index 90f5e694957554579f33a9c1c5ccea58889b6dab..62993898a58b383dbef4edbbafb2bc869490fbd9 100644 (file)
@@ -21,17 +21,17 @@ attribute lclist mylclist;
 define one = 1;
 define ten = 10;
 
-function int onef(int a)
+function onef(int a) -> int
 {
        return 1;
 }
 
-function int twof(int a)
+function twof(int a) -> int
 {
        return 2;
 }
 
-function int oneg(int a)
+function oneg(int a) -> int
 {
        return 1;
 }
@@ -274,7 +274,7 @@ bt_test_suite(t_bytestring, "Testing bytestrings");
  *     -------------
  */
 
-function pair 'mkpair-a'(int a)
+function 'mkpair-a'(int a) -> pair
 {
        return (1, a);
 }
@@ -749,7 +749,7 @@ bt_test_suite(t_flowspec, "Testing flowspec routes");
  *     -------------
  */
 
-function bgpmask mkpath(int a; int b)
+function mkpath(int a; int b) -> bgpmask
 {
        return [= a b 3 2 1 =];
 }
@@ -1432,7 +1432,7 @@ bt_test_suite(t_ec_set, "Testing sets of extended communities");
  *     -------------------------
  */
 
-function lc mktrip(int a)
+function mktrip(int a) -> lc
 {
        return (a, 2*a, 3*a);
 }
@@ -1747,7 +1747,7 @@ bt_test_suite(t_define, "Testing defined() function");
  *      -------------------------
  */
 
-function int callme(int arg1; int arg2)
+function callme(int arg1; int arg2) -> int
 int i;
 {
        case arg1 {
@@ -1758,12 +1758,12 @@ int i;
        return 0;
 }
 
-function int callmeagain(int a; int b; int c)
+function callmeagain(int a; int b; int c) -> int
 {
        return a + b + c;
 }
 
-function int fifteen()
+function fifteen() -> int
 {
        return 15;
 }
@@ -1796,28 +1796,28 @@ function local_vars(int j)
        bt_assert(j = 35 && k = 20 && m = 100);
 }
 
-function int factorial(int x)
+function factorial(int x) -> int
 {
        if x = 0 then return 0;
        if x = 1 then return 1;
        else return x * factorial(x - 1);
 }
 
-function int fibonacci(int x)
+function fibonacci(int x) -> int
 {
        if x = 0 then return 0;
        if x = 1 then return 1;
        else return fibonacci(x - 1) + fibonacci(x - 2);
 }
 
-function bgppath hanoi_init(int a; int b)
+function hanoi_init(int a; int b) -> bgppath
 {
        if b = 0
        then return +empty+;
        else return prepend(hanoi_init(a + 1, b - 1), a);
 }
 
-function bgppath hanoi_solve(int n; bgppath h_src; bgppath h_dst; bgppath h_aux; bool x; bool y)
+function hanoi_solve(int n; bgppath h_src; bgppath h_dst; bgppath h_aux; bool x; bool y) -> bgppath
 {
        # x -> return src or dst
        # y -> print state