Browse Source

config: parse default mac address from board.json

Example:
{
	"network-device": {
		"eth0": {
			"macaddr": "bc:a5:11:16:76:d7"
		}
	}
}

Signed-off-by: Felix Fietkau <nbd@nbd.name>
Felix Fietkau 3 years ago
parent
commit
42c48866f1
11 changed files with 141 additions and 26 deletions
  1. 56 0
      config.c
  2. 1 0
      config.h
  3. 52 0
      config/board.json
  4. 17 6
      device.c
  5. 2 1
      device.h
  6. 0 6
      interface-ip.c
  7. 0 5
      macvlan.c
  8. 8 0
      netifd.h
  9. 3 1
      system-dummy.c
  10. 2 2
      system-linux.c
  11. 0 5
      veth.c

+ 56 - 0
config.c

@@ -18,6 +18,8 @@
 
 #include <uci.h>
 
+#include <libubox/blobmsg_json.h>
+
 #include "netifd.h"
 #include "interface.h"
 #include "interface-ip.h"
@@ -31,6 +33,7 @@ bool config_init = false;
 static struct uci_context *uci_ctx;
 static struct uci_package *uci_network;
 static struct uci_package *uci_wireless;
+static struct blob_attr *board_netdevs;
 static struct blob_buf b;
 
 static int
@@ -654,6 +657,57 @@ config_init_wireless(void)
 	}
 }
 
+
+static struct blob_attr *
+config_find_blobmsg_attr(struct blob_attr *attr, const char *name, int type)
+{
+	struct blobmsg_policy policy = { .name = name, .type = type };
+	struct blob_attr *cur;
+
+	blobmsg_parse(&policy, 1, &cur, blobmsg_data(attr), blobmsg_len(attr));
+
+	return cur;
+}
+
+struct ether_addr *config_get_default_macaddr(const char *ifname)
+{
+	struct blob_attr *cur;
+
+	if (!board_netdevs)
+		return NULL;
+
+	cur = config_find_blobmsg_attr(board_netdevs, ifname, BLOBMSG_TYPE_TABLE);
+	if (!cur)
+		return NULL;
+
+	cur = config_find_blobmsg_attr(cur, "macaddr", BLOBMSG_TYPE_STRING);
+	if (!cur)
+		return NULL;
+
+	return ether_aton(blobmsg_get_string(cur));
+}
+
+static void
+config_init_board(void)
+{
+	struct blob_attr *cur;
+
+	blob_buf_init(&b, 0);
+
+	if (!blobmsg_add_json_from_file(&b, DEFAULT_BOARD_JSON))
+		return;
+
+	free(board_netdevs);
+	board_netdevs = NULL;
+
+	cur = config_find_blobmsg_attr(b.head, "network-device",
+				       BLOBMSG_TYPE_TABLE);
+	if (!cur)
+		return;
+
+	board_netdevs = blob_memdup(cur);
+}
+
 int
 config_init_all(void)
 {
@@ -676,6 +730,8 @@ config_init_all(void)
 		ret = -1;
 	}
 
+	config_init_board();
+
 	vlist_update(&interfaces);
 	config_init = true;
 	device_lock();

+ 1 - 0
config.h

@@ -20,5 +20,6 @@
 extern bool config_init;
 
 int config_init_all(void);
+struct ether_addr *config_get_default_macaddr(const char *ifname);
 
 #endif

+ 52 - 0
config/board.json

