network: introduce new netdev create type NETDEV_CREATE_AFTER_CONFIGURED

It will be used to support L2TP tunnel in later commits.
This commit is contained in:
Yu Watanabe 2019-03-11 16:11:47 +09:00
parent 859e9c0487
commit 7033af49df
3 changed files with 52 additions and 0 deletions

View File

@ -598,6 +598,14 @@ static int netdev_create(NetDev *netdev, Link *link, link_netlink_message_handle
return 0;
}
static int netdev_create_after_configured(NetDev *netdev, Link *link) {
assert(netdev);
assert(link);
assert(NETDEV_VTABLE(netdev)->create_after_configured);
return NETDEV_VTABLE(netdev)->create_after_configured(netdev, link);
}
/* the callback must be called, possibly after a timeout, as otherwise the Link will hang */
int netdev_join(NetDev *netdev, Link *link, link_netlink_message_handler_t callback) {
int r;
@ -619,6 +627,11 @@ int netdev_join(NetDev *netdev, Link *link, link_netlink_message_handler_t callb
return r;
break;
case NETDEV_CREATE_AFTER_CONFIGURED:
r = netdev_create_after_configured(netdev, link);
if (r < 0)
return r;
break;
default:
assert_not_reached("Can not join independent netdev");
}

View File

@ -65,6 +65,7 @@ typedef enum NetDevCreateType {
NETDEV_CREATE_INDEPENDENT,
NETDEV_CREATE_MASTER,
NETDEV_CREATE_STACKED,
NETDEV_CREATE_AFTER_CONFIGURED,
_NETDEV_CREATE_MAX,
_NETDEV_CREATE_INVALID = -1,
} NetDevCreateType;
@ -123,6 +124,9 @@ typedef struct NetDevVTable {
/* create netdev, if not done via rtnl */
int (*create)(NetDev *netdev);
/* create netdev after link is fully configured */
int (*create_after_configured)(NetDev *netdev, Link *link);
/* perform additional configuration after netdev has been createad */
int (*post_create)(NetDev *netdev, Link *link, sd_netlink_message *message);
@ -162,6 +166,7 @@ int netdev_get(Manager *manager, const char *name, NetDev **ret);
int netdev_set_ifindex(NetDev *netdev, sd_netlink_message *newlink);
int netdev_get_mac(const char *ifname, struct ether_addr **ret);
int netdev_join(NetDev *netdev, Link *link, link_netlink_message_handler_t cb);
int netdev_join_after_configured(NetDev *netdev, Link *link, link_netlink_message_handler_t callback);
const char *netdev_kind_to_string(NetDevKind d) _const_;
NetDevKind netdev_kind_from_string(const char *d) _pure_;

View File

@ -822,6 +822,35 @@ static Address* link_find_dhcp_server_address(Link *link) {
return NULL;
}
static int link_join_netdevs_after_configured(Link *link) {
NetDev *netdev;
Iterator i;
int r;
HASHMAP_FOREACH(netdev, link->network->stacked_netdevs, i) {
if (netdev->ifindex > 0)
/* Assume already enslaved. */
continue;
if (netdev_get_create_type(netdev) != NETDEV_CREATE_AFTER_CONFIGURED)
continue;
log_struct(LOG_DEBUG,
LOG_LINK_INTERFACE(link),
LOG_NETDEV_INTERFACE(netdev),
LOG_LINK_MESSAGE(link, "Enslaving by '%s'", netdev->ifname));
r = netdev_join(netdev, link, NULL);
if (r < 0)
return log_struct_errno(LOG_WARNING, r,
LOG_LINK_INTERFACE(link),
LOG_NETDEV_INTERFACE(netdev),
LOG_LINK_MESSAGE(link, "Could not join netdev '%s': %m", netdev->ifname));
}
return 0;
}
static void link_enter_configured(Link *link) {
assert(link);
assert(link->network);
@ -833,6 +862,8 @@ static void link_enter_configured(Link *link) {
link_set_state(link, LINK_STATE_CONFIGURED);
(void) link_join_netdevs_after_configured(link);
link_dirty(link);
}
@ -2685,6 +2716,9 @@ static int link_enter_join_netdev(Link *link) {
/* Assume already enslaved. */
continue;
if (netdev_get_create_type(netdev) != NETDEV_CREATE_STACKED)
continue;
log_struct(LOG_DEBUG,
LOG_LINK_INTERFACE(link),
LOG_NETDEV_INTERFACE(netdev),