aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Ahern <dsahern@gmail.com>2020-04-19 22:26:27 +0000
committerDavid Ahern <dsahern@gmail.com>2020-04-19 22:26:27 +0000
commit59ba1dd01175f8beff964d4e634e7612dc83bb59 (patch)
treee00bc3a898b5e7f11f6d103729aab3317ef6f641
parent5c762c3bc226cbfc2d7384b46985a885267961a7 (diff)
parentfe821d64e60cee2abc4347b3f67e8a3d698777a0 (diff)
downloadiproute2-59ba1dd01175f8beff964d4e634e7612dc83bb59.tar.gz
Merge branch 'master' into next
Signed-off-by: David Ahern <dsahern@gmail.com>
-rw-r--r--devlink/devlink.c54
-rw-r--r--ip/link_gre.c34
-rw-r--r--man/man8/tc-htb.824
3 files changed, 97 insertions, 15 deletions
diff --git a/devlink/devlink.c b/devlink/devlink.c
index 4cf58f408..f67fe6dd8 100644
--- a/devlink/devlink.c
+++ b/devlink/devlink.c
@@ -152,6 +152,30 @@ static int _mnlg_socket_recv_run(struct mnlg_socket *nlg,
return 0;
}
+static void dummy_signal_handler(int signum)
+{
+}
+
+static int _mnlg_socket_recv_run_intr(struct mnlg_socket *nlg,
+ mnl_cb_t data_cb, void *data)
+{
+ struct sigaction act, oact;
+ int err;
+
+ act.sa_handler = dummy_signal_handler;
+ sigemptyset(&act.sa_mask);
+ act.sa_flags = SA_NODEFER;
+
+ sigaction(SIGINT, &act, &oact);
+ err = mnlg_socket_recv_run(nlg, data_cb, data);
+ sigaction(SIGINT, &oact, NULL);
+ if (err < 0 && errno != EINTR) {
+ pr_err("devlink answers: %s\n", strerror(errno));
+ return -errno;
+ }
+ return 0;
+}
+
static int _mnlg_socket_send(struct mnlg_socket *nlg,
const struct nlmsghdr *nlh)
{
@@ -4236,7 +4260,21 @@ static const char *cmd_obj(uint8_t cmd)
static void pr_out_mon_header(uint8_t cmd)
{
- pr_out("[%s,%s] ", cmd_obj(cmd), cmd_name(cmd));
+ if (!is_json_context()) {
+ pr_out("[%s,%s] ", cmd_obj(cmd), cmd_name(cmd));
+ } else {
+ open_json_object(NULL);
+ print_string(PRINT_JSON, "command", NULL, cmd_name(cmd));
+ open_json_object(cmd_obj(cmd));
+ }
+}
+
+static void pr_out_mon_footer(void)
+{
+ if (is_json_context()) {
+ close_json_object();
+ close_json_object();
+ }
}
static bool cmd_filter_check(struct dl *dl, uint8_t cmd)
@@ -4306,6 +4344,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_handle(dl, tb);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_PORT_GET: /* fall through */
case DEVLINK_CMD_PORT_SET: /* fall through */
@@ -4317,6 +4356,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_port(dl, tb);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_PARAM_GET: /* fall through */
case DEVLINK_CMD_PARAM_SET: /* fall through */
@@ -4328,6 +4368,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_param(dl, tb, false);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_REGION_GET: /* fall through */
case DEVLINK_CMD_REGION_SET: /* fall through */
@@ -4339,6 +4380,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_region(dl, tb);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_FLASH_UPDATE: /* fall through */
case DEVLINK_CMD_FLASH_UPDATE_END: /* fall through */
@@ -4348,6 +4390,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_flash_update(dl, tb);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_HEALTH_REPORTER_RECOVER:
mnl_attr_parse(nlh, sizeof(*genl), attr_cb, tb);
@@ -4356,6 +4399,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_health(dl, tb);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_TRAP_GET: /* fall through */
case DEVLINK_CMD_TRAP_SET: /* fall through */
@@ -4372,6 +4416,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_trap(dl, tb, false);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_TRAP_GROUP_GET: /* fall through */
case DEVLINK_CMD_TRAP_GROUP_SET: /* fall through */
@@ -4384,6 +4429,7 @@ static int cmd_mon_show_cb(const struct nlmsghdr *nlh, void *data)
return MNL_CB_ERROR;
pr_out_mon_header(genl->cmd);
pr_out_trap_group(dl, tb, false);
+ pr_out_mon_footer();
break;
case DEVLINK_CMD_TRAP_POLICER_GET: /* fall through */
case DEVLINK_CMD_TRAP_POLICER_SET: /* fall through */
@@ -4423,7 +4469,11 @@ static int cmd_mon_show(struct dl *dl)
err = _mnlg_socket_group_add(dl->nlg, DEVLINK_GENL_MCGRP_CONFIG_NAME);
if (err)
return err;
- err = _mnlg_socket_recv_run(dl->nlg, cmd_mon_show_cb, dl);
+ open_json_object(NULL);
+ open_json_array(PRINT_JSON, "mon");
+ err = _mnlg_socket_recv_run_intr(dl->nlg, cmd_mon_show_cb, dl);
+ close_json_array(PRINT_JSON, NULL);
+ close_json_object();
if (err)
return err;
return 0;
diff --git a/ip/link_gre.c b/ip/link_gre.c
index e42f21ae4..d616a970e 100644
--- a/ip/link_gre.c
+++ b/ip/link_gre.c
@@ -23,8 +23,15 @@
#include "ip_common.h"
#include "tunnel.h"
+static bool gre_is_erspan(struct link_util *lu)
+{
+ return !strcmp(lu->id, "erspan");
+}
+
static void gre_print_help(struct link_util *lu, int argc, char **argv, FILE *f)
{
+ bool is_erspan = gre_is_erspan(lu);
+
fprintf(f,
"Usage: ... %-9s [ remote ADDR ]\n"
" [ local ADDR ]\n"
@@ -44,18 +51,20 @@ static void gre_print_help(struct link_util *lu, int argc, char **argv, FILE *f)
" [ encap-dport PORT ]\n"
" [ [no]encap-csum ]\n"
" [ [no]encap-csum6 ]\n"
- " [ [no]encap-remcsum ]\n"
- " [ erspan_ver version ]\n"
- " [ erspan IDX ]\n"
- " [ erspan_dir { ingress | egress } ]\n"
- " [ erspan_hwid hwid ]\n"
+ " [ [no]encap-remcsum ]\n", lu->id);
+ if (is_erspan)
+ fprintf(f,
+ " [ erspan_ver version ]\n"
+ " [ erspan IDX ]\n"
+ " [ erspan_dir { ingress | egress } ]\n"
+ " [ erspan_hwid hwid ]\n");
+ fprintf(f,
"\n"
"Where: ADDR := { IP_ADDRESS | any }\n"
" TOS := { NUMBER | inherit }\n"
" TTL := { 1..255 | inherit }\n"
" KEY := { DOTTED_QUAD | NUMBER }\n"
- " MARK := { 0x0..0xffffffff }\n",
- lu->id);
+ " MARK := { 0x0..0xffffffff }\n");
}
static int gre_parse_opt(struct link_util *lu, int argc, char **argv,
@@ -93,6 +102,7 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,
__u16 encapdport = 0;
__u8 metadata = 0;
__u32 fwmark = 0;
+ bool is_erspan = gre_is_erspan(lu);
__u32 erspan_idx = 0;
__u8 erspan_ver = 1;
__u8 erspan_dir = 0;
@@ -334,19 +344,19 @@ get_failed:
NEXT_ARG();
if (get_u32(&fwmark, *argv, 0))
invarg("invalid fwmark\n", *argv);
- } else if (strcmp(*argv, "erspan") == 0) {
+ } else if (is_erspan && strcmp(*argv, "erspan") == 0) {
NEXT_ARG();
if (get_u32(&erspan_idx, *argv, 0))
invarg("invalid erspan index\n", *argv);
if (erspan_idx & ~((1<<20) - 1) || erspan_idx == 0)
invarg("erspan index must be > 0 and <= 20-bit\n", *argv);
- } else if (strcmp(*argv, "erspan_ver") == 0) {
+ } else if (is_erspan && strcmp(*argv, "erspan_ver") == 0) {
NEXT_ARG();
if (get_u8(&erspan_ver, *argv, 0))
invarg("invalid erspan version\n", *argv);
if (erspan_ver != 1 && erspan_ver != 2)
invarg("erspan version must be 1 or 2\n", *argv);
- } else if (strcmp(*argv, "erspan_dir") == 0) {
+ } else if (is_erspan && strcmp(*argv, "erspan_dir") == 0) {
NEXT_ARG();
if (matches(*argv, "ingress") == 0)
erspan_dir = 0;
@@ -354,7 +364,7 @@ get_failed:
erspan_dir = 1;
else
invarg("Invalid erspan direction.", *argv);
- } else if (strcmp(*argv, "erspan_hwid") == 0) {
+ } else if (is_erspan && strcmp(*argv, "erspan_hwid") == 0) {
NEXT_ARG();
if (get_u16(&erspan_hwid, *argv, 0))
invarg("invalid erspan hwid\n", *argv);
@@ -402,7 +412,7 @@ get_failed:
addattr32(n, 1024, IFLA_GRE_LINK, link);
addattr_l(n, 1024, IFLA_GRE_TTL, &ttl, 1);
addattr32(n, 1024, IFLA_GRE_FWMARK, fwmark);
- if (erspan_ver) {
+ if (is_erspan) {
addattr8(n, 1024, IFLA_GRE_ERSPAN_VER, erspan_ver);
if (erspan_ver == 1 && erspan_idx != 0) {
addattr32(n, 1024, IFLA_GRE_ERSPAN_INDEX, erspan_idx);
diff --git a/man/man8/tc-htb.8 b/man/man8/tc-htb.8
index ae310f43f..a41623427 100644
--- a/man/man8/tc-htb.8
+++ b/man/man8/tc-htb.8
@@ -10,6 +10,8 @@ classid
major:
.B ] htb [ default
minor-id
+.B ] [ r2q
+divisor
.B ]
.B tc class ... dev
@@ -28,6 +30,8 @@ bytes
bytes
.B ] [ prio
priority
+.B ] [ quantum
+bytes
.B ]
.SH DESCRIPTION
@@ -93,6 +97,13 @@ will be generated within this qdisc.
.TP
default minor-id
Unclassified traffic gets sent to the class with this minor-id.
+.TP
+r2q divisor
+Divisor used to calculate
+.B quantum
+values for classes. Classes divide
+.B rate
+by this number. Default value is 10.
.SH CLASSES
Classes have a host of parameters to configure their operation.
@@ -109,7 +120,7 @@ class is going to have children.
.TP
prio priority
In the round-robin process, classes with the lowest priority field are tried
-for packets first. Mandatory.
+for packets first.
.TP
rate rate
@@ -134,6 +145,17 @@ Amount of bytes that can be burst at 'infinite' speed, in other words, as fast
as the interface can transmit them. For perfect evening out, should be equal to at most one average
packet. Should be at least as high as the highest cburst of all children.
+.TP
+quantum bytes
+Number of bytes to serve from this class before the scheduler moves to the next class.
+Default value is
+.B rate
+divided by the qdisc
+.B r2q
+parameter. If specified,
+.B r2q
+is ignored.
+
.SH NOTES
Due to Unix timing constraints, the maximum ceil rate is not infinite and may in fact be quite low. On Intel,
there are 100 timer events per second, the maximum rate is that rate at which 'burst' bytes are sent each timer tick.