* [master/thud][PATCH] iproute2: soft taprio: add patches for taprio
@ 2019-10-28 19:13 Jacob Stiffler
2019-10-29 21:04 ` Denys Dmytriyenko
0 siblings, 1 reply; 2+ messages in thread
From: Jacob Stiffler @ 2019-10-28 19:13 UTC (permalink / raw)
To: meta-arago
Signed-off-by: Jacob Stiffler <j-stiffler@ti.com>
---
.../iproute2/0001-utils-Implement-get_s64.patch | 64 +++
...-helper-to-retrieve-a-__s64-from-a-netlin.patch | 39 ++
...Add-helper-for-getting-a-__s32-from-netli.patch | 36 ++
...port-for-configuring-the-taprio-scheduler.patch | 488 +++++++++++++++++++++
.../0005-taprio-Add-manpage-for-tc-taprio-8.patch | 168 +++++++
...taprio-Add-support-for-changing-schedules.patch | 150 +++++++
...support-for-cycle_time-and-cycle_time_ext.patch | 147 +++++++
.../iproute2/0008-utils-Fix-get_s64-function.patch | 34 ++
...0009-taprio-Add-support-for-setting-flags.patch | 77 ++++
...prio-add-support-for-setting-txtime_delay.patch | 96 ++++
.../0011-tc-taprio-Update-documentation.patch | 80 ++++
| 128 ++++++
.../iproute2/iproute2_4.19.0.bbappend | 14 +-
13 files changed, 1520 insertions(+), 1 deletion(-)
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
new file mode 100644
index 0000000..a0d5a12
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
@@ -0,0 +1,64 @@
+From 7e4397dff47438be65fdf90dc4e51b763797d201 Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Fri, 5 Oct 2018 16:25:17 -0700
+Subject: [PATCH 01/12] utils: Implement get_s64()
+
+commit a066bac8a2775bc43d54ae7173057f75f543c44b upstream.
+
+Add this helper to read signed 64-bit integers from a string.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ include/utils.h | 1 +
+ lib/utils.c | 21 +++++++++++++++++++++
+ 2 files changed, 22 insertions(+)
+
+diff --git a/include/utils.h b/include/utils.h
+index 8cb4349e..58574a05 100644
+--- a/include/utils.h
++++ b/include/utils.h
+@@ -139,6 +139,7 @@ int get_time_rtt(unsigned *val, const char *arg, int *raw);
+ #define get_byte get_u8
+ #define get_ushort get_u16
+ #define get_short get_s16
++int get_s64(__s64 *val, const char *arg, int base);
+ int get_u64(__u64 *val, const char *arg, int base);
+ int get_u32(__u32 *val, const char *arg, int base);
+ int get_s32(__s32 *val, const char *arg, int base);
+diff --git a/lib/utils.c b/lib/utils.c
+index ad27f78c..be29530f 100644
+--- a/lib/utils.c
++++ b/lib/utils.c
+@@ -384,6 +384,27 @@ int get_u8(__u8 *val, const char *arg, int base)
+ return 0;
+ }
+
++int get_s64(__s64 *val, const char *arg, int base)
++{
++ long res;
++ char *ptr;
++
++ errno = 0;
++
++ if (!arg || !*arg)
++ return -1;
++ res = strtoll(arg, &ptr, base);
++ if (!ptr || ptr == arg || *ptr)
++ return -1;
++ if ((res == LLONG_MIN || res == LLONG_MAX) && errno == ERANGE)
++ return -1;
++ if (res > INT64_MAX || res < INT64_MIN)
++ return -1;
++
++ *val = res;
++ return 0;
++}
++
+ int get_s32(__s32 *val, const char *arg, int base)
+ {
+ long res;
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
new file mode 100644
index 0000000..b01e11d
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
@@ -0,0 +1,39 @@
+From 6d0bcdd9d0283768798227f4046414ed7da42047 Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Fri, 5 Oct 2018 16:25:18 -0700
+Subject: [PATCH 02/12] include: Add helper to retrieve a __s64 from a netlink
+ msg
+
+commit de63cd90444ac9fdf238f950c16cafe351846691 upstream.
+
+This allows signed 64-bit integers to be retrieved from a netlink
+message.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ include/libnetlink.h | 7 +++++++
+ 1 file changed, 7 insertions(+)
+
+diff --git a/include/libnetlink.h b/include/libnetlink.h
+index 9d9249e6..ffc49e56 100644
+--- a/include/libnetlink.h
++++ b/include/libnetlink.h
+@@ -185,6 +185,13 @@ static inline __u64 rta_getattr_u64(const struct rtattr *rta)
+ memcpy(&tmp, RTA_DATA(rta), sizeof(__u64));
+ return tmp;
+ }
++static inline __s64 rta_getattr_s64(const struct rtattr *rta)
++{
++ __s64 tmp;
++
++ memcpy(&tmp, RTA_DATA(rta), sizeof(tmp));
++ return tmp;
++}
+ static inline const char *rta_getattr_str(const struct rtattr *rta)
+ {
+ return (const char *)RTA_DATA(rta);
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
new file mode 100644
index 0000000..1718c23
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
@@ -0,0 +1,36 @@
+From ca37dce0e9c50645a3473dc942a33478eb79378d Mon Sep 17 00:00:00 2001
+From: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
+Date: Fri, 5 Oct 2018 16:25:19 -0700
+Subject: [PATCH 03/12] libnetlink: Add helper for getting a __s32 from netlink
+ msgs
+
+commit d791f3ad869659da4b151eded060840a88d9656a upstream.
+
+This function retrieves a signed 32-bit integer from a netlink message
+and returns it.
+
+Signed-off-by: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ include/libnetlink.h | 4 ++++
+ 1 file changed, 4 insertions(+)
+
+diff --git a/include/libnetlink.h b/include/libnetlink.h
+index ffc49e56..c44c3c72 100644
+--- a/include/libnetlink.h
++++ b/include/libnetlink.h
+@@ -185,6 +185,10 @@ static inline __u64 rta_getattr_u64(const struct rtattr *rta)
+ memcpy(&tmp, RTA_DATA(rta), sizeof(__u64));
+ return tmp;
+ }
++static inline __s32 rta_getattr_s32(const struct rtattr *rta)
++{
++ return *(__s32 *)RTA_DATA(rta);
++}
+ static inline __s64 rta_getattr_s64(const struct rtattr *rta)
+ {
+ __s64 tmp;
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
new file mode 100644
index 0000000..7cbf027
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
@@ -0,0 +1,488 @@
+From b53ed00cc819a9d57983f48a9fe8d02ec3b50fca Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Fri, 5 Oct 2018 16:25:21 -0700
+Subject: [PATCH 04/12] tc: Add support for configuring the taprio scheduler
+
+commit 0dd16449356f7ba88e5374392b577f0504b3f025 upstream.
+
+This traffic scheduler allows traffic classes states (transmission
+allowed/not allowed, in the simplest case) to be scheduled, according
+to a pre-generated time sequence. This is the basis of the IEEE
+802.1Qbv specification.
+
+Example configuration:
+
+tc qdisc replace dev enp3s0 parent root handle 100 taprio \
+ num_tc 3 \
+ map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \
+ queues 1@0 1@1 2@2 \
+ base-time 1528743495910289987 \
+ sched-entry S 01 300000 \
+ sched-entry S 02 300000 \
+ sched-entry S 04 300000 \
+ clockid CLOCK_TAI
+
+The configuration format is similar to mqprio. The main difference is
+the presence of a schedule, built by multiple "sched-entry"
+definitions, each entry has the following format:
+
+ sched-entry <CMD> <GATE MASK> <INTERVAL>
+
+The only supported <CMD> is "S", which means "SetGateStates",
+following the IEEE 802.1Qbv-2015 definition (Table 8-6). <GATE MASK>
+is a bitmask where each bit is a associated with a traffic class, so
+bit 0 (the least significant bit) being "on" means that traffic class
+0 is "active" for that schedule entry. <INTERVAL> is a time duration
+in nanoseconds that specifies for how long that state defined by <CMD>
+and <GATE MASK> should be held before moving to the next entry.
+
+This schedule is circular, that is, after the last entry is executed
+it starts from the first one, indefinitely.
+
+The other parameters can be defined as follows:
+
+ - base-time: specifies the instant when the schedule starts, if
+ 'base-time' is a time in the past, the schedule will start at
+
+ base-time + (N * cycle-time)
+
+ where N is the smallest integer so the resulting time is greater
+ than "now", and "cycle-time" is the sum of all the intervals of the
+ entries in the schedule;
+
+ - clockid: specifies the reference clock to be used;
+
+The parameters should be similar to what the IEEE 802.1Q family of
+specification defines.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ tc/Makefile | 1 +
+ tc/q_taprio.c | 400 ++++++++++++++++++++++++++++++++++++++++++++++++++
+ 2 files changed, 401 insertions(+)
+ create mode 100644 tc/q_taprio.c
+
+diff --git a/tc/Makefile b/tc/Makefile
+index 5a1a7ff9..25a28284 100644
+--- a/tc/Makefile
++++ b/tc/Makefile
+@@ -74,6 +74,7 @@ TCMODULES += e_bpf.o
+ TCMODULES += f_matchall.o
+ TCMODULES += q_cbs.o
+ TCMODULES += q_etf.o
++TCMODULES += q_taprio.o
+
+ TCSO :=
+ ifeq ($(TC_CONFIG_ATM),y)
+diff --git a/tc/q_taprio.c b/tc/q_taprio.c
+new file mode 100644
+index 00000000..562dacb8
+--- /dev/null
++++ b/tc/q_taprio.c
+@@ -0,0 +1,400 @@
++/*
++ * q_taprio.c Time Aware Priority Scheduler
++ *
++ * This program is free software; you can redistribute it and/or
++ * modify it under the terms of the GNU General Public License
++ * as published by the Free Software Foundation; either version
++ * 2 of the License, or (at your option) any later version.
++ *
++ * Authors: Vinicius Costa Gomes <vinicius.gomes@intel.com>
++ * Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
++ */
++
++#include <stdio.h>
++#include <stdlib.h>
++#include <unistd.h>
++#include <syslog.h>
++#include <fcntl.h>
++#include <inttypes.h>
++#include <sys/socket.h>
++#include <netinet/in.h>
++#include <arpa/inet.h>
++#include <string.h>
++
++#include "utils.h"
++#include "tc_util.h"
++#include "list.h"
++
++struct sched_entry {
++ struct list_head list;
++ uint32_t index;
++ uint32_t interval;
++ uint32_t gatemask;
++ uint8_t cmd;
++};
++
++#define CLOCKID_INVALID (-1)
++static const struct static_clockid {
++ const char *name;
++ clockid_t clockid;
++} clockids_sysv[] = {
++ { "REALTIME", CLOCK_REALTIME },
++ { "TAI", CLOCK_TAI },
++ { "BOOTTIME", CLOCK_BOOTTIME },
++ { "MONOTONIC", CLOCK_MONOTONIC },
++ { NULL }
++};
++
++static void explain(void)
++{
++ fprintf(stderr, "Usage: ... taprio clockid CLOCKID\n");
++ fprintf(stderr, " [num_tc NUMBER] [map P0 P1 ...] ");
++ fprintf(stderr, " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] ");
++ fprintf(stderr, " [ [sched-entry index cmd gate-mask interval] ... ] ");
++ fprintf(stderr, " [base-time time] ");
++ fprintf(stderr, "\nCLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)");
++ fprintf(stderr, "\n");
++}
++
++static void explain_clockid(const char *val)
++{
++ fprintf(stderr, "taprio: illegal value for \"clockid\": \"%s\".\n", val);
++ fprintf(stderr, "It must be a valid SYS-V id (i.e. CLOCK_TAI)\n");
++}
++
++static int get_clockid(__s32 *val, const char *arg)
++{
++ const struct static_clockid *c;
++
++ /* Drop the CLOCK_ prefix if that is being used. */
++ if (strcasestr(arg, "CLOCK_") != NULL)
++ arg += sizeof("CLOCK_") - 1;
++
++ for (c = clockids_sysv; c->name; c++) {
++ if (strcasecmp(c->name, arg) == 0) {
++ *val = c->clockid;
++
++ return 0;
++ }
++ }
++
++ return -1;
++}
++
++static const char* get_clock_name(clockid_t clockid)
++{
++ const struct static_clockid *c;
++
++ for (c = clockids_sysv; c->name; c++) {
++ if (clockid == c->clockid)
++ return c->name;
++ }
++
++ return "invalid";
++}
++
++static const char *entry_cmd_to_str(__u8 cmd)
++{
++ switch (cmd) {
++ case TC_TAPRIO_CMD_SET_GATES:
++ return "S";
++ default:
++ return "Invalid";
++ }
++}
++
++static int str_to_entry_cmd(const char *str)
++{
++ if (strcmp(str, "S") == 0)
++ return TC_TAPRIO_CMD_SET_GATES;
++
++ return -1;
++}
++
++static int add_sched_list(struct list_head *sched_entries, struct nlmsghdr *n)
++{
++ struct sched_entry *e;
++
++ list_for_each_entry(e, sched_entries, list) {
++ struct rtattr *a;
++
++ a = addattr_nest(n, 1024, TCA_TAPRIO_SCHED_ENTRY);
++
++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_CMD, &e->cmd, sizeof(e->cmd));
++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_GATE_MASK, &e->gatemask, sizeof(e->gatemask));
++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_INTERVAL, &e->interval, sizeof(e->interval));
++
++ addattr_nest_end(n, a);
++ }
++
++ return 0;
++}
++
++static void explain_sched_entry(void)
++{
++ fprintf(stderr, "Usage: ... taprio ... sched-entry <cmd> <gate mask> <interval>\n");
++}
++
++static struct sched_entry *create_entry(uint32_t gatemask, uint32_t interval, uint8_t cmd)
++{
++ struct sched_entry *e;
++
++ e = calloc(1, sizeof(*e));
++ if (!e)
++ return NULL;
++
++ e->gatemask = gatemask;
++ e->interval = interval;
++ e->cmd = cmd;
++
++ return e;
++}
++
++static int taprio_parse_opt(struct qdisc_util *qu, int argc,
++ char **argv, struct nlmsghdr *n, const char *dev)
++{
++ __s32 clockid = CLOCKID_INVALID;
++ struct tc_mqprio_qopt opt = { };
++ struct list_head sched_entries;
++ struct rtattr *tail;
++ __s64 base_time = 0;
++ int err, idx;
++
++ INIT_LIST_HEAD(&sched_entries);
++
++ while (argc > 0) {
++ idx = 0;
++ if (strcmp(*argv, "num_tc") == 0) {
++ NEXT_ARG();
++ if (get_u8(&opt.num_tc, *argv, 10)) {
++ fprintf(stderr, "Illegal \"num_tc\"\n");
++ return -1;
++ }
++ } else if (strcmp(*argv, "map") == 0) {
++ while (idx < TC_QOPT_MAX_QUEUE && NEXT_ARG_OK()) {
++ NEXT_ARG();
++ if (get_u8(&opt.prio_tc_map[idx], *argv, 10)) {
++ PREV_ARG();
++ break;
++ }
++ idx++;
++ }
++ for ( ; idx < TC_QOPT_MAX_QUEUE; idx++)
++ opt.prio_tc_map[idx] = 0;
++ } else if (strcmp(*argv, "queues") == 0) {
++ char *tmp, *tok;
++
++ while (idx < TC_QOPT_MAX_QUEUE && NEXT_ARG_OK()) {
++ NEXT_ARG();
++
++ tmp = strdup(*argv);
++ if (!tmp)
++ break;
++
++ tok = strtok(tmp, "@");
++ if (get_u16(&opt.count[idx], tok, 10)) {
++ free(tmp);
++ PREV_ARG();
++ break;
++ }
++ tok = strtok(NULL, "@");
++ if (get_u16(&opt.offset[idx], tok, 10)) {
++ free(tmp);
++ PREV_ARG();
++ break;
++ }
++ free(tmp);
++ idx++;
++ }
++ } else if (strcmp(*argv, "sched-entry") == 0) {
++ uint32_t mask, interval;
++ struct sched_entry *e;
++ uint8_t cmd;
++
++ NEXT_ARG();
++ err = str_to_entry_cmd(*argv);
++ if (err < 0) {
++ explain_sched_entry();
++ return -1;
++ }
++ cmd = err;
++
++ NEXT_ARG();
++ if (get_u32(&mask, *argv, 16)) {
++ explain_sched_entry();
++ return -1;
++ }
++
++ NEXT_ARG();
++ if (get_u32(&interval, *argv, 0)) {
++ explain_sched_entry();
++ return -1;
++ }
++
++ e = create_entry(mask, interval, cmd);
++ if (!e) {
++ fprintf(stderr, "taprio: not enough memory for new schedule entry\n");
++ return -1;
++ }
++
++ list_add_tail(&e->list, &sched_entries);
++
++ } else if (strcmp(*argv, "base-time") == 0) {
++ NEXT_ARG();
++ if (get_s64(&base_time, *argv, 10)) {
++ PREV_ARG();
++ break;
++ }
++ } else if (strcmp(*argv, "clockid") == 0) {
++ NEXT_ARG();
++ if (clockid != CLOCKID_INVALID) {
++ fprintf(stderr, "taprio: duplicate \"clockid\" specification\n");
++ return -1;
++ }
++ if (get_clockid(&clockid, *argv)) {
++ explain_clockid(*argv);
++ return -1;
++ }
++ } else if (strcmp(*argv, "help") == 0) {
++ explain();
++ return -1;
++ } else {
++ fprintf(stderr, "Unknown argument\n");
++ return -1;
++ }
++ argc--; argv++;
++ }
++
++ tail = NLMSG_TAIL(n);
++ addattr_l(n, 1024, TCA_OPTIONS, NULL, 0);
++
++ if (opt.num_tc > 0)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
++
++ if (base_time)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
++
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
++
++ if (!list_empty(&sched_entries)) {
++ struct rtattr *entry_list;
++ entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
++
++ err = add_sched_list(&sched_entries, n);
++ if (err < 0) {
++ fprintf(stderr, "Could not add schedule to netlink message\n");
++ return -1;
++ }
++
++ addattr_nest_end(n, entry_list);
++ }
++
++ tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
++
++ return 0;
++}
++
++static int print_sched_list(FILE *f, struct rtattr *list)
++{
++ struct rtattr *item;
++ int rem;
++
++ if (list == NULL)
++ return 0;
++
++ rem = RTA_PAYLOAD(list);
++
++ open_json_array(PRINT_JSON, "schedule");
++
++ for (item = RTA_DATA(list); RTA_OK(item, rem); item = RTA_NEXT(item, rem)) {
++ struct rtattr *tb[TCA_TAPRIO_SCHED_ENTRY_MAX + 1];
++ __u32 index = 0, gatemask = 0, interval = 0;
++ __u8 command = 0;
++
++ parse_rtattr_nested(tb, TCA_TAPRIO_SCHED_ENTRY_MAX, item);
++
++ if (tb[TCA_TAPRIO_SCHED_ENTRY_INDEX])
++ index = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_INDEX]);
++
++ if (tb[TCA_TAPRIO_SCHED_ENTRY_CMD])
++ command = rta_getattr_u8(tb[TCA_TAPRIO_SCHED_ENTRY_CMD]);
++
++ if (tb[TCA_TAPRIO_SCHED_ENTRY_GATE_MASK])
++ gatemask = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_GATE_MASK]);
++
++ if (tb[TCA_TAPRIO_SCHED_ENTRY_INTERVAL])
++ interval = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_INTERVAL]);
++
++ open_json_object(NULL);
++ print_uint(PRINT_ANY, "index", "\tindex %u", index);
++ print_string(PRINT_ANY, "cmd", " cmd %s", entry_cmd_to_str(command));
++ print_0xhex(PRINT_ANY, "gatemask", " gatemask %#x", gatemask);
++ print_uint(PRINT_ANY, "interval", " interval %u", interval);
++ close_json_object();
++
++ print_string(PRINT_FP, NULL, "%s", _SL_);
++ }
++
++ close_json_array(PRINT_ANY, "");
++
++ return 0;
++}
++
++static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
++{
++ struct rtattr *tb[TCA_TAPRIO_ATTR_MAX + 1];
++ struct tc_mqprio_qopt *qopt = 0;
++ __s32 clockid = CLOCKID_INVALID;
++ __s64 base_time = 0;
++ int i;
++
++ if (opt == NULL)
++ return 0;
++
++ parse_rtattr_nested(tb, TCA_TAPRIO_ATTR_MAX, opt);
++
++ if (tb[TCA_TAPRIO_ATTR_PRIOMAP] == NULL)
++ return -1;
++
++ qopt = RTA_DATA(tb[TCA_TAPRIO_ATTR_PRIOMAP]);
++
++ print_uint(PRINT_ANY, "tc", "tc %u ", qopt->num_tc);
++
++ open_json_array(PRINT_ANY, "map");
++ for (i = 0; i <= TC_PRIO_MAX; i++)
++ print_uint(PRINT_ANY, NULL, " %u", qopt->prio_tc_map[i]);
++ close_json_array(PRINT_ANY, "");
++
++ print_string(PRINT_FP, NULL, "%s", _SL_);
++
++ open_json_array(PRINT_ANY, "queues");
++ for (i = 0; i < qopt->num_tc; i++) {
++ open_json_object(NULL);
++ print_uint(PRINT_ANY, "offset", " offset %u", qopt->offset[i]);
++ print_uint(PRINT_ANY, "count", " count %u", qopt->count[i]);
++ close_json_object();
++ }
++ close_json_array(PRINT_ANY, "");
++
++ print_string(PRINT_FP, NULL, "%s", _SL_);
++
++ if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
++ base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
++
++ if (tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID])
++ clockid = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID]);
++
++ print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
++
++ print_lluint(PRINT_ANY, "base_time", " base-time %lld", base_time);
++
++ print_string(PRINT_FP, NULL, "%s", _SL_);
++
++ return print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
++}
++
++struct qdisc_util taprio_qdisc_util = {
++ .id = "taprio",
++ .parse_qopt = taprio_parse_opt,
++ .print_qopt = taprio_print_opt,
++};
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
new file mode 100644
index 0000000..a8bbcd0
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
@@ -0,0 +1,168 @@
+From b21190927e151761f138805cf3c208f8d28e8314 Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Fri, 5 Oct 2018 16:25:22 -0700
+Subject: [PATCH 05/12] taprio: Add manpage for tc-taprio(8)
+
+commit 579acb4bc52f84c629df5fcd2f9a054f41b48c57 upstream.
+
+This documents the parameters and provides an example of usage.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ man/man8/tc-taprio.8 | 142 +++++++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 142 insertions(+)
+ create mode 100644 man/man8/tc-taprio.8
+
+diff --git a/man/man8/tc-taprio.8 b/man/man8/tc-taprio.8
+new file mode 100644
+index 00000000..92055b43
+--- /dev/null
++++ b/man/man8/tc-taprio.8
+@@ -0,0 +1,142 @@
++.TH TAPRIO 8 "25 Sept 2018" "iproute2" "Linux"
++.SH NAME
++TAPRIO \- Time Aware Priority Shaper
++.SH SYNOPSIS
++.B tc qdisc ... dev
++dev
++.B parent
++classid
++.B [ handle
++major:
++.B ] taprio num_tc
++tcs
++.ti +8
++.B map
++P0 P1 P2 ...
++.B queues
++count1@offset1 count2@offset2 ...
++.ti +8
++.B base-time
++base-time
++.B clockid
++clockid
++.ti +8
++.B sched-entry
++<command 1> <gate mask 1> <interval 1>
++.ti +8
++.B sched-entry
++<command 2> <gate mask 2> <interval 2>
++.ti +8
++.B sched-entry
++<command 3> <gate mask 3> <interval 3>
++.ti +8
++.B sched-entry
++<command N> <gate mask N> <interval N>
++
++.SH DESCRIPTION
++The TAPRIO qdisc implements a simplified version of the scheduling
++state machine defined by IEEE 802.1Q-2018 Section 8.6.9, which allows
++configuration of a sequence of gate states, where each gate state
++allows outgoing traffic for a subset (potentially empty) of traffic
++classes.
++
++How traffic is mapped to different hardware queues is similar to
++.BR mqprio(8)
++and so the
++.B map
++and
++.Q queues
++parameters have the same meaning.
++
++The other parameters specify the schedule, and at what point in time
++it should start (it can behave as the schedule started in the past).
++
++.SH PARAMETERS
++.TP
++num_tc
++.BR
++Number of traffic classes to use. Up to 16 classes supported.
++
++.TP
++map
++.br
++The priority to traffic class map. Maps priorities 0..15 to a specified
++traffic class. See
++.BR mqprio(8)
++for more details.
++
++.TP
++queues
++.br
++Provide count and offset of queue range for each traffic class. In the
++format,
++.B count@offset.
++Queue ranges for each traffic classes cannot overlap and must be a
++contiguous range of queues.
++
++.TP
++base-time
++.br
++Specifies the instant in nanoseconds, using the reference of
++.B clockid,
++defining the time when the schedule starts. If 'base-time' is a time
++in the past, the schedule will start at
++
++base-time + (N * cycle-time)
++
++where N is the smallest integer so the resulting time is greater than
++"now", and "cycle-time" is the sum of all the intervals of the entries
++in the schedule;
++
++.TP
++clockid
++.br
++Specifies the clock to be used by qdisc's internal timer for measuring
++time and scheduling events.
++
++.TP
++sched-entry
++.br
++There may multiple
++.B sched-entry
++parameters in a single schedule. Each one has the
++
++sched-entry <command> <gatemask> <interval>
++
++format. The only supported <command> is "S", which
++means "SetGateStates", following the IEEE 802.1Q-2018 definition
++(Table 8-7). <gate mask> is a bitmask where each bit is a associated
++with a traffic class, so bit 0 (the least significant bit) being "on"
++means that traffic class 0 is "active" for that schedule entry.
++<interval> is a time duration, in nanoseconds, that specifies for how
++long that state defined by <command> and <gate mask> should be held
++before moving to the next entry.
++
++.SH EXAMPLES
++
++The following example shows how an traffic schedule with three traffic
++classes ("num_tc 3"), which are separated different traffic classes,
++we are going to call these TC 0, TC 1 and TC 2. We could read the
++"map" parameter below as: traffic with priority 3 is classified as TC
++0, priority 2 is classified as TC 1 and the rest is classified as TC
++2.
++
++The schedule will start at instant 1528743495910289987 using the
++reference CLOCK_TAI. The schedule is composed of three entries each of
++300us duration.
++
++.EX
++# tc qdisc replace dev eth0 parent root handle 100 taprio \\
++ num_tc 3 \\
++ map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \\
++ queues 1@0 1@1 2@2 \\
++ base-time 1528743495910289987 \\
++ sched-entry S 01 300000 \\
++ sched-entry S 02 300000 \\
++ sched-entry S 04 300000 \\
++ clockid CLOCK_TAI
++.EE
++
++
++.SH AUTHORS
++Vinicius Costa Gomes <vinicius.gomes@intel.com>
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
new file mode 100644
index 0000000..f0dd3db
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
@@ -0,0 +1,150 @@
+From 3a650c67b63e502989fccdabf8c02a575bdf2116 Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Mon, 29 Apr 2019 15:52:18 -0700
+Subject: [PATCH 06/12] taprio: Add support for changing schedules
+
+commit 602fae856d80bbaa365fd0421e3f2c2417ea804f upstream.
+
+This allows for a new schedule to be specified during runtime, without
+removing the current one.
+
+For that, the semantics of the 'tc qdisc change' operation in the
+context of taprio is that if "change" is called and there is a running
+schedule, a new schedule is created and the base-time (let's call it
+X) of this new schedule is used so at instant X, it becomes the
+"current" schedule. So, in short, "change" doesn't change the current
+schedule, it creates a new one and sets it up to it becomes the
+current one at some point.
+
+In IEEE 802.1Q terms, it means that we have support for the
+"Oper" (current and read-only) and "Admin" (future and mutable)
+schedules.
+
+Example of creating the first schedule, then adding a new one:
+
+(1)
+tc qdisc add dev IFACE parent root handle 100 taprio \
+ num_tc 1 \
+ map 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 \
+ queues 1@0 \
+ sched-entry S 0x1 1000000 \
+ sched-entry S 0x0 2000000 \
+ sched-entry S 0x1 3000000 \
+ sched-entry S 0x0 4000000 \
+ base-time 100000000 \
+ clockid CLOCK_TAI
+
+(2)
+tc qdisc change dev IFACE parent root handle 100 taprio \
+ base-time 7500000000000 \
+ sched-entry S 0x0 5000000 \
+ sched-entry S 0x1 5000000 \
+
+It was necessary to fix a bug, so the clockid doesn't need to be
+specified when changing the schedule.
+
+Most of the changes are related to make it easier to reuse the same
+function for printing the "admin" and "oper" schedules.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ tc/q_taprio.c | 42 +++++++++++++++++++++++++++++++++---------
+ 1 file changed, 33 insertions(+), 9 deletions(-)
+
+diff --git a/tc/q_taprio.c b/tc/q_taprio.c
+index 562dacb8..20804fc2 100644
+--- a/tc/q_taprio.c
++++ b/tc/q_taprio.c
+@@ -268,14 +268,15 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ tail = NLMSG_TAIL(n);
+ addattr_l(n, 1024, TCA_OPTIONS, NULL, 0);
+
++ if (clockid != CLOCKID_INVALID)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
++
+ if (opt.num_tc > 0)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
+
+ if (base_time)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
+
+- addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
+-
+ if (!list_empty(&sched_entries)) {
+ struct rtattr *entry_list;
+ entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
+@@ -306,6 +307,8 @@ static int print_sched_list(FILE *f, struct rtattr *list)
+
+ open_json_array(PRINT_JSON, "schedule");
+
++ print_string(PRINT_FP, NULL, "%s", _SL_);
++
+ for (item = RTA_DATA(list); RTA_OK(item, rem); item = RTA_NEXT(item, rem)) {
+ struct rtattr *tb[TCA_TAPRIO_SCHED_ENTRY_MAX + 1];
+ __u32 index = 0, gatemask = 0, interval = 0;
+@@ -340,12 +343,25 @@ static int print_sched_list(FILE *f, struct rtattr *list)
+ return 0;
+ }
+
++static int print_schedule(FILE *f, struct rtattr **tb)
++{
++ int64_t base_time = 0;
++
++ if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
++ base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
++
++ print_lluint(PRINT_ANY, "base_time", "\tbase-time %lld", base_time);
++
++ print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
++
++ return 0;
++}
++
+ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
+ {
+ struct rtattr *tb[TCA_TAPRIO_ATTR_MAX + 1];
+ struct tc_mqprio_qopt *qopt = 0;
+ __s32 clockid = CLOCKID_INVALID;
+- __s64 base_time = 0;
+ int i;
+
+ if (opt == NULL)
+@@ -378,19 +394,27 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
+
+ print_string(PRINT_FP, NULL, "%s", _SL_);
+
+- if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
+- base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
+-
+ if (tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID])
+ clockid = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID]);
+
+ print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
+
+- print_lluint(PRINT_ANY, "base_time", " base-time %lld", base_time);
++ print_schedule(f, tb);
+
+- print_string(PRINT_FP, NULL, "%s", _SL_);
++ if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
++ struct rtattr *t[TCA_TAPRIO_ATTR_MAX + 1];
++
++ parse_rtattr_nested(t, TCA_TAPRIO_ATTR_MAX,
++ tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]);
+
+- return print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
++ open_json_object(NULL);
++
++ print_schedule(f, t);
++
++ close_json_object();
++ }
++
++ return 0;
+ }
+
+ struct qdisc_util taprio_qdisc_util = {
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
new file mode 100644
index 0000000..6895a6a
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
@@ -0,0 +1,147 @@
+From 538fe8f7e208c7ed7c9af191c25b3c48adb348c3 Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Mon, 29 Apr 2019 15:52:19 -0700
+Subject: [PATCH 07/12] taprio: Add support for cycle_time and
+ cycle_time_extension
+
+commit 92f4b6032e7971d9b0247d7370c08cae2f1c58f9 upstream.
+
+This allows a cycle-time and a cycle-time-extension to be specified.
+
+Specifying a cycle-time will truncate that cycle, so when that instant
+is reached, the cycle will start from its beginning.
+
+A cycle-time-extension may cause the last entry of a cycle, just
+before the start of a new schedule (the base-time of the "admin"
+schedule) to be extended by at maximum "cycle-time-extension"
+nanoseconds. The idea of this feauture, as described by the IEEE
+802.1Q, is too avoid too narrow gate states.
+
+Example:
+
+tc qdisc change dev IFACE parent root handle 100 taprio \
+ sched-entry S 0x1 1000000 \
+ sched-entry S 0x0 2000000 \
+ sched-entry S 0x1 3000000 \
+ sched-entry S 0x0 4000000 \
+ cycle-time-extension 100000 \
+ cycle-time 9000000 \
+ base-time 12345678900000000
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ tc/q_taprio.c | 64 ++++++++++++++++++++++++++++++++++++++++++---------
+ 1 file changed, 53 insertions(+), 11 deletions(-)
+
+diff --git a/tc/q_taprio.c b/tc/q_taprio.c
+index 20804fc2..9a69b86b 100644
+--- a/tc/q_taprio.c
++++ b/tc/q_taprio.c
+@@ -155,8 +155,10 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ {
+ __s32 clockid = CLOCKID_INVALID;
+ struct tc_mqprio_qopt opt = { };
++ __s64 cycle_time_extension = 0;
+ struct list_head sched_entries;
+- struct rtattr *tail;
++ struct rtattr *tail, *l;
++ __s64 cycle_time = 0;
+ __s64 base_time = 0;
+ int err, idx;
+
+@@ -245,6 +247,29 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ PREV_ARG();
+ break;
+ }
++ } else if (strcmp(*argv, "cycle-time") == 0) {
++ NEXT_ARG();
++ if (cycle_time) {
++ fprintf(stderr, "taprio: duplicate \"cycle-time\" specification\n");
++ return -1;
++ }
++
++ if (get_s64(&cycle_time, *argv, 10)) {
++ PREV_ARG();
++ break;
++ }
++
++ } else if (strcmp(*argv, "cycle-time-extension") == 0) {
++ NEXT_ARG();
++ if (cycle_time_extension) {
++ fprintf(stderr, "taprio: duplicate \"cycle-time-extension\" specification\n");
++ return -1;
++ }
++
++ if (get_s64(&cycle_time_extension, *argv, 10)) {
++ PREV_ARG();
++ break;
++ }
+ } else if (strcmp(*argv, "clockid") == 0) {
+ NEXT_ARG();
+ if (clockid != CLOCKID_INVALID) {
+@@ -277,19 +302,24 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ if (base_time)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
+
+- if (!list_empty(&sched_entries)) {
+- struct rtattr *entry_list;
+- entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
++ if (cycle_time)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME,
++ &cycle_time, sizeof(cycle_time));
+
+- err = add_sched_list(&sched_entries, n);
+- if (err < 0) {
+- fprintf(stderr, "Could not add schedule to netlink message\n");
+- return -1;
+- }
++ if (cycle_time_extension)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION,
++ &cycle_time_extension, sizeof(cycle_time_extension));
++
++ l = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
+
+- addattr_nest_end(n, entry_list);
++ err = add_sched_list(&sched_entries, n);
++ if (err < 0) {
++ fprintf(stderr, "Could not add schedule to netlink message\n");
++ return -1;
+ }
+
++ addattr_nest_end(n, l);
++
+ tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
+
+ return 0;
+@@ -345,13 +375,25 @@ static int print_sched_list(FILE *f, struct rtattr *list)
+
+ static int print_schedule(FILE *f, struct rtattr **tb)
+ {
+- int64_t base_time = 0;
++ int64_t base_time = 0, cycle_time = 0, cycle_time_extension = 0;
+
+ if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
+ base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
+
++ if (tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME])
++ cycle_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME]);
++
++ if (tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION])
++ cycle_time_extension = rta_getattr_s64(
++ tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION]);
++
+ print_lluint(PRINT_ANY, "base_time", "\tbase-time %lld", base_time);
+
++ print_lluint(PRINT_ANY, "cycle_time", " cycle-time %lld", cycle_time);
++
++ print_lluint(PRINT_ANY, "cycle_time_extension",
++ " cycle-time-extension %lld", cycle_time_extension);
++
+ print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
+
+ return 0;
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
new file mode 100644
index 0000000..cc265f8
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
@@ -0,0 +1,34 @@
+From 0c672a07e1d5a8068f2323e88a72e5349dacbed9 Mon Sep 17 00:00:00 2001
+From: Kurt Kanzenbach <kurt@linutronix.de>
+Date: Thu, 4 Jul 2019 14:24:27 +0200
+Subject: [PATCH 08/12] utils: Fix get_s64() function
+
+commit c875433b145e33645798ecfe4d99bcb28c80d1e9 upstream.
+
+get_s64() uses internally strtoll() to parse the value out of a given
+string. strtoll() returns a long long. However, the intermediate variable is
+long only which might be 32 bit on some systems. So, fix it.
+
+Signed-off-by: Kurt Kanzenbach <kurt@linutronix.de>
+Signed-off-by: Stephen Hemminger <stephen@networkplumber.org>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ lib/utils.c | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/lib/utils.c b/lib/utils.c
+index be29530f..9c121ce3 100644
+--- a/lib/utils.c
++++ b/lib/utils.c
+@@ -386,7 +386,7 @@ int get_u8(__u8 *val, const char *arg, int base)
+
+ int get_s64(__s64 *val, const char *arg, int base)
+ {
+- long res;
++ long long res;
+ char *ptr;
+
+ errno = 0;
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
new file mode 100644
index 0000000..4f2ffde
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
@@ -0,0 +1,77 @@
+From 7e5c69b7a4733f099ca53aecfafa5dac4a3a002d Mon Sep 17 00:00:00 2001
+From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Date: Thu, 18 Jul 2019 12:55:40 -0700
+Subject: [PATCH 09/12] taprio: Add support for setting flags
+
+commit ee000bf217870b6425849c03b309faa64539ff24 upstream.
+
+This allows a new parameter, flags, to be passed to taprio. Currently, it
+only supports enabling the txtime-assist mode. But, we plan to add
+different modes for taprio (e.g. hardware offloading) and this parameter
+will be useful in enabling those modes.
+
+Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
+Signed-off-by: Vedang Patel <vedang.patel@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ tc/q_taprio.c | 22 ++++++++++++++++++++++
+ 1 file changed, 22 insertions(+)
+
+diff --git a/tc/q_taprio.c b/tc/q_taprio.c
+index 9a69b86b..91e3f27b 100644
+--- a/tc/q_taprio.c
++++ b/tc/q_taprio.c
+@@ -158,6 +158,7 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ __s64 cycle_time_extension = 0;
+ struct list_head sched_entries;
+ struct rtattr *tail, *l;
++ __u32 taprio_flags = 0;
+ __s64 cycle_time = 0;
+ __s64 base_time = 0;
+ int err, idx;
+@@ -280,6 +281,17 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ explain_clockid(*argv);
+ return -1;
+ }
++ } else if (strcmp(*argv, "flags") == 0) {
++ NEXT_ARG();
++ if (taprio_flags) {
++ fprintf(stderr, "taprio: duplicate \"flags\" specification\n");
++ return -1;
++ }
++ if (get_u32(&taprio_flags, *argv, 0)) {
++ PREV_ARG();
++ return -1;
++ }
++
+ } else if (strcmp(*argv, "help") == 0) {
+ explain();
+ return -1;
+@@ -296,6 +308,9 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ if (clockid != CLOCKID_INVALID)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
+
++ if (taprio_flags)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_FLAGS, &taprio_flags, sizeof(taprio_flags));
++
+ if (opt.num_tc > 0)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
+
+@@ -441,6 +456,13 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
+
+ print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
+
++ if (tb[TCA_TAPRIO_ATTR_FLAGS]) {
++ __u32 flags;
++
++ flags = rta_getattr_u32(tb[TCA_TAPRIO_ATTR_FLAGS]);
++ print_0xhex(PRINT_ANY, "flags", " flags %#x", flags);
++ }
++
+ print_schedule(f, tb);
+
+ if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
new file mode 100644
index 0000000..77c9580
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
@@ -0,0 +1,96 @@
+From 1f018de4a624dac26e7c4ea2a6b47a63d1c9c45f Mon Sep 17 00:00:00 2001
+From: Vedang Patel <vedang.patel@intel.com>
+Date: Thu, 18 Jul 2019 12:55:41 -0700
+Subject: [PATCH 10/12] taprio: add support for setting txtime_delay.
+
+commit a5e6ee3b34226f76c8be4b1e3e3ad82212ea4d50 upstream.
+
+This adds support for setting the txtime_delay parameter which is useful
+for the txtime offload mode of taprio.
+
+Signed-off-by: Vedang Patel <vedang.patel@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ tc/q_taprio.c | 37 ++++++++++++++++++++++++++++++-------
+ 1 file changed, 30 insertions(+), 7 deletions(-)
+
+diff --git a/tc/q_taprio.c b/tc/q_taprio.c
+index 91e3f27b..5e498489 100644
+--- a/tc/q_taprio.c
++++ b/tc/q_taprio.c
+@@ -47,13 +47,14 @@ static const struct static_clockid {
+
+ static void explain(void)
+ {
+- fprintf(stderr, "Usage: ... taprio clockid CLOCKID\n");
+- fprintf(stderr, " [num_tc NUMBER] [map P0 P1 ...] ");
+- fprintf(stderr, " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] ");
+- fprintf(stderr, " [ [sched-entry index cmd gate-mask interval] ... ] ");
+- fprintf(stderr, " [base-time time] ");
+- fprintf(stderr, "\nCLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)");
+- fprintf(stderr, "\n");
++ fprintf(stderr,
++ "Usage: ... taprio clockid CLOCKID\n"
++ " [num_tc NUMBER] [map P0 P1 ...] "
++ " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] "
++ " [ [sched-entry index cmd gate-mask interval] ... ] "
++ " [base-time time] [txtime-delay delay]"
++ "\n"
++ "CLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)\n");
+ }
+
+ static void explain_clockid(const char *val)
+@@ -159,6 +160,7 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ struct list_head sched_entries;
+ struct rtattr *tail, *l;
+ __u32 taprio_flags = 0;
++ __u32 txtime_delay = 0;
+ __s64 cycle_time = 0;
+ __s64 base_time = 0;
+ int err, idx;
+@@ -292,6 +294,17 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ return -1;
+ }
+
++ } else if (strcmp(*argv, "txtime-delay") == 0) {
++ NEXT_ARG();
++ if (txtime_delay != 0) {
++ fprintf(stderr, "taprio: duplicate \"txtime-delay\" specification\n");
++ return -1;
++ }
++ if (get_u32(&txtime_delay, *argv, 0)) {
++ PREV_ARG();
++ return -1;
++ }
++
+ } else if (strcmp(*argv, "help") == 0) {
+ explain();
+ return -1;
+@@ -314,6 +327,9 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
+ if (opt.num_tc > 0)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
+
++ if (txtime_delay)
++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_TXTIME_DELAY, &txtime_delay, sizeof(txtime_delay));
++
+ if (base_time)
+ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
+
+@@ -463,6 +479,13 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
+ print_0xhex(PRINT_ANY, "flags", " flags %#x", flags);
+ }
+
++ if (tb[TCA_TAPRIO_ATTR_TXTIME_DELAY]) {
++ __u32 txtime_delay;
++
++ txtime_delay = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_TXTIME_DELAY]);
++ print_uint(PRINT_ANY, "txtime_delay", " txtime delay %d", txtime_delay);
++ }
++
+ print_schedule(f, tb);
+
+ if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
new file mode 100644
index 0000000..a575e2e
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
@@ -0,0 +1,80 @@
+From 5932369560e2ad1deecafa829edd0e89170a3545 Mon Sep 17 00:00:00 2001
+From: Vedang Patel <vedang.patel@intel.com>
+Date: Thu, 18 Jul 2019 12:55:43 -0700
+Subject: [PATCH 11/12] tc: taprio: Update documentation
+
+commit a794d0523711d5ab4530483b9435ba627e07d28b upstream.
+
+Add documentation for the latest options, flags and txtime-delay, to the
+taprio manpage.
+
+This also adds an example to run tc in txtime offload mode.
+
+Signed-off-by: Vedang Patel <vedang.patel@intel.com>
+Signed-off-by: David Ahern <dsahern@gmail.com>
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ man/man8/tc-taprio.8 | 40 ++++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 40 insertions(+)
+
+diff --git a/man/man8/tc-taprio.8 b/man/man8/tc-taprio.8
+index 92055b43..2cb39da3 100644
+--- a/man/man8/tc-taprio.8
++++ b/man/man8/tc-taprio.8
+@@ -112,6 +112,26 @@ means that traffic class 0 is "active" for that schedule entry.
+ long that state defined by <command> and <gate mask> should be held
+ before moving to the next entry.
+
++.TP
++flags
++.br
++Specifies different modes for taprio. Currently, only txtime-assist is
++supported which can be enabled by setting it to 0x1. In this mode, taprio will
++set the transmit timestamp depending on the interval in which the packet needs
++to be transmitted. It will then utililize the
++.BR etf(8)
++qdisc to sort and transmit the packets at the right time. The second example
++can be used as a reference to configure this mode.
++
++.TP
++txtime-delay
++.br
++This parameter is specific to the txtime offload mode. It specifies the maximum
++time a packet might take to reach the network card from the taprio qdisc. The
++value should always be greater than the delta specified in the
++.BR etf(8)
++qdisc.
++
+ .SH EXAMPLES
+
+ The following example shows how an traffic schedule with three traffic
+@@ -137,6 +157,26 @@ reference CLOCK_TAI. The schedule is composed of three entries each of
+ clockid CLOCK_TAI
+ .EE
+
++Following is an example to enable the txtime offload mode in taprio. See
++.BR etf(8)
++for more information about configuring the ETF qdisc.
++
++.EX
++# tc qdisc replace dev eth0 parent root handle 100 taprio \\
++ num_tc 3 \\
++ map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \\
++ queues 1@0 1@0 1@0 \\
++ base-time 1528743495910289987 \\
++ sched-entry S 01 300000 \\
++ sched-entry S 02 300000 \\
++ sched-entry S 04 400000 \\
++ flags 0x1 \\
++ txtime-delay 200000 \\
++ clockid CLOCK_TAI
++
++# tc qdisc replace dev $IFACE parent 100:1 etf skip_skb_check \\
++ offload delta 200000 clockid CLOCK_TAI
++.EE
+
+ .SH AUTHORS
+ Vinicius Costa Gomes <vinicius.gomes@intel.com>
+--
+2.18.1
+
--git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
new file mode 100644
index 0000000..0914b8d
--- /dev/null
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
@@ -0,0 +1,128 @@
+From 3736970b76dc41cd2d76399650709eab6a031807 Mon Sep 17 00:00:00 2001
+From: Murali Karicheri <m-karicheri2@ti.com>
+Date: Thu, 17 Oct 2019 17:50:18 -0400
+Subject: [PATCH 12/12] sync pkt_sched header with kernel version
+
+For picking taprio specific definitions, sync up the pkt_sched.h with
+kernel header.
+
+Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
+---
+ include/uapi/linux/const.h | 31 ++++++++++++++++
+ include/uapi/linux/pkt_sched.h | 64 ++++++++++++++++++++++++++++++++++
+ 2 files changed, 95 insertions(+)
+ create mode 100644 include/uapi/linux/const.h
+
+diff --git a/include/uapi/linux/const.h b/include/uapi/linux/const.h
+new file mode 100644
+index 00000000..fd885c79
+--- /dev/null
++++ b/include/uapi/linux/const.h
+@@ -0,0 +1,31 @@
++/* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
++/* const.h: Macros for dealing with constants. */
++
++#ifndef _LINUX_CONST_H
++#define _LINUX_CONST_H
++
++/* Some constant macros are used in both assembler and
++ * C code. Therefore we cannot annotate them always with
++ * 'UL' and other type specifiers unilaterally. We
++ * use the following macros to deal with this.
++ *
++ * Similarly, _AT() will cast an expression with a type in C, but
++ * leave it unchanged in asm.
++ */
++
++#ifdef __ASSEMBLY__
++#define _AC(X,Y) X
++#define _AT(T,X) X
++#else
++#define __AC(X,Y) (X##Y)
++#define _AC(X,Y) __AC(X,Y)
++#define _AT(T,X) ((T)(X))
++#endif
++
++#define _UL(x) (_AC(x, UL))
++#define _ULL(x) (_AC(x, ULL))
++
++#define _BITUL(x) (_UL(1) << (x))
++#define _BITULL(x) (_ULL(1) << (x))
++
++#endif /* _LINUX_CONST_H */
+diff --git a/include/uapi/linux/pkt_sched.h b/include/uapi/linux/pkt_sched.h
+index 8975fd1a..9408fb43 100644
+--- a/include/uapi/linux/pkt_sched.h
++++ b/include/uapi/linux/pkt_sched.h
+@@ -1084,4 +1084,68 @@ enum {
+ CAKE_ATM_MAX
+ };
+
++
++/* TAPRIO */
++enum {
++ TC_TAPRIO_CMD_SET_GATES = 0x00,
++ TC_TAPRIO_CMD_SET_AND_HOLD = 0x01,
++ TC_TAPRIO_CMD_SET_AND_RELEASE = 0x02,
++};
++
++enum {
++ TCA_TAPRIO_SCHED_ENTRY_UNSPEC,
++ TCA_TAPRIO_SCHED_ENTRY_INDEX, /* u32 */
++ TCA_TAPRIO_SCHED_ENTRY_CMD, /* u8 */
++ TCA_TAPRIO_SCHED_ENTRY_GATE_MASK, /* u32 */
++ TCA_TAPRIO_SCHED_ENTRY_INTERVAL, /* u32 */
++ __TCA_TAPRIO_SCHED_ENTRY_MAX,
++};
++#define TCA_TAPRIO_SCHED_ENTRY_MAX (__TCA_TAPRIO_SCHED_ENTRY_MAX - 1)
++
++/* The format for schedule entry list is:
++ * [TCA_TAPRIO_SCHED_ENTRY_LIST]
++ * [TCA_TAPRIO_SCHED_ENTRY]
++ * [TCA_TAPRIO_SCHED_ENTRY_CMD]
++ * [TCA_TAPRIO_SCHED_ENTRY_GATES]
++ * [TCA_TAPRIO_SCHED_ENTRY_INTERVAL]
++ */
++enum {
++ TCA_TAPRIO_SCHED_UNSPEC,
++ TCA_TAPRIO_SCHED_ENTRY,
++ __TCA_TAPRIO_SCHED_MAX,
++};
++
++#define TCA_TAPRIO_SCHED_MAX (__TCA_TAPRIO_SCHED_MAX - 1)
++
++/* The format for the admin sched (dump only):
++ * [TCA_TAPRIO_SCHED_ADMIN_SCHED]
++ * [TCA_TAPRIO_ATTR_SCHED_BASE_TIME]
++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]
++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY]
++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_CMD]
++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_GATES]
++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_INTERVAL]
++ */
++
++#define TCA_TAPRIO_ATTR_FLAG_TXTIME_ASSIST BIT(0)
++#define TCA_TAPRIO_ATTR_FLAG_FULL_OFFLOAD BIT(1)
++
++enum {
++ TCA_TAPRIO_ATTR_UNSPEC,
++ TCA_TAPRIO_ATTR_PRIOMAP, /* struct tc_mqprio_qopt */
++ TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST, /* nested of entry */
++ TCA_TAPRIO_ATTR_SCHED_BASE_TIME, /* s64 */
++ TCA_TAPRIO_ATTR_SCHED_SINGLE_ENTRY, /* single entry */
++ TCA_TAPRIO_ATTR_SCHED_CLOCKID, /* s32 */
++ TCA_TAPRIO_PAD,
++ TCA_TAPRIO_ATTR_ADMIN_SCHED, /* The admin sched, only used in dump */
++ TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME, /* s64 */
++ TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION, /* s64 */
++ TCA_TAPRIO_ATTR_FLAGS, /* u32 */
++ TCA_TAPRIO_ATTR_TXTIME_DELAY, /* u32 */
++ __TCA_TAPRIO_ATTR_MAX,
++};
++
++#define TCA_TAPRIO_ATTR_MAX (__TCA_TAPRIO_ATTR_MAX - 1)
++
+ #endif
+--
+2.18.1
+
diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend b/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
index 2100f49..7fa33f6 100644
--- a/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
+++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
@@ -1,4 +1,4 @@
-PR_append = ".arago5"
+PR_append = ".arago6"
FILESEXTRAPATHS_prepend := "${THISDIR}/${PN}:"
@@ -7,4 +7,16 @@ SRC_URI_append = " \
file://0002-hsr-prp-introduce-common-definitions-for-netlink-int.patch \
file://0003-hsr-prp-refactor-common-code.patch \
file://0004-hsr-prp-add-support-for-vlan-tagged-supervision-fram.patch \
+ file://0001-utils-Implement-get_s64.patch \
+ file://0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch \
+ file://0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch \
+ file://0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch \
+ file://0005-taprio-Add-manpage-for-tc-taprio-8.patch \
+ file://0006-taprio-Add-support-for-changing-schedules.patch \
+ file://0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch \
+ file://0008-utils-Fix-get_s64-function.patch \
+ file://0009-taprio-Add-support-for-setting-flags.patch \
+ file://0010-taprio-add-support-for-setting-txtime_delay.patch \
+ file://0011-tc-taprio-Update-documentation.patch \
+ file://0012-sync-pkt_sched-header-with-kernel-version.patch \
"
--
1.9.1
^ permalink raw reply related [flat|nested] 2+ messages in thread* Re: [master/thud][PATCH] iproute2: soft taprio: add patches for taprio
2019-10-28 19:13 [master/thud][PATCH] iproute2: soft taprio: add patches for taprio Jacob Stiffler
@ 2019-10-29 21:04 ` Denys Dmytriyenko
0 siblings, 0 replies; 2+ messages in thread
From: Denys Dmytriyenko @ 2019-10-29 21:04 UTC (permalink / raw)
To: Jacob Stiffler; +Cc: meta-arago
Patches being added should have:
Upstream-Status: Backport
--
Denys
On Mon, Oct 28, 2019 at 03:13:50PM -0400, Jacob Stiffler wrote:
> Signed-off-by: Jacob Stiffler <j-stiffler@ti.com>
> ---
> .../iproute2/0001-utils-Implement-get_s64.patch | 64 +++
> ...-helper-to-retrieve-a-__s64-from-a-netlin.patch | 39 ++
> ...Add-helper-for-getting-a-__s32-from-netli.patch | 36 ++
> ...port-for-configuring-the-taprio-scheduler.patch | 488 +++++++++++++++++++++
> .../0005-taprio-Add-manpage-for-tc-taprio-8.patch | 168 +++++++
> ...taprio-Add-support-for-changing-schedules.patch | 150 +++++++
> ...support-for-cycle_time-and-cycle_time_ext.patch | 147 +++++++
> .../iproute2/0008-utils-Fix-get_s64-function.patch | 34 ++
> ...0009-taprio-Add-support-for-setting-flags.patch | 77 ++++
> ...prio-add-support-for-setting-txtime_delay.patch | 96 ++++
> .../0011-tc-taprio-Update-documentation.patch | 80 ++++
> ...sync-pkt_sched-header-with-kernel-version.patch | 128 ++++++
> .../iproute2/iproute2_4.19.0.bbappend | 14 +-
> 13 files changed, 1520 insertions(+), 1 deletion(-)
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
> create mode 100644 meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
>
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
> new file mode 100644
> index 0000000..a0d5a12
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0001-utils-Implement-get_s64.patch
> @@ -0,0 +1,64 @@
> +From 7e4397dff47438be65fdf90dc4e51b763797d201 Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Fri, 5 Oct 2018 16:25:17 -0700
> +Subject: [PATCH 01/12] utils: Implement get_s64()
> +
> +commit a066bac8a2775bc43d54ae7173057f75f543c44b upstream.
> +
> +Add this helper to read signed 64-bit integers from a string.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + include/utils.h | 1 +
> + lib/utils.c | 21 +++++++++++++++++++++
> + 2 files changed, 22 insertions(+)
> +
> +diff --git a/include/utils.h b/include/utils.h
> +index 8cb4349e..58574a05 100644
> +--- a/include/utils.h
> ++++ b/include/utils.h
> +@@ -139,6 +139,7 @@ int get_time_rtt(unsigned *val, const char *arg, int *raw);
> + #define get_byte get_u8
> + #define get_ushort get_u16
> + #define get_short get_s16
> ++int get_s64(__s64 *val, const char *arg, int base);
> + int get_u64(__u64 *val, const char *arg, int base);
> + int get_u32(__u32 *val, const char *arg, int base);
> + int get_s32(__s32 *val, const char *arg, int base);
> +diff --git a/lib/utils.c b/lib/utils.c
> +index ad27f78c..be29530f 100644
> +--- a/lib/utils.c
> ++++ b/lib/utils.c
> +@@ -384,6 +384,27 @@ int get_u8(__u8 *val, const char *arg, int base)
> + return 0;
> + }
> +
> ++int get_s64(__s64 *val, const char *arg, int base)
> ++{
> ++ long res;
> ++ char *ptr;
> ++
> ++ errno = 0;
> ++
> ++ if (!arg || !*arg)
> ++ return -1;
> ++ res = strtoll(arg, &ptr, base);
> ++ if (!ptr || ptr == arg || *ptr)
> ++ return -1;
> ++ if ((res == LLONG_MIN || res == LLONG_MAX) && errno == ERANGE)
> ++ return -1;
> ++ if (res > INT64_MAX || res < INT64_MIN)
> ++ return -1;
> ++
> ++ *val = res;
> ++ return 0;
> ++}
> ++
> + int get_s32(__s32 *val, const char *arg, int base)
> + {
> + long res;
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
> new file mode 100644
> index 0000000..b01e11d
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch
> @@ -0,0 +1,39 @@
> +From 6d0bcdd9d0283768798227f4046414ed7da42047 Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Fri, 5 Oct 2018 16:25:18 -0700
> +Subject: [PATCH 02/12] include: Add helper to retrieve a __s64 from a netlink
> + msg
> +
> +commit de63cd90444ac9fdf238f950c16cafe351846691 upstream.
> +
> +This allows signed 64-bit integers to be retrieved from a netlink
> +message.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + include/libnetlink.h | 7 +++++++
> + 1 file changed, 7 insertions(+)
> +
> +diff --git a/include/libnetlink.h b/include/libnetlink.h
> +index 9d9249e6..ffc49e56 100644
> +--- a/include/libnetlink.h
> ++++ b/include/libnetlink.h
> +@@ -185,6 +185,13 @@ static inline __u64 rta_getattr_u64(const struct rtattr *rta)
> + memcpy(&tmp, RTA_DATA(rta), sizeof(__u64));
> + return tmp;
> + }
> ++static inline __s64 rta_getattr_s64(const struct rtattr *rta)
> ++{
> ++ __s64 tmp;
> ++
> ++ memcpy(&tmp, RTA_DATA(rta), sizeof(tmp));
> ++ return tmp;
> ++}
> + static inline const char *rta_getattr_str(const struct rtattr *rta)
> + {
> + return (const char *)RTA_DATA(rta);
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
> new file mode 100644
> index 0000000..1718c23
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch
> @@ -0,0 +1,36 @@
> +From ca37dce0e9c50645a3473dc942a33478eb79378d Mon Sep 17 00:00:00 2001
> +From: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
> +Date: Fri, 5 Oct 2018 16:25:19 -0700
> +Subject: [PATCH 03/12] libnetlink: Add helper for getting a __s32 from netlink
> + msgs
> +
> +commit d791f3ad869659da4b151eded060840a88d9656a upstream.
> +
> +This function retrieves a signed 32-bit integer from a netlink message
> +and returns it.
> +
> +Signed-off-by: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + include/libnetlink.h | 4 ++++
> + 1 file changed, 4 insertions(+)
> +
> +diff --git a/include/libnetlink.h b/include/libnetlink.h
> +index ffc49e56..c44c3c72 100644
> +--- a/include/libnetlink.h
> ++++ b/include/libnetlink.h
> +@@ -185,6 +185,10 @@ static inline __u64 rta_getattr_u64(const struct rtattr *rta)
> + memcpy(&tmp, RTA_DATA(rta), sizeof(__u64));
> + return tmp;
> + }
> ++static inline __s32 rta_getattr_s32(const struct rtattr *rta)
> ++{
> ++ return *(__s32 *)RTA_DATA(rta);
> ++}
> + static inline __s64 rta_getattr_s64(const struct rtattr *rta)
> + {
> + __s64 tmp;
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
> new file mode 100644
> index 0000000..7cbf027
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch
> @@ -0,0 +1,488 @@
> +From b53ed00cc819a9d57983f48a9fe8d02ec3b50fca Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Fri, 5 Oct 2018 16:25:21 -0700
> +Subject: [PATCH 04/12] tc: Add support for configuring the taprio scheduler
> +
> +commit 0dd16449356f7ba88e5374392b577f0504b3f025 upstream.
> +
> +This traffic scheduler allows traffic classes states (transmission
> +allowed/not allowed, in the simplest case) to be scheduled, according
> +to a pre-generated time sequence. This is the basis of the IEEE
> +802.1Qbv specification.
> +
> +Example configuration:
> +
> +tc qdisc replace dev enp3s0 parent root handle 100 taprio \
> + num_tc 3 \
> + map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \
> + queues 1@0 1@1 2@2 \
> + base-time 1528743495910289987 \
> + sched-entry S 01 300000 \
> + sched-entry S 02 300000 \
> + sched-entry S 04 300000 \
> + clockid CLOCK_TAI
> +
> +The configuration format is similar to mqprio. The main difference is
> +the presence of a schedule, built by multiple "sched-entry"
> +definitions, each entry has the following format:
> +
> + sched-entry <CMD> <GATE MASK> <INTERVAL>
> +
> +The only supported <CMD> is "S", which means "SetGateStates",
> +following the IEEE 802.1Qbv-2015 definition (Table 8-6). <GATE MASK>
> +is a bitmask where each bit is a associated with a traffic class, so
> +bit 0 (the least significant bit) being "on" means that traffic class
> +0 is "active" for that schedule entry. <INTERVAL> is a time duration
> +in nanoseconds that specifies for how long that state defined by <CMD>
> +and <GATE MASK> should be held before moving to the next entry.
> +
> +This schedule is circular, that is, after the last entry is executed
> +it starts from the first one, indefinitely.
> +
> +The other parameters can be defined as follows:
> +
> + - base-time: specifies the instant when the schedule starts, if
> + 'base-time' is a time in the past, the schedule will start at
> +
> + base-time + (N * cycle-time)
> +
> + where N is the smallest integer so the resulting time is greater
> + than "now", and "cycle-time" is the sum of all the intervals of the
> + entries in the schedule;
> +
> + - clockid: specifies the reference clock to be used;
> +
> +The parameters should be similar to what the IEEE 802.1Q family of
> +specification defines.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + tc/Makefile | 1 +
> + tc/q_taprio.c | 400 ++++++++++++++++++++++++++++++++++++++++++++++++++
> + 2 files changed, 401 insertions(+)
> + create mode 100644 tc/q_taprio.c
> +
> +diff --git a/tc/Makefile b/tc/Makefile
> +index 5a1a7ff9..25a28284 100644
> +--- a/tc/Makefile
> ++++ b/tc/Makefile
> +@@ -74,6 +74,7 @@ TCMODULES += e_bpf.o
> + TCMODULES += f_matchall.o
> + TCMODULES += q_cbs.o
> + TCMODULES += q_etf.o
> ++TCMODULES += q_taprio.o
> +
> + TCSO :=
> + ifeq ($(TC_CONFIG_ATM),y)
> +diff --git a/tc/q_taprio.c b/tc/q_taprio.c
> +new file mode 100644
> +index 00000000..562dacb8
> +--- /dev/null
> ++++ b/tc/q_taprio.c
> +@@ -0,0 +1,400 @@
> ++/*
> ++ * q_taprio.c Time Aware Priority Scheduler
> ++ *
> ++ * This program is free software; you can redistribute it and/or
> ++ * modify it under the terms of the GNU General Public License
> ++ * as published by the Free Software Foundation; either version
> ++ * 2 of the License, or (at your option) any later version.
> ++ *
> ++ * Authors: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> ++ * Jesus Sanchez-Palencia <jesus.sanchez-palencia@intel.com>
> ++ */
> ++
> ++#include <stdio.h>
> ++#include <stdlib.h>
> ++#include <unistd.h>
> ++#include <syslog.h>
> ++#include <fcntl.h>
> ++#include <inttypes.h>
> ++#include <sys/socket.h>
> ++#include <netinet/in.h>
> ++#include <arpa/inet.h>
> ++#include <string.h>
> ++
> ++#include "utils.h"
> ++#include "tc_util.h"
> ++#include "list.h"
> ++
> ++struct sched_entry {
> ++ struct list_head list;
> ++ uint32_t index;
> ++ uint32_t interval;
> ++ uint32_t gatemask;
> ++ uint8_t cmd;
> ++};
> ++
> ++#define CLOCKID_INVALID (-1)
> ++static const struct static_clockid {
> ++ const char *name;
> ++ clockid_t clockid;
> ++} clockids_sysv[] = {
> ++ { "REALTIME", CLOCK_REALTIME },
> ++ { "TAI", CLOCK_TAI },
> ++ { "BOOTTIME", CLOCK_BOOTTIME },
> ++ { "MONOTONIC", CLOCK_MONOTONIC },
> ++ { NULL }
> ++};
> ++
> ++static void explain(void)
> ++{
> ++ fprintf(stderr, "Usage: ... taprio clockid CLOCKID\n");
> ++ fprintf(stderr, " [num_tc NUMBER] [map P0 P1 ...] ");
> ++ fprintf(stderr, " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] ");
> ++ fprintf(stderr, " [ [sched-entry index cmd gate-mask interval] ... ] ");
> ++ fprintf(stderr, " [base-time time] ");
> ++ fprintf(stderr, "\nCLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)");
> ++ fprintf(stderr, "\n");
> ++}
> ++
> ++static void explain_clockid(const char *val)
> ++{
> ++ fprintf(stderr, "taprio: illegal value for \"clockid\": \"%s\".\n", val);
> ++ fprintf(stderr, "It must be a valid SYS-V id (i.e. CLOCK_TAI)\n");
> ++}
> ++
> ++static int get_clockid(__s32 *val, const char *arg)
> ++{
> ++ const struct static_clockid *c;
> ++
> ++ /* Drop the CLOCK_ prefix if that is being used. */
> ++ if (strcasestr(arg, "CLOCK_") != NULL)
> ++ arg += sizeof("CLOCK_") - 1;
> ++
> ++ for (c = clockids_sysv; c->name; c++) {
> ++ if (strcasecmp(c->name, arg) == 0) {
> ++ *val = c->clockid;
> ++
> ++ return 0;
> ++ }
> ++ }
> ++
> ++ return -1;
> ++}
> ++
> ++static const char* get_clock_name(clockid_t clockid)
> ++{
> ++ const struct static_clockid *c;
> ++
> ++ for (c = clockids_sysv; c->name; c++) {
> ++ if (clockid == c->clockid)
> ++ return c->name;
> ++ }
> ++
> ++ return "invalid";
> ++}
> ++
> ++static const char *entry_cmd_to_str(__u8 cmd)
> ++{
> ++ switch (cmd) {
> ++ case TC_TAPRIO_CMD_SET_GATES:
> ++ return "S";
> ++ default:
> ++ return "Invalid";
> ++ }
> ++}
> ++
> ++static int str_to_entry_cmd(const char *str)
> ++{
> ++ if (strcmp(str, "S") == 0)
> ++ return TC_TAPRIO_CMD_SET_GATES;
> ++
> ++ return -1;
> ++}
> ++
> ++static int add_sched_list(struct list_head *sched_entries, struct nlmsghdr *n)
> ++{
> ++ struct sched_entry *e;
> ++
> ++ list_for_each_entry(e, sched_entries, list) {
> ++ struct rtattr *a;
> ++
> ++ a = addattr_nest(n, 1024, TCA_TAPRIO_SCHED_ENTRY);
> ++
> ++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_CMD, &e->cmd, sizeof(e->cmd));
> ++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_GATE_MASK, &e->gatemask, sizeof(e->gatemask));
> ++ addattr_l(n, 1024, TCA_TAPRIO_SCHED_ENTRY_INTERVAL, &e->interval, sizeof(e->interval));
> ++
> ++ addattr_nest_end(n, a);
> ++ }
> ++
> ++ return 0;
> ++}
> ++
> ++static void explain_sched_entry(void)
> ++{
> ++ fprintf(stderr, "Usage: ... taprio ... sched-entry <cmd> <gate mask> <interval>\n");
> ++}
> ++
> ++static struct sched_entry *create_entry(uint32_t gatemask, uint32_t interval, uint8_t cmd)
> ++{
> ++ struct sched_entry *e;
> ++
> ++ e = calloc(1, sizeof(*e));
> ++ if (!e)
> ++ return NULL;
> ++
> ++ e->gatemask = gatemask;
> ++ e->interval = interval;
> ++ e->cmd = cmd;
> ++
> ++ return e;
> ++}
> ++
> ++static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> ++ char **argv, struct nlmsghdr *n, const char *dev)
> ++{
> ++ __s32 clockid = CLOCKID_INVALID;
> ++ struct tc_mqprio_qopt opt = { };
> ++ struct list_head sched_entries;
> ++ struct rtattr *tail;
> ++ __s64 base_time = 0;
> ++ int err, idx;
> ++
> ++ INIT_LIST_HEAD(&sched_entries);
> ++
> ++ while (argc > 0) {
> ++ idx = 0;
> ++ if (strcmp(*argv, "num_tc") == 0) {
> ++ NEXT_ARG();
> ++ if (get_u8(&opt.num_tc, *argv, 10)) {
> ++ fprintf(stderr, "Illegal \"num_tc\"\n");
> ++ return -1;
> ++ }
> ++ } else if (strcmp(*argv, "map") == 0) {
> ++ while (idx < TC_QOPT_MAX_QUEUE && NEXT_ARG_OK()) {
> ++ NEXT_ARG();
> ++ if (get_u8(&opt.prio_tc_map[idx], *argv, 10)) {
> ++ PREV_ARG();
> ++ break;
> ++ }
> ++ idx++;
> ++ }
> ++ for ( ; idx < TC_QOPT_MAX_QUEUE; idx++)
> ++ opt.prio_tc_map[idx] = 0;
> ++ } else if (strcmp(*argv, "queues") == 0) {
> ++ char *tmp, *tok;
> ++
> ++ while (idx < TC_QOPT_MAX_QUEUE && NEXT_ARG_OK()) {
> ++ NEXT_ARG();
> ++
> ++ tmp = strdup(*argv);
> ++ if (!tmp)
> ++ break;
> ++
> ++ tok = strtok(tmp, "@");
> ++ if (get_u16(&opt.count[idx], tok, 10)) {
> ++ free(tmp);
> ++ PREV_ARG();
> ++ break;
> ++ }
> ++ tok = strtok(NULL, "@");
> ++ if (get_u16(&opt.offset[idx], tok, 10)) {
> ++ free(tmp);
> ++ PREV_ARG();
> ++ break;
> ++ }
> ++ free(tmp);
> ++ idx++;
> ++ }
> ++ } else if (strcmp(*argv, "sched-entry") == 0) {
> ++ uint32_t mask, interval;
> ++ struct sched_entry *e;
> ++ uint8_t cmd;
> ++
> ++ NEXT_ARG();
> ++ err = str_to_entry_cmd(*argv);
> ++ if (err < 0) {
> ++ explain_sched_entry();
> ++ return -1;
> ++ }
> ++ cmd = err;
> ++
> ++ NEXT_ARG();
> ++ if (get_u32(&mask, *argv, 16)) {
> ++ explain_sched_entry();
> ++ return -1;
> ++ }
> ++
> ++ NEXT_ARG();
> ++ if (get_u32(&interval, *argv, 0)) {
> ++ explain_sched_entry();
> ++ return -1;
> ++ }
> ++
> ++ e = create_entry(mask, interval, cmd);
> ++ if (!e) {
> ++ fprintf(stderr, "taprio: not enough memory for new schedule entry\n");
> ++ return -1;
> ++ }
> ++
> ++ list_add_tail(&e->list, &sched_entries);
> ++
> ++ } else if (strcmp(*argv, "base-time") == 0) {
> ++ NEXT_ARG();
> ++ if (get_s64(&base_time, *argv, 10)) {
> ++ PREV_ARG();
> ++ break;
> ++ }
> ++ } else if (strcmp(*argv, "clockid") == 0) {
> ++ NEXT_ARG();
> ++ if (clockid != CLOCKID_INVALID) {
> ++ fprintf(stderr, "taprio: duplicate \"clockid\" specification\n");
> ++ return -1;
> ++ }
> ++ if (get_clockid(&clockid, *argv)) {
> ++ explain_clockid(*argv);
> ++ return -1;
> ++ }
> ++ } else if (strcmp(*argv, "help") == 0) {
> ++ explain();
> ++ return -1;
> ++ } else {
> ++ fprintf(stderr, "Unknown argument\n");
> ++ return -1;
> ++ }
> ++ argc--; argv++;
> ++ }
> ++
> ++ tail = NLMSG_TAIL(n);
> ++ addattr_l(n, 1024, TCA_OPTIONS, NULL, 0);
> ++
> ++ if (opt.num_tc > 0)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
> ++
> ++ if (base_time)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
> ++
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
> ++
> ++ if (!list_empty(&sched_entries)) {
> ++ struct rtattr *entry_list;
> ++ entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
> ++
> ++ err = add_sched_list(&sched_entries, n);
> ++ if (err < 0) {
> ++ fprintf(stderr, "Could not add schedule to netlink message\n");
> ++ return -1;
> ++ }
> ++
> ++ addattr_nest_end(n, entry_list);
> ++ }
> ++
> ++ tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
> ++
> ++ return 0;
> ++}
> ++
> ++static int print_sched_list(FILE *f, struct rtattr *list)
> ++{
> ++ struct rtattr *item;
> ++ int rem;
> ++
> ++ if (list == NULL)
> ++ return 0;
> ++
> ++ rem = RTA_PAYLOAD(list);
> ++
> ++ open_json_array(PRINT_JSON, "schedule");
> ++
> ++ for (item = RTA_DATA(list); RTA_OK(item, rem); item = RTA_NEXT(item, rem)) {
> ++ struct rtattr *tb[TCA_TAPRIO_SCHED_ENTRY_MAX + 1];
> ++ __u32 index = 0, gatemask = 0, interval = 0;
> ++ __u8 command = 0;
> ++
> ++ parse_rtattr_nested(tb, TCA_TAPRIO_SCHED_ENTRY_MAX, item);
> ++
> ++ if (tb[TCA_TAPRIO_SCHED_ENTRY_INDEX])
> ++ index = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_INDEX]);
> ++
> ++ if (tb[TCA_TAPRIO_SCHED_ENTRY_CMD])
> ++ command = rta_getattr_u8(tb[TCA_TAPRIO_SCHED_ENTRY_CMD]);
> ++
> ++ if (tb[TCA_TAPRIO_SCHED_ENTRY_GATE_MASK])
> ++ gatemask = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_GATE_MASK]);
> ++
> ++ if (tb[TCA_TAPRIO_SCHED_ENTRY_INTERVAL])
> ++ interval = rta_getattr_u32(tb[TCA_TAPRIO_SCHED_ENTRY_INTERVAL]);
> ++
> ++ open_json_object(NULL);
> ++ print_uint(PRINT_ANY, "index", "\tindex %u", index);
> ++ print_string(PRINT_ANY, "cmd", " cmd %s", entry_cmd_to_str(command));
> ++ print_0xhex(PRINT_ANY, "gatemask", " gatemask %#x", gatemask);
> ++ print_uint(PRINT_ANY, "interval", " interval %u", interval);
> ++ close_json_object();
> ++
> ++ print_string(PRINT_FP, NULL, "%s", _SL_);
> ++ }
> ++
> ++ close_json_array(PRINT_ANY, "");
> ++
> ++ return 0;
> ++}
> ++
> ++static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
> ++{
> ++ struct rtattr *tb[TCA_TAPRIO_ATTR_MAX + 1];
> ++ struct tc_mqprio_qopt *qopt = 0;
> ++ __s32 clockid = CLOCKID_INVALID;
> ++ __s64 base_time = 0;
> ++ int i;
> ++
> ++ if (opt == NULL)
> ++ return 0;
> ++
> ++ parse_rtattr_nested(tb, TCA_TAPRIO_ATTR_MAX, opt);
> ++
> ++ if (tb[TCA_TAPRIO_ATTR_PRIOMAP] == NULL)
> ++ return -1;
> ++
> ++ qopt = RTA_DATA(tb[TCA_TAPRIO_ATTR_PRIOMAP]);
> ++
> ++ print_uint(PRINT_ANY, "tc", "tc %u ", qopt->num_tc);
> ++
> ++ open_json_array(PRINT_ANY, "map");
> ++ for (i = 0; i <= TC_PRIO_MAX; i++)
> ++ print_uint(PRINT_ANY, NULL, " %u", qopt->prio_tc_map[i]);
> ++ close_json_array(PRINT_ANY, "");
> ++
> ++ print_string(PRINT_FP, NULL, "%s", _SL_);
> ++
> ++ open_json_array(PRINT_ANY, "queues");
> ++ for (i = 0; i < qopt->num_tc; i++) {
> ++ open_json_object(NULL);
> ++ print_uint(PRINT_ANY, "offset", " offset %u", qopt->offset[i]);
> ++ print_uint(PRINT_ANY, "count", " count %u", qopt->count[i]);
> ++ close_json_object();
> ++ }
> ++ close_json_array(PRINT_ANY, "");
> ++
> ++ print_string(PRINT_FP, NULL, "%s", _SL_);
> ++
> ++ if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
> ++ base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
> ++
> ++ if (tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID])
> ++ clockid = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID]);
> ++
> ++ print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
> ++
> ++ print_lluint(PRINT_ANY, "base_time", " base-time %lld", base_time);
> ++
> ++ print_string(PRINT_FP, NULL, "%s", _SL_);
> ++
> ++ return print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
> ++}
> ++
> ++struct qdisc_util taprio_qdisc_util = {
> ++ .id = "taprio",
> ++ .parse_qopt = taprio_parse_opt,
> ++ .print_qopt = taprio_print_opt,
> ++};
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
> new file mode 100644
> index 0000000..a8bbcd0
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0005-taprio-Add-manpage-for-tc-taprio-8.patch
> @@ -0,0 +1,168 @@
> +From b21190927e151761f138805cf3c208f8d28e8314 Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Fri, 5 Oct 2018 16:25:22 -0700
> +Subject: [PATCH 05/12] taprio: Add manpage for tc-taprio(8)
> +
> +commit 579acb4bc52f84c629df5fcd2f9a054f41b48c57 upstream.
> +
> +This documents the parameters and provides an example of usage.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + man/man8/tc-taprio.8 | 142 +++++++++++++++++++++++++++++++++++++++++++
> + 1 file changed, 142 insertions(+)
> + create mode 100644 man/man8/tc-taprio.8
> +
> +diff --git a/man/man8/tc-taprio.8 b/man/man8/tc-taprio.8
> +new file mode 100644
> +index 00000000..92055b43
> +--- /dev/null
> ++++ b/man/man8/tc-taprio.8
> +@@ -0,0 +1,142 @@
> ++.TH TAPRIO 8 "25 Sept 2018" "iproute2" "Linux"
> ++.SH NAME
> ++TAPRIO \- Time Aware Priority Shaper
> ++.SH SYNOPSIS
> ++.B tc qdisc ... dev
> ++dev
> ++.B parent
> ++classid
> ++.B [ handle
> ++major:
> ++.B ] taprio num_tc
> ++tcs
> ++.ti +8
> ++.B map
> ++P0 P1 P2 ...
> ++.B queues
> ++count1@offset1 count2@offset2 ...
> ++.ti +8
> ++.B base-time
> ++base-time
> ++.B clockid
> ++clockid
> ++.ti +8
> ++.B sched-entry
> ++<command 1> <gate mask 1> <interval 1>
> ++.ti +8
> ++.B sched-entry
> ++<command 2> <gate mask 2> <interval 2>
> ++.ti +8
> ++.B sched-entry
> ++<command 3> <gate mask 3> <interval 3>
> ++.ti +8
> ++.B sched-entry
> ++<command N> <gate mask N> <interval N>
> ++
> ++.SH DESCRIPTION
> ++The TAPRIO qdisc implements a simplified version of the scheduling
> ++state machine defined by IEEE 802.1Q-2018 Section 8.6.9, which allows
> ++configuration of a sequence of gate states, where each gate state
> ++allows outgoing traffic for a subset (potentially empty) of traffic
> ++classes.
> ++
> ++How traffic is mapped to different hardware queues is similar to
> ++.BR mqprio(8)
> ++and so the
> ++.B map
> ++and
> ++.Q queues
> ++parameters have the same meaning.
> ++
> ++The other parameters specify the schedule, and at what point in time
> ++it should start (it can behave as the schedule started in the past).
> ++
> ++.SH PARAMETERS
> ++.TP
> ++num_tc
> ++.BR
> ++Number of traffic classes to use. Up to 16 classes supported.
> ++
> ++.TP
> ++map
> ++.br
> ++The priority to traffic class map. Maps priorities 0..15 to a specified
> ++traffic class. See
> ++.BR mqprio(8)
> ++for more details.
> ++
> ++.TP
> ++queues
> ++.br
> ++Provide count and offset of queue range for each traffic class. In the
> ++format,
> ++.B count@offset.
> ++Queue ranges for each traffic classes cannot overlap and must be a
> ++contiguous range of queues.
> ++
> ++.TP
> ++base-time
> ++.br
> ++Specifies the instant in nanoseconds, using the reference of
> ++.B clockid,
> ++defining the time when the schedule starts. If 'base-time' is a time
> ++in the past, the schedule will start at
> ++
> ++base-time + (N * cycle-time)
> ++
> ++where N is the smallest integer so the resulting time is greater than
> ++"now", and "cycle-time" is the sum of all the intervals of the entries
> ++in the schedule;
> ++
> ++.TP
> ++clockid
> ++.br
> ++Specifies the clock to be used by qdisc's internal timer for measuring
> ++time and scheduling events.
> ++
> ++.TP
> ++sched-entry
> ++.br
> ++There may multiple
> ++.B sched-entry
> ++parameters in a single schedule. Each one has the
> ++
> ++sched-entry <command> <gatemask> <interval>
> ++
> ++format. The only supported <command> is "S", which
> ++means "SetGateStates", following the IEEE 802.1Q-2018 definition
> ++(Table 8-7). <gate mask> is a bitmask where each bit is a associated
> ++with a traffic class, so bit 0 (the least significant bit) being "on"
> ++means that traffic class 0 is "active" for that schedule entry.
> ++<interval> is a time duration, in nanoseconds, that specifies for how
> ++long that state defined by <command> and <gate mask> should be held
> ++before moving to the next entry.
> ++
> ++.SH EXAMPLES
> ++
> ++The following example shows how an traffic schedule with three traffic
> ++classes ("num_tc 3"), which are separated different traffic classes,
> ++we are going to call these TC 0, TC 1 and TC 2. We could read the
> ++"map" parameter below as: traffic with priority 3 is classified as TC
> ++0, priority 2 is classified as TC 1 and the rest is classified as TC
> ++2.
> ++
> ++The schedule will start at instant 1528743495910289987 using the
> ++reference CLOCK_TAI. The schedule is composed of three entries each of
> ++300us duration.
> ++
> ++.EX
> ++# tc qdisc replace dev eth0 parent root handle 100 taprio \\
> ++ num_tc 3 \\
> ++ map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \\
> ++ queues 1@0 1@1 2@2 \\
> ++ base-time 1528743495910289987 \\
> ++ sched-entry S 01 300000 \\
> ++ sched-entry S 02 300000 \\
> ++ sched-entry S 04 300000 \\
> ++ clockid CLOCK_TAI
> ++.EE
> ++
> ++
> ++.SH AUTHORS
> ++Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
> new file mode 100644
> index 0000000..f0dd3db
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0006-taprio-Add-support-for-changing-schedules.patch
> @@ -0,0 +1,150 @@
> +From 3a650c67b63e502989fccdabf8c02a575bdf2116 Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Mon, 29 Apr 2019 15:52:18 -0700
> +Subject: [PATCH 06/12] taprio: Add support for changing schedules
> +
> +commit 602fae856d80bbaa365fd0421e3f2c2417ea804f upstream.
> +
> +This allows for a new schedule to be specified during runtime, without
> +removing the current one.
> +
> +For that, the semantics of the 'tc qdisc change' operation in the
> +context of taprio is that if "change" is called and there is a running
> +schedule, a new schedule is created and the base-time (let's call it
> +X) of this new schedule is used so at instant X, it becomes the
> +"current" schedule. So, in short, "change" doesn't change the current
> +schedule, it creates a new one and sets it up to it becomes the
> +current one at some point.
> +
> +In IEEE 802.1Q terms, it means that we have support for the
> +"Oper" (current and read-only) and "Admin" (future and mutable)
> +schedules.
> +
> +Example of creating the first schedule, then adding a new one:
> +
> +(1)
> +tc qdisc add dev IFACE parent root handle 100 taprio \
> + num_tc 1 \
> + map 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 \
> + queues 1@0 \
> + sched-entry S 0x1 1000000 \
> + sched-entry S 0x0 2000000 \
> + sched-entry S 0x1 3000000 \
> + sched-entry S 0x0 4000000 \
> + base-time 100000000 \
> + clockid CLOCK_TAI
> +
> +(2)
> +tc qdisc change dev IFACE parent root handle 100 taprio \
> + base-time 7500000000000 \
> + sched-entry S 0x0 5000000 \
> + sched-entry S 0x1 5000000 \
> +
> +It was necessary to fix a bug, so the clockid doesn't need to be
> +specified when changing the schedule.
> +
> +Most of the changes are related to make it easier to reuse the same
> +function for printing the "admin" and "oper" schedules.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + tc/q_taprio.c | 42 +++++++++++++++++++++++++++++++++---------
> + 1 file changed, 33 insertions(+), 9 deletions(-)
> +
> +diff --git a/tc/q_taprio.c b/tc/q_taprio.c
> +index 562dacb8..20804fc2 100644
> +--- a/tc/q_taprio.c
> ++++ b/tc/q_taprio.c
> +@@ -268,14 +268,15 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + tail = NLMSG_TAIL(n);
> + addattr_l(n, 1024, TCA_OPTIONS, NULL, 0);
> +
> ++ if (clockid != CLOCKID_INVALID)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
> ++
> + if (opt.num_tc > 0)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
> +
> + if (base_time)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
> +
> +- addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
> +-
> + if (!list_empty(&sched_entries)) {
> + struct rtattr *entry_list;
> + entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
> +@@ -306,6 +307,8 @@ static int print_sched_list(FILE *f, struct rtattr *list)
> +
> + open_json_array(PRINT_JSON, "schedule");
> +
> ++ print_string(PRINT_FP, NULL, "%s", _SL_);
> ++
> + for (item = RTA_DATA(list); RTA_OK(item, rem); item = RTA_NEXT(item, rem)) {
> + struct rtattr *tb[TCA_TAPRIO_SCHED_ENTRY_MAX + 1];
> + __u32 index = 0, gatemask = 0, interval = 0;
> +@@ -340,12 +343,25 @@ static int print_sched_list(FILE *f, struct rtattr *list)
> + return 0;
> + }
> +
> ++static int print_schedule(FILE *f, struct rtattr **tb)
> ++{
> ++ int64_t base_time = 0;
> ++
> ++ if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
> ++ base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
> ++
> ++ print_lluint(PRINT_ANY, "base_time", "\tbase-time %lld", base_time);
> ++
> ++ print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
> ++
> ++ return 0;
> ++}
> ++
> + static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
> + {
> + struct rtattr *tb[TCA_TAPRIO_ATTR_MAX + 1];
> + struct tc_mqprio_qopt *qopt = 0;
> + __s32 clockid = CLOCKID_INVALID;
> +- __s64 base_time = 0;
> + int i;
> +
> + if (opt == NULL)
> +@@ -378,19 +394,27 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
> +
> + print_string(PRINT_FP, NULL, "%s", _SL_);
> +
> +- if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
> +- base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
> +-
> + if (tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID])
> + clockid = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_SCHED_CLOCKID]);
> +
> + print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
> +
> +- print_lluint(PRINT_ANY, "base_time", " base-time %lld", base_time);
> ++ print_schedule(f, tb);
> +
> +- print_string(PRINT_FP, NULL, "%s", _SL_);
> ++ if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
> ++ struct rtattr *t[TCA_TAPRIO_ATTR_MAX + 1];
> ++
> ++ parse_rtattr_nested(t, TCA_TAPRIO_ATTR_MAX,
> ++ tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]);
> +
> +- return print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
> ++ open_json_object(NULL);
> ++
> ++ print_schedule(f, t);
> ++
> ++ close_json_object();
> ++ }
> ++
> ++ return 0;
> + }
> +
> + struct qdisc_util taprio_qdisc_util = {
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
> new file mode 100644
> index 0000000..6895a6a
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch
> @@ -0,0 +1,147 @@
> +From 538fe8f7e208c7ed7c9af191c25b3c48adb348c3 Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Mon, 29 Apr 2019 15:52:19 -0700
> +Subject: [PATCH 07/12] taprio: Add support for cycle_time and
> + cycle_time_extension
> +
> +commit 92f4b6032e7971d9b0247d7370c08cae2f1c58f9 upstream.
> +
> +This allows a cycle-time and a cycle-time-extension to be specified.
> +
> +Specifying a cycle-time will truncate that cycle, so when that instant
> +is reached, the cycle will start from its beginning.
> +
> +A cycle-time-extension may cause the last entry of a cycle, just
> +before the start of a new schedule (the base-time of the "admin"
> +schedule) to be extended by at maximum "cycle-time-extension"
> +nanoseconds. The idea of this feauture, as described by the IEEE
> +802.1Q, is too avoid too narrow gate states.
> +
> +Example:
> +
> +tc qdisc change dev IFACE parent root handle 100 taprio \
> + sched-entry S 0x1 1000000 \
> + sched-entry S 0x0 2000000 \
> + sched-entry S 0x1 3000000 \
> + sched-entry S 0x0 4000000 \
> + cycle-time-extension 100000 \
> + cycle-time 9000000 \
> + base-time 12345678900000000
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + tc/q_taprio.c | 64 ++++++++++++++++++++++++++++++++++++++++++---------
> + 1 file changed, 53 insertions(+), 11 deletions(-)
> +
> +diff --git a/tc/q_taprio.c b/tc/q_taprio.c
> +index 20804fc2..9a69b86b 100644
> +--- a/tc/q_taprio.c
> ++++ b/tc/q_taprio.c
> +@@ -155,8 +155,10 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + {
> + __s32 clockid = CLOCKID_INVALID;
> + struct tc_mqprio_qopt opt = { };
> ++ __s64 cycle_time_extension = 0;
> + struct list_head sched_entries;
> +- struct rtattr *tail;
> ++ struct rtattr *tail, *l;
> ++ __s64 cycle_time = 0;
> + __s64 base_time = 0;
> + int err, idx;
> +
> +@@ -245,6 +247,29 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + PREV_ARG();
> + break;
> + }
> ++ } else if (strcmp(*argv, "cycle-time") == 0) {
> ++ NEXT_ARG();
> ++ if (cycle_time) {
> ++ fprintf(stderr, "taprio: duplicate \"cycle-time\" specification\n");
> ++ return -1;
> ++ }
> ++
> ++ if (get_s64(&cycle_time, *argv, 10)) {
> ++ PREV_ARG();
> ++ break;
> ++ }
> ++
> ++ } else if (strcmp(*argv, "cycle-time-extension") == 0) {
> ++ NEXT_ARG();
> ++ if (cycle_time_extension) {
> ++ fprintf(stderr, "taprio: duplicate \"cycle-time-extension\" specification\n");
> ++ return -1;
> ++ }
> ++
> ++ if (get_s64(&cycle_time_extension, *argv, 10)) {
> ++ PREV_ARG();
> ++ break;
> ++ }
> + } else if (strcmp(*argv, "clockid") == 0) {
> + NEXT_ARG();
> + if (clockid != CLOCKID_INVALID) {
> +@@ -277,19 +302,24 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + if (base_time)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
> +
> +- if (!list_empty(&sched_entries)) {
> +- struct rtattr *entry_list;
> +- entry_list = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
> ++ if (cycle_time)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME,
> ++ &cycle_time, sizeof(cycle_time));
> +
> +- err = add_sched_list(&sched_entries, n);
> +- if (err < 0) {
> +- fprintf(stderr, "Could not add schedule to netlink message\n");
> +- return -1;
> +- }
> ++ if (cycle_time_extension)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION,
> ++ &cycle_time_extension, sizeof(cycle_time_extension));
> ++
> ++ l = addattr_nest(n, 1024, TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST | NLA_F_NESTED);
> +
> +- addattr_nest_end(n, entry_list);
> ++ err = add_sched_list(&sched_entries, n);
> ++ if (err < 0) {
> ++ fprintf(stderr, "Could not add schedule to netlink message\n");
> ++ return -1;
> + }
> +
> ++ addattr_nest_end(n, l);
> ++
> + tail->rta_len = (void *) NLMSG_TAIL(n) - (void *) tail;
> +
> + return 0;
> +@@ -345,13 +375,25 @@ static int print_sched_list(FILE *f, struct rtattr *list)
> +
> + static int print_schedule(FILE *f, struct rtattr **tb)
> + {
> +- int64_t base_time = 0;
> ++ int64_t base_time = 0, cycle_time = 0, cycle_time_extension = 0;
> +
> + if (tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME])
> + base_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_BASE_TIME]);
> +
> ++ if (tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME])
> ++ cycle_time = rta_getattr_s64(tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME]);
> ++
> ++ if (tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION])
> ++ cycle_time_extension = rta_getattr_s64(
> ++ tb[TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION]);
> ++
> + print_lluint(PRINT_ANY, "base_time", "\tbase-time %lld", base_time);
> +
> ++ print_lluint(PRINT_ANY, "cycle_time", " cycle-time %lld", cycle_time);
> ++
> ++ print_lluint(PRINT_ANY, "cycle_time_extension",
> ++ " cycle-time-extension %lld", cycle_time_extension);
> ++
> + print_sched_list(f, tb[TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]);
> +
> + return 0;
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
> new file mode 100644
> index 0000000..cc265f8
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0008-utils-Fix-get_s64-function.patch
> @@ -0,0 +1,34 @@
> +From 0c672a07e1d5a8068f2323e88a72e5349dacbed9 Mon Sep 17 00:00:00 2001
> +From: Kurt Kanzenbach <kurt@linutronix.de>
> +Date: Thu, 4 Jul 2019 14:24:27 +0200
> +Subject: [PATCH 08/12] utils: Fix get_s64() function
> +
> +commit c875433b145e33645798ecfe4d99bcb28c80d1e9 upstream.
> +
> +get_s64() uses internally strtoll() to parse the value out of a given
> +string. strtoll() returns a long long. However, the intermediate variable is
> +long only which might be 32 bit on some systems. So, fix it.
> +
> +Signed-off-by: Kurt Kanzenbach <kurt@linutronix.de>
> +Signed-off-by: Stephen Hemminger <stephen@networkplumber.org>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + lib/utils.c | 2 +-
> + 1 file changed, 1 insertion(+), 1 deletion(-)
> +
> +diff --git a/lib/utils.c b/lib/utils.c
> +index be29530f..9c121ce3 100644
> +--- a/lib/utils.c
> ++++ b/lib/utils.c
> +@@ -386,7 +386,7 @@ int get_u8(__u8 *val, const char *arg, int base)
> +
> + int get_s64(__s64 *val, const char *arg, int base)
> + {
> +- long res;
> ++ long long res;
> + char *ptr;
> +
> + errno = 0;
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
> new file mode 100644
> index 0000000..4f2ffde
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0009-taprio-Add-support-for-setting-flags.patch
> @@ -0,0 +1,77 @@
> +From 7e5c69b7a4733f099ca53aecfafa5dac4a3a002d Mon Sep 17 00:00:00 2001
> +From: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Date: Thu, 18 Jul 2019 12:55:40 -0700
> +Subject: [PATCH 09/12] taprio: Add support for setting flags
> +
> +commit ee000bf217870b6425849c03b309faa64539ff24 upstream.
> +
> +This allows a new parameter, flags, to be passed to taprio. Currently, it
> +only supports enabling the txtime-assist mode. But, we plan to add
> +different modes for taprio (e.g. hardware offloading) and this parameter
> +will be useful in enabling those modes.
> +
> +Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +Signed-off-by: Vedang Patel <vedang.patel@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + tc/q_taprio.c | 22 ++++++++++++++++++++++
> + 1 file changed, 22 insertions(+)
> +
> +diff --git a/tc/q_taprio.c b/tc/q_taprio.c
> +index 9a69b86b..91e3f27b 100644
> +--- a/tc/q_taprio.c
> ++++ b/tc/q_taprio.c
> +@@ -158,6 +158,7 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + __s64 cycle_time_extension = 0;
> + struct list_head sched_entries;
> + struct rtattr *tail, *l;
> ++ __u32 taprio_flags = 0;
> + __s64 cycle_time = 0;
> + __s64 base_time = 0;
> + int err, idx;
> +@@ -280,6 +281,17 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + explain_clockid(*argv);
> + return -1;
> + }
> ++ } else if (strcmp(*argv, "flags") == 0) {
> ++ NEXT_ARG();
> ++ if (taprio_flags) {
> ++ fprintf(stderr, "taprio: duplicate \"flags\" specification\n");
> ++ return -1;
> ++ }
> ++ if (get_u32(&taprio_flags, *argv, 0)) {
> ++ PREV_ARG();
> ++ return -1;
> ++ }
> ++
> + } else if (strcmp(*argv, "help") == 0) {
> + explain();
> + return -1;
> +@@ -296,6 +308,9 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + if (clockid != CLOCKID_INVALID)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_CLOCKID, &clockid, sizeof(clockid));
> +
> ++ if (taprio_flags)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_FLAGS, &taprio_flags, sizeof(taprio_flags));
> ++
> + if (opt.num_tc > 0)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
> +
> +@@ -441,6 +456,13 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
> +
> + print_string(PRINT_ANY, "clockid", "clockid %s", get_clock_name(clockid));
> +
> ++ if (tb[TCA_TAPRIO_ATTR_FLAGS]) {
> ++ __u32 flags;
> ++
> ++ flags = rta_getattr_u32(tb[TCA_TAPRIO_ATTR_FLAGS]);
> ++ print_0xhex(PRINT_ANY, "flags", " flags %#x", flags);
> ++ }
> ++
> + print_schedule(f, tb);
> +
> + if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
> new file mode 100644
> index 0000000..77c9580
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0010-taprio-add-support-for-setting-txtime_delay.patch
> @@ -0,0 +1,96 @@
> +From 1f018de4a624dac26e7c4ea2a6b47a63d1c9c45f Mon Sep 17 00:00:00 2001
> +From: Vedang Patel <vedang.patel@intel.com>
> +Date: Thu, 18 Jul 2019 12:55:41 -0700
> +Subject: [PATCH 10/12] taprio: add support for setting txtime_delay.
> +
> +commit a5e6ee3b34226f76c8be4b1e3e3ad82212ea4d50 upstream.
> +
> +This adds support for setting the txtime_delay parameter which is useful
> +for the txtime offload mode of taprio.
> +
> +Signed-off-by: Vedang Patel <vedang.patel@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + tc/q_taprio.c | 37 ++++++++++++++++++++++++++++++-------
> + 1 file changed, 30 insertions(+), 7 deletions(-)
> +
> +diff --git a/tc/q_taprio.c b/tc/q_taprio.c
> +index 91e3f27b..5e498489 100644
> +--- a/tc/q_taprio.c
> ++++ b/tc/q_taprio.c
> +@@ -47,13 +47,14 @@ static const struct static_clockid {
> +
> + static void explain(void)
> + {
> +- fprintf(stderr, "Usage: ... taprio clockid CLOCKID\n");
> +- fprintf(stderr, " [num_tc NUMBER] [map P0 P1 ...] ");
> +- fprintf(stderr, " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] ");
> +- fprintf(stderr, " [ [sched-entry index cmd gate-mask interval] ... ] ");
> +- fprintf(stderr, " [base-time time] ");
> +- fprintf(stderr, "\nCLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)");
> +- fprintf(stderr, "\n");
> ++ fprintf(stderr,
> ++ "Usage: ... taprio clockid CLOCKID\n"
> ++ " [num_tc NUMBER] [map P0 P1 ...] "
> ++ " [queues COUNT@OFFSET COUNT@OFFSET COUNT@OFFSET ...] "
> ++ " [ [sched-entry index cmd gate-mask interval] ... ] "
> ++ " [base-time time] [txtime-delay delay]"
> ++ "\n"
> ++ "CLOCKID must be a valid SYS-V id (i.e. CLOCK_TAI)\n");
> + }
> +
> + static void explain_clockid(const char *val)
> +@@ -159,6 +160,7 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + struct list_head sched_entries;
> + struct rtattr *tail, *l;
> + __u32 taprio_flags = 0;
> ++ __u32 txtime_delay = 0;
> + __s64 cycle_time = 0;
> + __s64 base_time = 0;
> + int err, idx;
> +@@ -292,6 +294,17 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + return -1;
> + }
> +
> ++ } else if (strcmp(*argv, "txtime-delay") == 0) {
> ++ NEXT_ARG();
> ++ if (txtime_delay != 0) {
> ++ fprintf(stderr, "taprio: duplicate \"txtime-delay\" specification\n");
> ++ return -1;
> ++ }
> ++ if (get_u32(&txtime_delay, *argv, 0)) {
> ++ PREV_ARG();
> ++ return -1;
> ++ }
> ++
> + } else if (strcmp(*argv, "help") == 0) {
> + explain();
> + return -1;
> +@@ -314,6 +327,9 @@ static int taprio_parse_opt(struct qdisc_util *qu, int argc,
> + if (opt.num_tc > 0)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_PRIOMAP, &opt, sizeof(opt));
> +
> ++ if (txtime_delay)
> ++ addattr_l(n, 1024, TCA_TAPRIO_ATTR_TXTIME_DELAY, &txtime_delay, sizeof(txtime_delay));
> ++
> + if (base_time)
> + addattr_l(n, 1024, TCA_TAPRIO_ATTR_SCHED_BASE_TIME, &base_time, sizeof(base_time));
> +
> +@@ -463,6 +479,13 @@ static int taprio_print_opt(struct qdisc_util *qu, FILE *f, struct rtattr *opt)
> + print_0xhex(PRINT_ANY, "flags", " flags %#x", flags);
> + }
> +
> ++ if (tb[TCA_TAPRIO_ATTR_TXTIME_DELAY]) {
> ++ __u32 txtime_delay;
> ++
> ++ txtime_delay = rta_getattr_s32(tb[TCA_TAPRIO_ATTR_TXTIME_DELAY]);
> ++ print_uint(PRINT_ANY, "txtime_delay", " txtime delay %d", txtime_delay);
> ++ }
> ++
> + print_schedule(f, tb);
> +
> + if (tb[TCA_TAPRIO_ATTR_ADMIN_SCHED]) {
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
> new file mode 100644
> index 0000000..a575e2e
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0011-tc-taprio-Update-documentation.patch
> @@ -0,0 +1,80 @@
> +From 5932369560e2ad1deecafa829edd0e89170a3545 Mon Sep 17 00:00:00 2001
> +From: Vedang Patel <vedang.patel@intel.com>
> +Date: Thu, 18 Jul 2019 12:55:43 -0700
> +Subject: [PATCH 11/12] tc: taprio: Update documentation
> +
> +commit a794d0523711d5ab4530483b9435ba627e07d28b upstream.
> +
> +Add documentation for the latest options, flags and txtime-delay, to the
> +taprio manpage.
> +
> +This also adds an example to run tc in txtime offload mode.
> +
> +Signed-off-by: Vedang Patel <vedang.patel@intel.com>
> +Signed-off-by: David Ahern <dsahern@gmail.com>
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + man/man8/tc-taprio.8 | 40 ++++++++++++++++++++++++++++++++++++++++
> + 1 file changed, 40 insertions(+)
> +
> +diff --git a/man/man8/tc-taprio.8 b/man/man8/tc-taprio.8
> +index 92055b43..2cb39da3 100644
> +--- a/man/man8/tc-taprio.8
> ++++ b/man/man8/tc-taprio.8
> +@@ -112,6 +112,26 @@ means that traffic class 0 is "active" for that schedule entry.
> + long that state defined by <command> and <gate mask> should be held
> + before moving to the next entry.
> +
> ++.TP
> ++flags
> ++.br
> ++Specifies different modes for taprio. Currently, only txtime-assist is
> ++supported which can be enabled by setting it to 0x1. In this mode, taprio will
> ++set the transmit timestamp depending on the interval in which the packet needs
> ++to be transmitted. It will then utililize the
> ++.BR etf(8)
> ++qdisc to sort and transmit the packets at the right time. The second example
> ++can be used as a reference to configure this mode.
> ++
> ++.TP
> ++txtime-delay
> ++.br
> ++This parameter is specific to the txtime offload mode. It specifies the maximum
> ++time a packet might take to reach the network card from the taprio qdisc. The
> ++value should always be greater than the delta specified in the
> ++.BR etf(8)
> ++qdisc.
> ++
> + .SH EXAMPLES
> +
> + The following example shows how an traffic schedule with three traffic
> +@@ -137,6 +157,26 @@ reference CLOCK_TAI. The schedule is composed of three entries each of
> + clockid CLOCK_TAI
> + .EE
> +
> ++Following is an example to enable the txtime offload mode in taprio. See
> ++.BR etf(8)
> ++for more information about configuring the ETF qdisc.
> ++
> ++.EX
> ++# tc qdisc replace dev eth0 parent root handle 100 taprio \\
> ++ num_tc 3 \\
> ++ map 2 2 1 0 2 2 2 2 2 2 2 2 2 2 2 2 \\
> ++ queues 1@0 1@0 1@0 \\
> ++ base-time 1528743495910289987 \\
> ++ sched-entry S 01 300000 \\
> ++ sched-entry S 02 300000 \\
> ++ sched-entry S 04 400000 \\
> ++ flags 0x1 \\
> ++ txtime-delay 200000 \\
> ++ clockid CLOCK_TAI
> ++
> ++# tc qdisc replace dev $IFACE parent 100:1 etf skip_skb_check \\
> ++ offload delta 200000 clockid CLOCK_TAI
> ++.EE
> +
> + .SH AUTHORS
> + Vinicius Costa Gomes <vinicius.gomes@intel.com>
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
> new file mode 100644
> index 0000000..0914b8d
> --- /dev/null
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2/0012-sync-pkt_sched-header-with-kernel-version.patch
> @@ -0,0 +1,128 @@
> +From 3736970b76dc41cd2d76399650709eab6a031807 Mon Sep 17 00:00:00 2001
> +From: Murali Karicheri <m-karicheri2@ti.com>
> +Date: Thu, 17 Oct 2019 17:50:18 -0400
> +Subject: [PATCH 12/12] sync pkt_sched header with kernel version
> +
> +For picking taprio specific definitions, sync up the pkt_sched.h with
> +kernel header.
> +
> +Signed-off-by: Murali Karicheri <m-karicheri2@ti.com>
> +---
> + include/uapi/linux/const.h | 31 ++++++++++++++++
> + include/uapi/linux/pkt_sched.h | 64 ++++++++++++++++++++++++++++++++++
> + 2 files changed, 95 insertions(+)
> + create mode 100644 include/uapi/linux/const.h
> +
> +diff --git a/include/uapi/linux/const.h b/include/uapi/linux/const.h
> +new file mode 100644
> +index 00000000..fd885c79
> +--- /dev/null
> ++++ b/include/uapi/linux/const.h
> +@@ -0,0 +1,31 @@
> ++/* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
> ++/* const.h: Macros for dealing with constants. */
> ++
> ++#ifndef _LINUX_CONST_H
> ++#define _LINUX_CONST_H
> ++
> ++/* Some constant macros are used in both assembler and
> ++ * C code. Therefore we cannot annotate them always with
> ++ * 'UL' and other type specifiers unilaterally. We
> ++ * use the following macros to deal with this.
> ++ *
> ++ * Similarly, _AT() will cast an expression with a type in C, but
> ++ * leave it unchanged in asm.
> ++ */
> ++
> ++#ifdef __ASSEMBLY__
> ++#define _AC(X,Y) X
> ++#define _AT(T,X) X
> ++#else
> ++#define __AC(X,Y) (X##Y)
> ++#define _AC(X,Y) __AC(X,Y)
> ++#define _AT(T,X) ((T)(X))
> ++#endif
> ++
> ++#define _UL(x) (_AC(x, UL))
> ++#define _ULL(x) (_AC(x, ULL))
> ++
> ++#define _BITUL(x) (_UL(1) << (x))
> ++#define _BITULL(x) (_ULL(1) << (x))
> ++
> ++#endif /* _LINUX_CONST_H */
> +diff --git a/include/uapi/linux/pkt_sched.h b/include/uapi/linux/pkt_sched.h
> +index 8975fd1a..9408fb43 100644
> +--- a/include/uapi/linux/pkt_sched.h
> ++++ b/include/uapi/linux/pkt_sched.h
> +@@ -1084,4 +1084,68 @@ enum {
> + CAKE_ATM_MAX
> + };
> +
> ++
> ++/* TAPRIO */
> ++enum {
> ++ TC_TAPRIO_CMD_SET_GATES = 0x00,
> ++ TC_TAPRIO_CMD_SET_AND_HOLD = 0x01,
> ++ TC_TAPRIO_CMD_SET_AND_RELEASE = 0x02,
> ++};
> ++
> ++enum {
> ++ TCA_TAPRIO_SCHED_ENTRY_UNSPEC,
> ++ TCA_TAPRIO_SCHED_ENTRY_INDEX, /* u32 */
> ++ TCA_TAPRIO_SCHED_ENTRY_CMD, /* u8 */
> ++ TCA_TAPRIO_SCHED_ENTRY_GATE_MASK, /* u32 */
> ++ TCA_TAPRIO_SCHED_ENTRY_INTERVAL, /* u32 */
> ++ __TCA_TAPRIO_SCHED_ENTRY_MAX,
> ++};
> ++#define TCA_TAPRIO_SCHED_ENTRY_MAX (__TCA_TAPRIO_SCHED_ENTRY_MAX - 1)
> ++
> ++/* The format for schedule entry list is:
> ++ * [TCA_TAPRIO_SCHED_ENTRY_LIST]
> ++ * [TCA_TAPRIO_SCHED_ENTRY]
> ++ * [TCA_TAPRIO_SCHED_ENTRY_CMD]
> ++ * [TCA_TAPRIO_SCHED_ENTRY_GATES]
> ++ * [TCA_TAPRIO_SCHED_ENTRY_INTERVAL]
> ++ */
> ++enum {
> ++ TCA_TAPRIO_SCHED_UNSPEC,
> ++ TCA_TAPRIO_SCHED_ENTRY,
> ++ __TCA_TAPRIO_SCHED_MAX,
> ++};
> ++
> ++#define TCA_TAPRIO_SCHED_MAX (__TCA_TAPRIO_SCHED_MAX - 1)
> ++
> ++/* The format for the admin sched (dump only):
> ++ * [TCA_TAPRIO_SCHED_ADMIN_SCHED]
> ++ * [TCA_TAPRIO_ATTR_SCHED_BASE_TIME]
> ++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST]
> ++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY]
> ++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_CMD]
> ++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_GATES]
> ++ * [TCA_TAPRIO_ATTR_SCHED_ENTRY_INTERVAL]
> ++ */
> ++
> ++#define TCA_TAPRIO_ATTR_FLAG_TXTIME_ASSIST BIT(0)
> ++#define TCA_TAPRIO_ATTR_FLAG_FULL_OFFLOAD BIT(1)
> ++
> ++enum {
> ++ TCA_TAPRIO_ATTR_UNSPEC,
> ++ TCA_TAPRIO_ATTR_PRIOMAP, /* struct tc_mqprio_qopt */
> ++ TCA_TAPRIO_ATTR_SCHED_ENTRY_LIST, /* nested of entry */
> ++ TCA_TAPRIO_ATTR_SCHED_BASE_TIME, /* s64 */
> ++ TCA_TAPRIO_ATTR_SCHED_SINGLE_ENTRY, /* single entry */
> ++ TCA_TAPRIO_ATTR_SCHED_CLOCKID, /* s32 */
> ++ TCA_TAPRIO_PAD,
> ++ TCA_TAPRIO_ATTR_ADMIN_SCHED, /* The admin sched, only used in dump */
> ++ TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME, /* s64 */
> ++ TCA_TAPRIO_ATTR_SCHED_CYCLE_TIME_EXTENSION, /* s64 */
> ++ TCA_TAPRIO_ATTR_FLAGS, /* u32 */
> ++ TCA_TAPRIO_ATTR_TXTIME_DELAY, /* u32 */
> ++ __TCA_TAPRIO_ATTR_MAX,
> ++};
> ++
> ++#define TCA_TAPRIO_ATTR_MAX (__TCA_TAPRIO_ATTR_MAX - 1)
> ++
> + #endif
> +--
> +2.18.1
> +
> diff --git a/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend b/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
> index 2100f49..7fa33f6 100644
> --- a/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
> +++ b/meta-arago-distro/recipes-connectivity/iproute2/iproute2_4.19.0.bbappend
> @@ -1,4 +1,4 @@
> -PR_append = ".arago5"
> +PR_append = ".arago6"
>
> FILESEXTRAPATHS_prepend := "${THISDIR}/${PN}:"
>
> @@ -7,4 +7,16 @@ SRC_URI_append = " \
> file://0002-hsr-prp-introduce-common-definitions-for-netlink-int.patch \
> file://0003-hsr-prp-refactor-common-code.patch \
> file://0004-hsr-prp-add-support-for-vlan-tagged-supervision-fram.patch \
> + file://0001-utils-Implement-get_s64.patch \
> + file://0002-include-Add-helper-to-retrieve-a-__s64-from-a-netlin.patch \
> + file://0003-libnetlink-Add-helper-for-getting-a-__s32-from-netli.patch \
> + file://0004-tc-Add-support-for-configuring-the-taprio-scheduler.patch \
> + file://0005-taprio-Add-manpage-for-tc-taprio-8.patch \
> + file://0006-taprio-Add-support-for-changing-schedules.patch \
> + file://0007-taprio-Add-support-for-cycle_time-and-cycle_time_ext.patch \
> + file://0008-utils-Fix-get_s64-function.patch \
> + file://0009-taprio-Add-support-for-setting-flags.patch \
> + file://0010-taprio-add-support-for-setting-txtime_delay.patch \
> + file://0011-tc-taprio-Update-documentation.patch \
> + file://0012-sync-pkt_sched-header-with-kernel-version.patch \
> "
> --
> 1.9.1
>
> _______________________________________________
> meta-arago mailing list
> meta-arago@arago-project.org
> http://arago-project.org/cgi-bin/mailman/listinfo/meta-arago
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2019-10-29 21:05 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2019-10-28 19:13 [master/thud][PATCH] iproute2: soft taprio: add patches for taprio Jacob Stiffler
2019-10-29 21:04 ` Denys Dmytriyenko
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.