@@ -0,0 +1,52 @@
+{
+    "model": {
+        "id": "netgear,gs110tpp-v1",
+        "name": "Netgear GS110TPP"
+    },
+    "bridge": {
+        "name": "switch",
+        "macaddr": "bc:a5:11:16:76:d7"
+    },
+    "network": {
+        "wan": {
+            "ifname": " lan1 lan2 lan3 lan4 lan5 lan6 lan7 lan8",
+            "protocol": "dhcp",
+            "macaddr": "bc:a5:11:16:76:d7"
+        },
+        "lan": {
+            "ifname": "lan1",
+            "protocol": "static",
+            "vlan": "100",
+            "macaddr": "be:a5:11:16:76:d7"
+        }
+    },
+    "network-device": {
+        "eth0": {
+            "macaddr": "bc:a5:11:16:76:d7"
+        },
+        "lan1": {
+            "macaddr": "be:a5:11:16:76:d7"
+        },
+        "lan2": {
+            "macaddr": "be:a5:11:16:76:d8"
+        },
+        "lan3": {
+            "macaddr": "be:a5:11:16:76:d9"
+        },
+        "lan4": {
+            "macaddr": "be:a5:11:16:76:da"
+        },
+        "lan5": {
+            "macaddr": "be:a5:11:16:76:db"
+        },
+        "lan6": {
+            "macaddr": "be:a5:11:16:76:dc"
+        },
+        "lan7": {
+            "macaddr": "be:a5:11:16:76:dd"
+        },
+        "lan8": {
+            "macaddr": "be:a5:11:16:76:de"
+        }
+    }
+}

+ 17 - 6
device.c

@@ -18,11 +18,6 @@
 
 #include <sys/types.h>
 #include <sys/socket.h>
-#include <net/ethernet.h>
-
-#ifdef linux
-#include <netinet/ether.h>
-#endif
 
 #include <libubox/list.h>
 
@@ -232,7 +227,7 @@ device_merge_settings(struct device *dev, struct device_settings *n)
 	n->txqueuelen = s->flags & DEV_OPT_TXQUEUELEN ?
 		s->txqueuelen : os->txqueuelen;
 	memcpy(n->macaddr,
-		(s->flags & DEV_OPT_MACADDR ? s->macaddr : os->macaddr),
+		(s->flags & (DEV_OPT_MACADDR|DEV_OPT_DEFAULT_MACADDR) ? s->macaddr : os->macaddr),
 		sizeof(n->macaddr));
 	n->ipv6 = s->flags & DEV_OPT_IPV6 ? s->ipv6 : os->ipv6;
 	n->promisc = s->flags & DEV_OPT_PROMISC ? s->promisc : os->promisc;
@@ -430,6 +425,21 @@ void device_broadcast_event(struct device *dev, enum device_event ev)
 	safe_list_for_each(&dev->users, device_broadcast_cb, &dev_ev);
 }
 
