Since parsing of arphrd_type happens via sym_tbl, there is no dedicated
parser function to perform the check in. So instead make use of maxval
in expr_ctx to reject the value.

While being at it, introduce a switch() to check for meta.key value in a
single place.

Signed-off-by: Phil Sutter <p...@nwl.cc>
---
 src/evaluate.c | 24 ++++++++++++++++++------
 1 file changed, 18 insertions(+), 6 deletions(-)

diff --git a/src/evaluate.c b/src/evaluate.c
index 55cd9d00d274c..ff52aefc669e0 100644
--- a/src/evaluate.c
+++ b/src/evaluate.c
@@ -23,6 +23,7 @@
 #include <netinet/icmp6.h>
 #include <net/ethernet.h>
 #include <net/if.h>
+#include <net/if_arp.h>
 #include <errno.h>
 
 #include <expression.h>
@@ -1795,14 +1796,25 @@ static int expr_evaluate_fib(struct eval_ctx *ctx, 
struct expr **exprp)
 static int expr_evaluate_meta(struct eval_ctx *ctx, struct expr **exprp)
 {
        struct expr *meta = *exprp;
+       unsigned int maxval = 0;
 
-       if (ctx->pctx.family != NFPROTO_INET &&
-           meta->flags & EXPR_F_PROTOCOL &&
-           meta->meta.key == NFT_META_NFPROTO)
+       switch (meta->meta.key) {
+       case NFT_META_NFPROTO:
+               if (ctx->pctx.family == NFPROTO_INET ||
+                   !(meta->flags & EXPR_F_PROTOCOL))
+                       break;
                return expr_error(ctx->msgs, meta,
-                                         "meta nfproto is only useful in the 
inet family");
-
-       return expr_evaluate_primary(ctx, exprp);
+                                 "meta nfproto is only useful in the inet 
family");
+       case NFT_META_IIFTYPE:
+       case NFT_META_OIFTYPE:
+               maxval = ARPHRD_VOID - 1;
+               break;
+       default:
+               break;
+       }
+       __expr_set_context(&ctx->ectx, (*exprp)->dtype, (*exprp)->byteorder,
+                          (*exprp)->len, maxval);
+       return 0;
 }
 
 static int expr_evaluate_socket(struct eval_ctx *ctx, struct expr **expr)
-- 
2.22.0

Reply via email to