]> git.proxmox.com Git - mirror_iproute2.git/blobdiff - tc/m_police.c
lib: introduce print_nl
[mirror_iproute2.git] / tc / m_police.c
index 9ae25f28882021330fb011ca094a089b785e1d60..f3b07f7b0439c172413144b9d8e3a73cbca624a8 100644 (file)
@@ -16,7 +16,6 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <unistd.h>
-#include <syslog.h>
 #include <fcntl.h>
 #include <sys/socket.h>
 #include <netinet/in.h>
@@ -36,11 +35,13 @@ static void usage(void)
 {
        fprintf(stderr, "Usage: ... police rate BPS burst BYTES[/BYTES] [ mtu BYTES[/BYTES] ]\n");
        fprintf(stderr, "                [ peakrate BPS ] [ avrate BPS ] [ overhead BYTES ]\n");
-       fprintf(stderr, "                [ linklayer TYPE ] [ ACTIONTERM ]\n");
+       fprintf(stderr, "                [ linklayer TYPE ] [ CONTROL ]\n");
 
-       fprintf(stderr, "New Syntax ACTIONTERM := conform-exceed <EXCEEDACT>[/NOTEXCEEDACT]\n");
-       fprintf(stderr, "Where: *EXCEEDACT := pipe | ok | reclassify | drop | continue\n");
-       fprintf(stderr, "Where:  pipe is only valid for new syntax\n");
+       fprintf(stderr, "Where: CONTROL := conform-exceed <EXCEEDACT>[/NOTEXCEEDACT]\n");
+       fprintf(stderr, "                  Define how to handle packets which exceed (<EXCEEDACT>)\n");
+       fprintf(stderr, "                  or conform (<NOTEXCEEDACT>) the configured bandwidth limit.\n");
+       fprintf(stderr, "       EXCEEDACT/NOTEXCEEDACT := { pipe | ok | reclassify | drop | continue |\n");
+       fprintf(stderr, "                                   goto chain <CHAIN_INDEX> }\n");
        exit(-1);
 }
 
@@ -49,77 +50,6 @@ static void explain1(char *arg)
        fprintf(stderr, "Illegal \"%s\"\n", arg);
 }
 
-static const char *police_action_n2a(int action, char *buf, int len)
-{
-       switch (action) {
-       case -1:
-               return "continue";
-               break;
-       case TC_POLICE_OK:
-               return "pass";
-               break;
-       case TC_POLICE_SHOT:
-               return "drop";
-               break;
-       case TC_POLICE_RECLASSIFY:
-               return "reclassify";
-       case TC_POLICE_PIPE:
-               return "pipe";
-       default:
-               snprintf(buf, len, "%d", action);
-               return buf;
-       }
-}
-
-static int police_action_a2n(const char *arg, int *result)
-{
-       int res;
-
-       if (matches(arg, "continue") == 0)
-               res = -1;
-       else if (matches(arg, "drop") == 0)
-               res = TC_POLICE_SHOT;
-       else if (matches(arg, "shot") == 0)
-               res = TC_POLICE_SHOT;
-       else if (matches(arg, "pass") == 0)
-               res = TC_POLICE_OK;
-       else if (strcmp(arg, "ok") == 0)
-               res = TC_POLICE_OK;
-       else if (matches(arg, "reclassify") == 0)
-               res = TC_POLICE_RECLASSIFY;
-       else if (matches(arg, "pipe") == 0)
-               res = TC_POLICE_PIPE;
-       else {
-               char dummy;
-
-               if (sscanf(arg, "%d%c", &res, &dummy) != 1)
-                       return -1;
-       }
-       *result = res;
-       return 0;
-}
-
-static int get_police_result(int *action, int *result, char *arg)
-{
-       char *p = strchr(arg, '/');
-
-       if (p)
-               *p = 0;
-
-       if (police_action_a2n(arg, action)) {
-               if (p)
-                       *p = '/';
-               return -1;
-       }
-
-       if (p) {
-               *p = '/';
-               if (police_action_a2n(p+1, result))
-                       return -1;
-       }
-       return 0;
-}
-
 int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p,
                     int tca_id, struct nlmsghdr *n)
 {
@@ -215,23 +145,23 @@ int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p,
                                explain1("peakrate");
                                return -1;
                        }