+static void
+device_fill_default_settings(struct device *dev)
+{
+	struct device_settings *s = &dev->settings;
+	struct ether_addr *ea;
+
+	if (!(s->flags & DEV_OPT_MACADDR)) {
+		ea = config_get_default_macaddr(dev->ifname);
+		if (ea) {
+			memcpy(s->macaddr, ea, 6);
+			s->flags |= DEV_OPT_DEFAULT_MACADDR;
+		}
+	}
+}
+
 int device_claim(struct device_user *dep)
 {
 	struct device *dev = dep->dev;
@@ -447,6 +457,7 @@ int device_claim(struct device_user *dep)
 		return 0;
 
 	device_broadcast_event(dev, DEV_EVENT_SETUP);
+	device_fill_default_settings(dev);
 	if (dev->external) {
 		/* Get ifindex for external claimed devices so a valid   */
 		/* ifindex is in place avoiding possible race conditions */

+ 2 - 1
device.h

@@ -93,7 +93,8 @@ enum {
 	DEV_OPT_IGMPVERSION		= (1 << 7),
 	DEV_OPT_MLDVERSION		= (1 << 8),
 	DEV_OPT_NEIGHREACHABLETIME	= (1 << 9),
-	/* 2 bit hole */
+	DEV_OPT_DEFAULT_MACADDR		= (1 << 10),
+	/* 1 bit hole */
 	DEV_OPT_MTU6			= (1 << 12),
 	DEV_OPT_DADTRANSMITS		= (1 << 13),
 	DEV_OPT_MULTICAST_TO_UNICAST	= (1 << 14),

+ 0 - 6
interface-ip.c

@@ -22,12 +22,6 @@
 #include <arpa/inet.h>
 #include <netinet/in.h>
 
-#ifdef linux
-#include <netinet/ether.h>
-#else
-#include <net/ethernet.h>
-#endif
-
 #include "netifd.h"
 #include "device.h"
 #include "interface.h"

+ 0 - 5
macvlan.c

@@ -17,11 +17,6 @@
 #include <stdio.h>
 #include <assert.h>
 #include <errno.h>
-#include <net/ethernet.h>
-
-#ifdef linux
-#include <netinet/ether.h>
-#endif
 
 #include "netifd.h"
 #include "device.h"

+ 8 - 0
netifd.h

@@ -26,6 +26,12 @@
 
 #include <libubus.h>
 
+#ifdef linux
+#include <netinet/ether.h>
+#else
+#include <net/ethernet.h>
+#endif
+
 #include "utils.h"
 
 #ifdef DUMMY_MODE
@@ -33,11 +39,13 @@
 #define DEFAULT_CONFIG_PATH	"./config"
 #define DEFAULT_HOTPLUG_PATH	"./examples/hotplug-cmd"
 #define DEFAULT_RESOLV_CONF	"./tmp/resolv.conf"
+#define DEFAULT_BOARD_JSON	"./config/board.json"
 #else
 #define DEFAULT_MAIN_PATH	"/lib/netifd"
 #define DEFAULT_CONFIG_PATH	NULL /* use the default set in libuci */
 #define DEFAULT_HOTPLUG_PATH	"/sbin/hotplug-call"
 #define DEFAULT_RESOLV_CONF	"/tmp/resolv.conf.d/resolv.conf.auto"
+#define DEFAULT_BOARD_JSON	"/etc/board.json"
 #endif
 
 extern const char *resolv_conf;

+ 3 - 1
system-dummy.c

@@ -159,7 +159,9 @@ system_if_dump_stats(struct device *dev, struct blob_buf *b)
 void
 system_if_apply_settings(struct device *dev, struct device_settings *s, unsigned int apply_mask)
 {
-	if ((s->flags & DEV_OPT_MACADDR & apply_mask) && !dev->external) {
+	apply_mask &= s->flags;
+
+	if ((apply_mask & (DEV_OPT_MACADDR | DEV_OPT_DEFAULT_MACADDR)) && !dev->external) {
 		D(SYSTEM, "ifconfig %s hw ether %s\n",
 		  dev->ifname, format_macaddr(s->macaddr));
 	}

+ 2 - 2
system-linux.c

@@ -28,8 +28,8 @@
 
 #include <limits.h>
 #include <arpa/inet.h>
-#include <netinet/ether.h>
 #include <netinet/in.h>
+#include <netinet/ether.h>
 
 #include <linux/rtnetlink.h>
 #include <linux/neighbour.h>
@@ -1659,7 +1659,7 @@ system_if_apply_settings(struct device *dev, struct device_settings *s, unsigned
 		if (ioctl(sock_ioctl, SIOCSIFTXQLEN, &ifr) < 0)
 			s->flags &= ~DEV_OPT_TXQUEUELEN;
 	}
-	if ((apply_mask & DEV_OPT_MACADDR) && !dev->external) {
+	if ((apply_mask & (DEV_OPT_MACADDR | DEV_OPT_DEFAULT_MACADDR)) && !dev->external) {
 		ifr.ifr_hwaddr.sa_family = ARPHRD_ETHER;
 		memcpy(&ifr.ifr_hwaddr.sa_data, s->macaddr, sizeof(s->macaddr));
 		if (ioctl(sock_ioctl, SIOCSIFHWADDR, &ifr) < 0)

+ 0 - 5
veth.c

@@ -18,11 +18,6 @@
 #include <stdio.h>
 #include <assert.h>
 #include <errno.h>
-#include <net/ethernet.h>
-
-#ifdef linux
-#include <netinet/ether.h>
-#endif
 
 #include "netifd.h"
 #include "device.h"