diff options
author | Phil Sutter <phil@nwl.cc> | 2024-03-20 15:54:54 +0100 |
---|---|---|
committer | Phil Sutter <phil@nwl.cc> | 2024-04-12 14:33:14 +0200 |
commit | 0ac39384fd9e48ff6bcc5605df2cbeb33af64b9e (patch) | |
tree | 1009847e954207c82d829d1c357712723d0cb789 /src/json.c | |
parent | 3bccc478d27498f7ecc8a0233176accb1b91f584 (diff) |
json: Accept more than two operands in binary expressions
The most common use case is ORing flags like
| syn | ack | rst
but nft seems to be fine with less intuitive stuff like
| meta mark set ip dscp << 2 << 3
so support all of them.
Signed-off-by: Phil Sutter <phil@nwl.cc>
Diffstat (limited to 'src/json.c')
-rw-r--r-- | src/json.c | 19 |
1 files changed, 16 insertions, 3 deletions
@@ -540,11 +540,24 @@ json_t *flagcmp_expr_json(const struct expr *expr, struct output_ctx *octx) "right", expr_print_json(expr->flagcmp.value, octx)); } +static json_t * +__binop_expr_json(int op, const struct expr *expr, struct output_ctx *octx) +{ + json_t *a = json_array(); + + if (expr->etype == EXPR_BINOP && expr->op == op) { + json_array_extend(a, __binop_expr_json(op, expr->left, octx)); + json_array_extend(a, __binop_expr_json(op, expr->right, octx)); + } else { + json_array_append_new(a, expr_print_json(expr, octx)); + } + return a; +} + json_t *binop_expr_json(const struct expr *expr, struct output_ctx *octx) { - return json_pack("{s:[o, o]}", expr_op_symbols[expr->op], - expr_print_json(expr->left, octx), - expr_print_json(expr->right, octx)); + return json_pack("{s:o}", expr_op_symbols[expr->op], + __binop_expr_json(expr->op, expr, octx)); } json_t *relational_expr_json(const struct expr *expr, struct output_ctx *octx) |