diff --git a/src/network/generator/network-generator.c b/src/network/generator/network-generator.c index 8c96598e204..e1f4e598c6a 100644 --- a/src/network/generator/network-generator.c +++ b/src/network/generator/network-generator.c @@ -14,6 +14,7 @@ #include "string-table.h" #include "string-util.h" #include "strv.h" +#include "vlan-util.h" /* # .network @@ -965,6 +966,24 @@ static int parse_cmdline_rd_peerdns(Context *context, const char *key, const cha return network_set_dhcp_use_dns(context, "", r); } +static int extract_vlan_id(const char *vlan_name, uint16_t *ret) { + assert(!isempty(vlan_name)); + assert(ret); + + /* From dracut.cmdline(7): + * We support the four styles of vlan names: + * VLAN_PLUS_VID (vlan0005), + * VLAN_PLUS_VID_NO_PAD (vlan5), + * DEV_PLUS_VID (eth0.0005), and + * DEV_PLUS_VID_NO_PAD (eth0.5). */ + + for (const char *p = vlan_name + strlen(vlan_name) - 1; p > vlan_name; p--) + if (!ascii_isdigit(*p)) + return parse_vlanid(p+1, ret); + + return -EINVAL; +} + static int parse_cmdline_vlan(Context *context, const char *key, const char *value) { const char *name, *p; NetDev *netdev; @@ -989,6 +1008,10 @@ static int parse_cmdline_vlan(Context *context, const char *key, const char *val return log_debug_errno(r, "Failed to create VLAN device for '%s': %m", name); } + r = extract_vlan_id(name, &netdev->vlan_id); + if (r < 0) + return log_debug_errno(r, "Failed to parse VLAN ID from VLAN device name '%s': %m", name); + return network_set_vlan(context, p + 1, name); } @@ -1367,6 +1390,13 @@ void netdev_dump(NetDev *netdev, FILE *f) { if (netdev->mtu > 0) fprintf(f, "MTUBytes=%" PRIu32 "\n", netdev->mtu); + + if (streq(netdev->kind, "vlan")) { + fprintf(f, + "\n[VLAN]\n" + "Id=%u\n", + netdev->vlan_id); + } } void link_dump(Link *link, FILE *f) { diff --git a/src/network/generator/network-generator.h b/src/network/generator/network-generator.h index 166ec68fe60..f2fdd02808c 100644 --- a/src/network/generator/network-generator.h +++ b/src/network/generator/network-generator.h @@ -79,6 +79,9 @@ struct NetDev { char *ifname; char *kind; uint32_t mtu; + + /* [VLAN] */ + uint16_t vlan_id; }; struct Link { diff --git a/src/network/generator/test-network-generator.c b/src/network/generator/test-network-generator.c index 72f3dc620e5..a65ce5a39b3 100644 --- a/src/network/generator/test-network-generator.c +++ b/src/network/generator/test-network-generator.c @@ -361,6 +361,38 @@ int main(int argc, char *argv[]) { "MTUBytes=1530\n" ); + test_netdev_one("vlan123", "vlan", "vlan123:eth0", + "[NetDev]\n" + "Kind=vlan\n" + "Name=vlan123\n" + "\n[VLAN]\n" + "Id=123\n" + ); + + test_netdev_one("vlan0013", "vlan", "vlan0013:eth0", + "[NetDev]\n" + "Kind=vlan\n" + "Name=vlan0013\n" + "\n[VLAN]\n" + "Id=11\n" /* 0013 (octal) -> 11 */ + ); + + test_netdev_one("eth0.123", "vlan", "eth0.123:eth0", + "[NetDev]\n" + "Kind=vlan\n" + "Name=eth0.123\n" + "\n[VLAN]\n" + "Id=123\n" + ); + + test_netdev_one("eth0.0013", "vlan", "eth0.0013:eth0", + "[NetDev]\n" + "Kind=vlan\n" + "Name=eth0.0013\n" + "\n[VLAN]\n" + "Id=11\n" /* 0013 (octal) -> 11 */ + ); + test_link_one("hogehoge", "ifname", "hogehoge:00:11:22:33:44:55", "[Match]\n" "MACAddress=00:11:22:33:44:55\n"