From 17ee3c1ffddb06a93c20617eda5d60b474c22dbe Mon Sep 17 00:00:00 2001 From: Ben Pfaff Date: Fri, 16 Jul 2010 15:50:57 -0700 Subject: [PATCH] netdev-linux: Avoid minor number 0 in traffic control. Linux traffic control handles with minor number 0 refer to qdiscs, not to classes. This commit deals with this by using a conversion function: OpenFlow queue 0 maps to minor 1, queue 1 to minor 2, and so on. --- lib/dpif-linux.c | 2 +- lib/netdev-linux.c | 18 +++++++++++------- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/lib/dpif-linux.c b/lib/dpif-linux.c index a28355d48..432d5ed1a 100644 --- a/lib/dpif-linux.c +++ b/lib/dpif-linux.c @@ -463,7 +463,7 @@ dpif_linux_queue_to_priority(const struct dpif *dpif OVS_UNUSED, uint32_t queue_id, uint32_t *priority) { if (queue_id < 0xf000) { - *priority = TC_H_MAKE(1 << 16, queue_id); + *priority = TC_H_MAKE(1 << 16, queue_id + 1); return 0; } else { return EINVAL; diff --git a/lib/netdev-linux.c b/lib/netdev-linux.c index bcba1a237..09a461296 100644 --- a/lib/netdev-linux.c +++ b/lib/netdev-linux.c @@ -2341,8 +2341,10 @@ htb_parse_tcmsg__(struct ofpbuf *tcmsg, unsigned int *queue_id, error = tc_parse_class(tcmsg, &handle, &nl_options, stats); if (!error && queue_id) { - if (tc_get_major(handle) == 1 && tc_get_minor(handle) < HTB_N_QUEUES) { - *queue_id = tc_get_minor(handle); + unsigned int major = tc_get_major(handle); + unsigned int minor = tc_get_minor(handle); + if (major == 1 && minor > 0 && minor <= HTB_N_QUEUES) { + *queue_id = minor - 1; } else { error = EPROTO; } @@ -2567,7 +2569,7 @@ htb_class_set(struct netdev *netdev, unsigned int queue_id, return error; } - error = htb_setup_class__(netdev, tc_make_handle(1, queue_id), + error = htb_setup_class__(netdev, tc_make_handle(1, queue_id + 1), tc_make_handle(1, 0xfffe), &hc); if (error) { return error; @@ -2587,7 +2589,7 @@ htb_class_delete(struct netdev *netdev, unsigned int queue_id) hc = port_array_get(&htb->tc.queues, queue_id); assert(hc != NULL); - error = tc_delete_class(netdev, tc_make_handle(1, queue_id)); + error = tc_delete_class(netdev, tc_make_handle(1, queue_id + 1)); if (!error) { free(hc); port_array_delete(&htb->tc.queues, queue_id); @@ -2599,7 +2601,7 @@ static int htb_class_get_stats(const struct netdev *netdev, unsigned int queue_id, struct netdev_queue_stats *stats) { - return htb_query_class__(netdev, tc_make_handle(1, queue_id), + return htb_query_class__(netdev, tc_make_handle(1, queue_id + 1), tc_make_handle(1, 0xfffe), NULL, stats); } @@ -2609,7 +2611,7 @@ htb_class_dump_stats(const struct netdev *netdev OVS_UNUSED, netdev_dump_queue_stats_cb *cb, void *aux) { struct netdev_queue_stats stats; - unsigned int handle; + unsigned int handle, major, minor; int error; error = tc_parse_class(nlmsg, &handle, NULL, &stats); @@ -2617,7 +2619,9 @@ htb_class_dump_stats(const struct netdev *netdev OVS_UNUSED, return error; } - if (tc_get_major(handle) == 1 && tc_get_minor(handle) < HTB_N_QUEUES) { + major = tc_get_major(handle); + minor = tc_get_minor(handle); + if (major == 1 && minor > 0 && minor <= HTB_N_QUEUES) { (*cb)(tc_get_minor(handle), &stats, aux); } return 0; -- 2.43.0