-               } else if (matches(*argv, "reclassify") == 0) {
-                       p.action = TC_POLICE_RECLASSIFY;
-               } else if (matches(*argv, "drop") == 0 ||
-                          matches(*argv, "shot") == 0) {
-                       p.action = TC_POLICE_SHOT;
-               } else if (matches(*argv, "continue") == 0) {
-                       p.action = TC_POLICE_UNSPEC;
-               } else if (matches(*argv, "pass") == 0) {
-                       p.action = TC_POLICE_OK;
-               } else if (matches(*argv, "pipe") == 0) {
-                       p.action = TC_POLICE_PIPE;
+               } else if (matches(*argv, "reclassify") == 0 ||
+                          matches(*argv, "drop") == 0 ||
+                          matches(*argv, "shot") == 0 ||
+                          matches(*argv, "continue") == 0 ||
+                          matches(*argv, "pass") == 0 ||
+                          matches(*argv, "ok") == 0 ||
+                          matches(*argv, "pipe") == 0 ||
+                          matches(*argv, "goto") == 0) {
+                       if (!parse_action_control(&argc, &argv, &p.action, false))
+                               goto action_ctrl_ok;
+                       return -1;
                } else if (strcmp(*argv, "conform-exceed") == 0) {
                        NEXT_ARG();
-                       if (get_police_result(&p.action, &presult, *argv)) {
-                               fprintf(stderr, "Illegal \"action\"\n");
-                               return -1;
-                       }
+                       if (!parse_action_control_slash(&argc, &argv, &p.action,
+                                                       &presult, true))
+                               goto action_ctrl_ok;
+                       return -1;
                } else if (matches(*argv, "overhead") == 0) {
                        NEXT_ARG();
                        if (get_u16(&overhead, *argv, 10)) {
@@ -247,8 +177,9 @@ int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p,
                } else {
                        break;
                }
+               NEXT_ARG_FWD();
+action_ctrl_ok:
                ok++;
-               argc--; argv++;
        }
 
        if (!ok)
@@ -301,8 +232,7 @@ int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p,
                }
        }
 
-       tail = NLMSG_TAIL(n);
-       addattr_l(n, MAX_MSG, tca_id, NULL, 0);
+       tail = addattr_nest(n, MAX_MSG, tca_id);
        addattr_l(n, MAX_MSG, TCA_POLICE_TBF, &p, sizeof(p));
        if (p.rate.rate)
                addattr_l(n, MAX_MSG, TCA_POLICE_RATE, rtab, 1024);
@@ -313,7 +243,7 @@ int act_parse_police(struct action_util *a, int *argc_p, char ***argv_p,
        if (presult)
                addattr32(n, MAX_MSG, TCA_POLICE_RESULT, presult);
 
-       tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
+       addattr_nest_end(n, tail);
        res = 0;
 
        *argc_p = argc;
@@ -367,14 +297,13 @@ int print_police(struct action_util *a, FILE *f, struct rtattr *arg)
                fprintf(f, "avrate %s ",
                        sprint_rate(rta_getattr_u32(tb[TCA_POLICE_AVRATE]),
                                    b1));
-       fprintf(f, "action %s",
-               police_action_n2a(p->action, b1, sizeof(b1)));
+
+       print_action_control(f, "action ", p->action, "");
 
        if (tb[TCA_POLICE_RESULT]) {
                __u32 action = rta_getattr_u32(tb[TCA_POLICE_RESULT]);
 
-               fprintf(f, "/%s",
-                       police_action_n2a(action, b1, sizeof(b1)));
+               print_action_control(f, "/", action, " ");
        } else
                fprintf(f, " ");