From eaccce1b85efafbea1607ff88d7259541f311ee2 Mon Sep 17 00:00:00 2001 From: Andrea Claudi Date: Wed, 5 Jun 2019 13:10:31 +0200 Subject: [PATCH] tc/actions: introduce support for goto chain action Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=1714660 Upstream Status: iproute2.git commit d19f72f7898a7 commit d19f72f7898a78ef76628833c204afb96f9a05cd Author: Jiri Pirko Date: Tue May 16 19:29:37 2017 +0200 tc/actions: introduce support for goto chain action Allow user to set control action "goto" with filter chain index as a parameter. Signed-off-by: Jiri Pirko --- man/man8/tc-ife.8 | 2 +- man/man8/tc-pedit.8 | 2 +- man/man8/tc-police.8 | 2 +- man/man8/tc-vlan.8 | 2 +- tc/m_connmark.c | 3 ++- tc/m_gact.c | 6 ++++-- tc/m_pedit.c | 3 ++- tc/m_police.c | 6 ++++-- tc/m_skbmod.c | 3 ++- tc/m_vlan.c | 3 ++- tc/tc_util.c | 24 +++++++++++++++++++++++- 11 files changed, 43 insertions(+), 13 deletions(-) diff --git a/man/man8/tc-ife.8 b/man/man8/tc-ife.8 index a8f1f287d1502..24595cc6d615c 100644 --- a/man/man8/tc-ife.8 +++ b/man/man8/tc-ife.8 @@ -34,7 +34,7 @@ IFE - encapsulate/decapsulate metadata .ti -8 .IR CONTROL " := { " -.BR reclassify " | " use " | " pipe " | " drop " | " continue " | " ok " }" +.BR reclassify " | " use " | " pipe " | " drop " | " continue " | " ok " | " goto " " chain " " CHAIN_INDEX " }" .SH DESCRIPTION The .B ife diff --git a/man/man8/tc-pedit.8 b/man/man8/tc-pedit.8 index 82d4217bc9589..bbd725c4d0ba1 100644 --- a/man/man8/tc-pedit.8 +++ b/man/man8/tc-pedit.8 @@ -82,7 +82,7 @@ pedit - generic packet editor action .ti -8 .IR CONTROL " := {" -.BR reclassify " | " pipe " | " drop " | " shot " | " continue " | " pass " }" +.BR reclassify " | " pipe " | " drop " | " shot " | " continue " | " pass " | " goto " " chain " " CHAIN_INDEX " }" .SH DESCRIPTION The .B pedit diff --git a/man/man8/tc-police.8 b/man/man8/tc-police.8 index 620c28813fc7e..bcc5f438825d1 100644 --- a/man/man8/tc-police.8 +++ b/man/man8/tc-police.8 @@ -30,7 +30,7 @@ police - policing action .ti -8 .IR EXCEEDACT/NOTEXCEEDACT " := { " -.BR pipe " | " ok " | " reclassify " | " drop " | " continue " }" +.BR pipe " | " ok " | " reclassify " | " drop " | " continue " | " goto " " chain " " CHAIN_INDEX " }" .SH DESCRIPTION The .B police diff --git a/man/man8/tc-vlan.8 b/man/man8/tc-vlan.8 index a526f66b60b4c..f5ffc25f054ed 100644 --- a/man/man8/tc-vlan.8 +++ b/man/man8/tc-vlan.8 @@ -26,7 +26,7 @@ vlan - vlan manipulation module .ti -8 .IR CONTROL " := { " -.BR reclassify " | " pipe " | " drop " | " continue " | " pass " }" +.BR reclassify " | " pipe " | " drop " | " continue " | " pass " | " goto " " chain " " CHAIN_INDEX " }" .SH DESCRIPTION The .B vlan diff --git a/tc/m_connmark.c b/tc/m_connmark.c index 3c2274bc0d2af..37d7185415490 100644 --- a/tc/m_connmark.c +++ b/tc/m_connmark.c @@ -30,7 +30,8 @@ explain(void) fprintf(stderr, "Usage: ... connmark [zone ZONE] [CONTROL] [index ]\n"); fprintf(stderr, "where :\n" "\tZONE is the conntrack zone\n" - "\tCONTROL := reclassify|pipe|drop|continue|ok\n"); + "\tCONTROL := reclassify | pipe | drop | continue | ok |\n" + "\t goto chain \n"); } static void diff --git a/tc/m_gact.c b/tc/m_gact.c index bc3860bbe4441..c04c00bbded3c 100644 --- a/tc/m_gact.c +++ b/tc/m_gact.c @@ -45,7 +45,8 @@ explain(void) #ifdef CONFIG_GACT_PROB fprintf(stderr, "Usage: ... gact [RAND] [INDEX]\n"); fprintf(stderr, - "Where: \tACTION := reclassify | drop | continue | pass | pipe\n" + "Where: \tACTION := reclassify | drop | continue | pass | pipe |\n" + " \t goto chain \n" "\tRAND := random \n" "\tRANDTYPE := netrand | determ\n" "\tVAL : = value not exceeding 10000\n" @@ -54,7 +55,8 @@ explain(void) #else fprintf(stderr, "Usage: ... gact [INDEX]\n"); fprintf(stderr, - "Where: \tACTION := reclassify | drop | continue | pass | pipe\n" + "Where: \tACTION := reclassify | drop | continue | pass | pipe |\n" + " \t goto chain \n" "\tINDEX := index value used\n" "\n"); #endif diff --git a/tc/m_pedit.c b/tc/m_pedit.c index b7d26b4540beb..5d89ab1d832ab 100644 --- a/tc/m_pedit.c +++ b/tc/m_pedit.c @@ -45,7 +45,8 @@ static void explain(void) "\t\tCMD:= clear | invert | set | add | retain\n" "\t:= ip | ip6 \n" " \t\t| udp | tcp | icmp \n" - "\tCONTROL:= reclassify | pipe | drop | continue | pass\n" + "\tCONTROL:= reclassify | pipe | drop | continue | pass |\n" + "\t goto chain \n" "\tNOTE: if 'ex' is set, extended functionality will be supported (kernel >= 4.11)\n" "For Example usage look at the examples directory\n"); diff --git a/tc/m_police.c b/tc/m_police.c index 2b73969de5daf..86117db0482ec 100644 --- a/tc/m_police.c +++ b/tc/m_police.c @@ -41,7 +41,8 @@ static void usage(void) fprintf(stderr, "Where: CONTROL := conform-exceed [/NOTEXCEEDACT]\n"); fprintf(stderr, " Define how to handle packets which exceed ()\n"); fprintf(stderr, " or conform () the configured bandwidth limit.\n"); - fprintf(stderr, " EXCEEDACT/NOTEXCEEDACT := { pipe | ok | reclassify | drop | continue }\n"); + fprintf(stderr, " EXCEEDACT/NOTEXCEEDACT := { pipe | ok | reclassify | drop | continue |\n"); + fprintf(stderr, " goto chain }\n"); exit(-1); } @@ -150,7 +151,8 @@ int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p, matches(*argv, "shot") == 0 || matches(*argv, "continue") == 0 || matches(*argv, "pass") == 0 || - matches(*argv, "pipe") == 0) { + matches(*argv, "pipe") == 0 || + matches(*argv, "goto") == 0) { if (parse_action_control(&argc, &argv, &p.action, false)) return -1; } else if (strcmp(*argv, "conform-exceed") == 0) { diff --git a/tc/m_skbmod.c b/tc/m_skbmod.c index 1ccd474309348..ba79308ba8354 100644 --- a/tc/m_skbmod.c +++ b/tc/m_skbmod.c @@ -36,7 +36,8 @@ static void skbmod_explain(void) "\tDMAC := 6 byte Destination MAC address\n" "\tSMAC := optional 6 byte Source MAC address\n" "\tETYPE := optional 16 bit ethertype\n" - "\tCONTROL := reclassify|pipe|drop|continue|ok\n" + "\tCONTROL := reclassify | pipe | drop | continue | ok |\n" + "\t goto chain \n" "\tINDEX := skbmod index value to use\n"); } diff --git a/tc/m_vlan.c b/tc/m_vlan.c index 2441b06847ecd..cccb4996b05f3 100644 --- a/tc/m_vlan.c +++ b/tc/m_vlan.c @@ -32,7 +32,8 @@ static void explain(void) fprintf(stderr, " vlan modify [ protocol VLANPROTO ] id VLANID [ priority VLANPRIO ] [CONTROL]\n"); fprintf(stderr, " VLANPROTO is one of 802.1Q or 802.1AD\n"); fprintf(stderr, " with default: 802.1Q\n"); - fprintf(stderr, " CONTROL := reclassify | pipe | drop | continue | pass\n"); + fprintf(stderr, " CONTROL := reclassify | pipe | drop | continue | pass |\n"); + fprintf(stderr, " goto chain \n"); } static void usage(void) diff --git a/tc/tc_util.c b/tc/tc_util.c index 840222832690b..194185a0fa1d8 100644 --- a/tc/tc_util.c +++ b/tc/tc_util.c @@ -415,6 +415,8 @@ static const char *action_n2a(int action) { static char buf[64]; + if (TC_ACT_EXT_CMP(action, TC_ACT_GOTO_CHAIN)) + return "goto"; switch (action) { case TC_ACT_UNSPEC: return "continue"; @@ -458,6 +460,7 @@ static int action_a2n(char *arg, int *result, bool allow_num) {"ok", TC_ACT_OK}, {"reclassify", TC_ACT_RECLASSIFY}, {"pipe", TC_ACT_PIPE}, + {"goto", TC_ACT_GOTO_CHAIN}, { NULL }, }, *iter; @@ -497,6 +500,22 @@ int parse_action_control(int *argc_p, char ***argv_p, fprintf(stderr, "Bad action type %s\n", *argv); return -1; } + if (result == TC_ACT_GOTO_CHAIN) { + __u32 chain_index; + + NEXT_ARG(); + if (matches(*argv, "chain") != 0) { + fprintf(stderr, "\"chain index\" expected\n"); + return -1; + } + NEXT_ARG(); + if (get_u32(&chain_index, *argv, 10) || + chain_index > TC_ACT_EXT_VAL_MASK) { + fprintf(stderr, "Illegal \"chain index\"\n"); + return -1; + } + result |= chain_index; + } NEXT_ARG_FWD(); *argc_p = argc; *argv_p = argv; @@ -604,7 +623,10 @@ int parse_action_control_slash(int *argc_p, char ***argv_p, void print_action_control(FILE *f, const char *prefix, int action, const char *suffix) { - fprintf(f, "%s%s%s", prefix, action_n2a(action), suffix); + fprintf(f, "%s%s", prefix, action_n2a(action)); + if (TC_ACT_EXT_CMP(action, TC_ACT_GOTO_CHAIN)) + fprintf(f, " chain %u", action & TC_ACT_EXT_VAL_MASK); + fprintf(f, "%s", suffix); } int get_linklayer(unsigned int *val, const char *arg) -- 2.20.1