The hardif patches were added to OpenWrt before they were accepted in the upstream repository. This seemed necessary at that time because OpenWrt 19.07 was alreadu branched of (to be released soon). But the upstream merged patches contain more cleanups. Having the actual upstream version in OpenWrt make it easier to integrate potential bugfixes. Signed-off-by: Sven Eckelmann <sven@narfation.org>
222 lines
6.5 KiB
Diff
222 lines
6.5 KiB
Diff
From: Sven Eckelmann <sven@narfation.org>
|
|
Date: Tue, 9 Jul 2019 19:26:47 +0200
|
|
Subject: batctl: Integrate hardif setting framework
|
|
|
|
batctl currently supports settings which are either mesh interface or vlan
|
|
specific. But B.A.T.M.A.N. V introduced two additional settings which are
|
|
hard (slave) interface specific.
|
|
|
|
To support these, an additional command prefix called hardif is implemented
|
|
for some sysfs commands:
|
|
|
|
$ batctl hardif eth0 ...
|
|
|
|
Signed-off-by: Sven Eckelmann <sven@narfation.org>
|
|
|
|
Origin: upstream, https://git.open-mesh.org/batctl.git/commit/6ed4dfc5459fd3b9ed221308075db592e538c92f
|
|
|
|
diff --git a/functions.c b/functions.c
|
|
index 61ea4879ebffbdadf8ef5bb12bb737c1ed7ff76f..4ffa86ca7830dea3ed2599656831b56f6fec9e33 100644
|
|
--- a/functions.c
|
|
+++ b/functions.c
|
|
@@ -998,6 +998,28 @@ int translate_vid(struct state *state, const char *vidstr)
|
|
return 0;
|
|
}
|
|
|
|
+int translate_hard_iface(struct state *state, const char *hardif)
|
|
+{
|
|
+ struct rtnl_link_iface_data link_data;
|
|
+ unsigned int arg_ifindex;
|
|
+
|
|
+ arg_ifindex = if_nametoindex(hardif);
|
|
+ if (arg_ifindex == 0)
|
|
+ return -ENODEV;
|
|
+
|
|
+ query_rtnl_link_single(arg_ifindex, &link_data);
|
|
+ if (!link_data.master_found)
|
|
+ return -ENOLINK;
|
|
+
|
|
+ if (!if_indextoname(link_data.master, state->mesh_iface))
|
|
+ return -ENOLINK;
|
|
+
|
|
+ state->hif = arg_ifindex;
|
|
+ state->selector = SP_HARDIF;
|
|
+
|
|
+ return 0;
|
|
+}
|
|
+
|
|
static int check_mesh_iface_netlink(struct state *state)
|
|
{
|
|
struct rtnl_link_iface_data link_data;
|
|
diff --git a/functions.h b/functions.h
|
|
index 7474c40bbcdcb8fac8865def2e82514aede62b69..0a08870cee651ee676e67d3e55677c53f59e41c4 100644
|
|
--- a/functions.h
|
|
+++ b/functions.h
|
|
@@ -53,6 +53,7 @@ int netlink_simple_request(struct nl_msg *msg);
|
|
int translate_mesh_iface_vlan(struct state *state, const char *vlandev);
|
|
int translate_vlan_iface(struct state *state, const char *vlandev);
|
|
int translate_vid(struct state *state, const char *vidstr);
|
|
+int translate_hard_iface(struct state *state, const char *hardif);
|
|
int get_algoname(const char *mesh_iface, char *algoname, size_t algoname_len);
|
|
int check_mesh_iface(struct state *state);
|
|
int check_mesh_iface_ownership(struct state *state, char *hard_iface);
|
|
diff --git a/main.c b/main.c
|
|
index 309087799b839848029bd5cbec60cbe1213f9190..3b3a16f4c1caffdd2be897e6bf2a00564e5580f8 100644
|
|
--- a/main.c
|
|
+++ b/main.c
|
|
@@ -35,7 +35,8 @@ static void print_usage(void)
|
|
{
|
|
.label = "commands:\n",
|
|
.types = BIT(SUBCOMMAND) |
|
|
- BIT(SUBCOMMAND_VID),
|
|
+ BIT(SUBCOMMAND_VID) |
|
|
+ BIT(SUBCOMMAND_HIF),
|
|
},
|
|
{
|
|
.label = "debug tables: \tdisplay the corresponding debug table\n",
|
|
@@ -51,6 +52,10 @@ static void print_usage(void)
|
|
"vid <vid> ",
|
|
NULL,
|
|
};
|
|
+ const char *hardif_prefixes[] = {
|
|
+ "hardif <netdev> ",
|
|
+ NULL,
|
|
+ };
|
|
const struct command **p;
|
|
const char **prefixes;
|
|
const char **prefix;
|
|
@@ -81,6 +86,9 @@ static void print_usage(void)
|
|
case SUBCOMMAND_VID:
|
|
prefixes = vlan_prefixes;
|
|
break;
|
|
+ case SUBCOMMAND_HIF:
|
|
+ prefixes = hardif_prefixes;
|
|
+ break;
|
|
default:
|
|
prefixes = default_prefixes;
|
|
break;
|
|
@@ -153,6 +161,9 @@ static const struct command *find_command(struct state *state, const char *name)
|
|
case SP_VLAN:
|
|
types = BIT(SUBCOMMAND_VID);
|
|
break;
|
|
+ case SP_HARDIF:
|
|
+ types = BIT(SUBCOMMAND_HIF);
|
|
+ break;
|
|
default:
|
|
return NULL;
|
|
}
|
|
@@ -171,6 +182,9 @@ static int detect_selector_prefix(int argc, char *argv[],
|
|
if (strcmp(argv[0], "vlan") == 0) {
|
|
*selector = SP_VLAN;
|
|
return 2;
|
|
+ } else if (strcmp(argv[0], "hardif") == 0) {
|
|
+ *selector = SP_HARDIF;
|
|
+ return 2;
|
|
}
|
|
|
|
return 0;
|
|
@@ -197,7 +211,17 @@ static int parse_meshif_args(struct state *state, int argc, char *argv[])
|
|
dev_arg, strerror(-ret));
|
|
return ret;
|
|
}
|
|
+ return parsed_args;
|
|
+ case SP_HARDIF:
|
|
+ ret = translate_hard_iface(state, dev_arg);
|
|
+ if (ret < 0) {
|
|
+ fprintf(stderr, "Error - invalid hardif %s: %s\n",
|
|
+ dev_arg, strerror(-ret));
|
|
+ return ret;
|
|
+ }
|
|
|
|
+ snprintf(state->hard_iface, sizeof(state->hard_iface), "%s",
|
|
+ dev_arg);
|
|
return parsed_args;
|
|
case SP_NONE_OR_MESHIF:
|
|
/* not allowed - see detect_selector_prefix */
|
|
diff --git a/main.h b/main.h
|
|
index efc277c5465942d7b4dba284d29f653273b42dce..a97b26fe7b969e01cbdb848e58824e36e3d236ab 100644
|
|
--- a/main.h
|
|
+++ b/main.h
|
|
@@ -59,11 +59,13 @@ enum command_flags {
|
|
enum selector_prefix {
|
|
SP_NONE_OR_MESHIF,
|
|
SP_VLAN,
|
|
+ SP_HARDIF,
|
|
};
|
|
|
|
enum command_type {
|
|
SUBCOMMAND,
|
|
SUBCOMMAND_VID,
|
|
+ SUBCOMMAND_HIF,
|
|
DEBUGTABLE,
|
|
};
|
|
|
|
@@ -72,7 +74,11 @@ struct state {
|
|
enum selector_prefix selector;
|
|
char mesh_iface[IF_NAMESIZE];
|
|
unsigned int mesh_ifindex;
|
|
- int vid;
|
|
+ char hard_iface[IF_NAMESIZE];
|
|
+ union {
|
|
+ unsigned int hif;
|
|
+ int vid;
|
|
+ };
|
|
const struct command *cmd;
|
|
|
|
struct nl_sock *sock;
|
|
diff --git a/sys.c b/sys.c
|
|
index 61a314d88010ef34507ec9dd6a77b53f318f63a8..b9555ee484f89c1022c0b4e74e18154d18b7af6b 100644
|
|
--- a/sys.c
|
|
+++ b/sys.c
|
|
@@ -150,6 +150,10 @@ static void settings_usage(struct state *state)
|
|
"vid <vid> ",
|
|
NULL,
|
|
};
|
|
+ const char *hardif_prefixes[] = {
|
|
+ "hardif <netdev> ",
|
|
+ NULL,
|
|
+ };
|
|
const char *linestart = "Usage:";
|
|
const char **prefixes;
|
|
const char **prefix;
|
|
@@ -158,6 +162,9 @@ static void settings_usage(struct state *state)
|
|
case SUBCOMMAND_VID:
|
|
prefixes = vlan_prefixes;
|
|
break;
|
|
+ case SUBCOMMAND_HIF:
|
|
+ prefixes = hardif_prefixes;
|
|
+ break;
|
|
default:
|
|
prefixes = default_prefixes;
|
|
break;
|
|
@@ -271,6 +278,14 @@ int handle_sys_setting(struct state *state, int argc, char **argv)
|
|
snprintf(path_buff, PATH_BUFF_LEN, SYS_VLAN_PATH,
|
|
state->mesh_iface, state->vid);
|
|
break;
|
|
+ case SP_HARDIF:
|
|
+ /* if a hard interface was specified then change the path to
|
|
+ * point to the proper ${hardif}/batman-adv path in the sysfs
|
|
+ * tree.
|
|
+ */
|
|
+ snprintf(path_buff, PATH_BUFF_LEN, SYS_HARDIF_PATH,
|
|
+ state->hard_iface);
|
|
+ break;
|
|
}
|
|
|
|
if (argc == 1) {
|
|
diff --git a/sys.h b/sys.h
|
|
index d4f2fcf542bc66b2b1c6ec55a9ac16e10fdc5cac..b6f0f9043a9af8e3c4d4f8bf7e4af4cab0aa5df9 100644
|
|
--- a/sys.h
|
|
+++ b/sys.h
|
|
@@ -21,8 +21,9 @@
|
|
#define SYS_BATIF_PATH_FMT "/sys/class/net/%s/mesh/"
|
|
#define SYS_IFACE_PATH "/sys/class/net"
|
|
#define SYS_IFACE_DIR SYS_IFACE_PATH"/%s/"
|
|
-#define SYS_MESH_IFACE_FMT SYS_IFACE_PATH"/%s/batman_adv/mesh_iface"
|
|
-#define SYS_IFACE_STATUS_FMT SYS_IFACE_PATH"/%s/batman_adv/iface_status"
|
|
+#define SYS_HARDIF_PATH SYS_IFACE_DIR "batman_adv/"
|
|
+#define SYS_MESH_IFACE_FMT SYS_HARDIF_PATH "mesh_iface"
|
|
+#define SYS_IFACE_STATUS_FMT SYS_HARDIF_PATH "iface_status"
|
|
#define SYS_VLAN_PATH SYS_IFACE_PATH"/%s/mesh/vlan%d/"
|
|
#define SYS_ROUTING_ALGO_FMT SYS_IFACE_PATH"/%s/mesh/routing_algo"
|
|
#define VLAN_ID_MAX_LEN 4
|