2 * m_skbedit.c SKB Editing module
4 * Copyright (c) 2008, Intel Corporation.
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
15 * You should have received a copy of the GNU General Public License along with
16 * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
17 * Place - Suite 330, Boston, MA 02111-1307 USA.
19 * Authors: Alexander Duyck <alexander.h.duyck@intel.com>
29 #include <linux/tc_act/tc_skbedit.h>
34 fprintf(stderr, "Usage: ... skbedit "
35 "queue_mapping QUEUE_MAPPING | priority PRIORITY \n"
36 "QUEUE_MAPPING = device transmit queue to use\n"
37 "PRIORITY = classID to assign to priority field\n");
48 parse_skbedit(struct action_util *a, int *argc_p, char ***argv_p, int tca_id,
51 struct tc_skbedit sel;
53 char **argv = *argv_p;
58 __u32 flags = 0, priority;
60 if (matches(*argv, "skbedit") != 0)
66 if (matches(*argv, "queue_mapping") == 0) {
67 flags |= SKBEDIT_F_QUEUE_MAPPING;
69 if (get_unsigned(&tmp, *argv, 10) || tmp > 65535) {
70 fprintf(stderr, "Illegal queue_mapping\n");
75 } else if (matches(*argv, "priority") == 0) {
76 flags |= SKBEDIT_F_PRIORITY;
78 if (get_tc_classid(&priority, *argv)) {
79 fprintf(stderr, "Illegal priority\n");
83 } else if (matches(*argv, "help") == 0) {
93 if (matches(*argv, "reclassify") == 0) {
94 sel.action = TC_ACT_RECLASSIFY;
96 } else if (matches(*argv, "pipe") == 0) {
97 sel.action = TC_ACT_PIPE;
99 } else if (matches(*argv, "drop") == 0 ||
100 matches(*argv, "shot") == 0) {
101 sel.action = TC_ACT_SHOT;
103 } else if (matches(*argv, "continue") == 0) {
104 sel.action = TC_ACT_UNSPEC;
106 } else if (matches(*argv, "pass") == 0) {
107 sel.action = TC_ACT_OK;
113 if (matches(*argv, "index") == 0) {
115 if (get_u32(&sel.index, *argv, 10)) {
116 fprintf(stderr, "Pedit: Illegal \"index\"\n");
131 tail = NLMSG_TAIL(n);
132 addattr_l(n, MAX_MSG, tca_id, NULL, 0);
133 addattr_l(n, MAX_MSG, TCA_SKBEDIT_PARMS, &sel, sizeof(sel));
134 if (flags & SKBEDIT_F_QUEUE_MAPPING)
135 addattr_l(n, MAX_MSG, TCA_SKBEDIT_QUEUE_MAPPING,
136 &queue_mapping, sizeof(queue_mapping));
137 if (flags & SKBEDIT_F_PRIORITY)
138 addattr_l(n, MAX_MSG, TCA_SKBEDIT_PRIORITY,
139 &priority, sizeof(priority));
140 tail->rta_len = (char *)NLMSG_TAIL(n) - (char *)tail;
147 static int print_skbedit(struct action_util *au, FILE *f, struct rtattr *arg)
149 struct tc_skbedit *sel;
150 struct rtattr *tb[TCA_SKBEDIT_MAX + 1];
153 __u16 *queue_mapping;
158 parse_rtattr_nested(tb, TCA_SKBEDIT_MAX, arg);
160 if (tb[TCA_SKBEDIT_PARMS] == NULL) {
161 fprintf(f, "[NULL skbedit parameters]");
165 sel = RTA_DATA(tb[TCA_SKBEDIT_PARMS]);
167 fprintf(f, " skbedit");
169 if (tb[TCA_SKBEDIT_QUEUE_MAPPING] != NULL) {
170 queue_mapping = RTA_DATA(tb[TCA_SKBEDIT_QUEUE_MAPPING]);
171 fprintf(f, " queue_mapping %u", *queue_mapping);
173 if (tb[TCA_SKBEDIT_PRIORITY] != NULL) {
174 priority = RTA_DATA(tb[TCA_SKBEDIT_PRIORITY]);
175 fprintf(f, " priority %s", sprint_tc_classid(*priority, b1));
179 if (tb[TCA_SKBEDIT_TM]) {
180 struct tcf_t *tm = RTA_DATA(tb[TCA_SKBEDIT_TM]);
188 struct action_util skbedit_action_util = {
190 .parse_aopt = parse_skbedit,
191 .print_aopt = print_skbedit,