diff options
author | Cong Wang <xiyou.wangcong@gmail.com> | 2014-04-02 01:03:30 (GMT) |
---|---|---|
committer | Thomas Haller <thaller@redhat.com> | 2014-04-09 07:10:19 (GMT) |
commit | 12bd035b053f2df4369da47f893fefcdeec6389d (patch) | |
tree | ee82f808853158e7320cfa43d09c4869a55af223 /lib/route | |
parent | ab55ea80a4fbad94c75e31e4107bbb48406ec999 (diff) | |
download | libnl-12bd035b053f2df4369da47f893fefcdeec6389d.zip libnl-12bd035b053f2df4369da47f893fefcdeec6389d.tar.gz libnl-12bd035b053f2df4369da47f893fefcdeec6389d.tar.bz2 |
veth: implement ->io_alloc
Users don't have to call rtnl_link_veth_alloc(), instead
use generic rtnl_link_set_type().
Signed-off-by: Cong Wang <xiyou.wangcong@gmail.com>
Acked-by: Thomas Graf <tgraf@suug.ch>
Signed-off-by: Thomas Haller <thaller@redhat.com>
Diffstat (limited to 'lib/route')
-rw-r--r-- | lib/route/link/veth.c | 41 |
1 files changed, 27 insertions, 14 deletions
diff --git a/lib/route/link/veth.c b/lib/route/link/veth.c index 4ce1f10..5282ccb 100644 --- a/lib/route/link/veth.c +++ b/lib/route/link/veth.c @@ -140,6 +140,31 @@ static int veth_put_attrs(struct nl_msg *msg, struct rtnl_link *link) return 0; } +static int veth_alloc(struct rtnl_link *link) +{ + struct rtnl_link *peer; + int err; + + /* return early if we are in recursion */ + if (link->l_info) + return 0; + + if (!(peer = rtnl_link_alloc())) + return -NLE_NOMEM; + + /* We don't need to hold a reference here, as link and + * its peer should always be freed together. + */ + peer->l_info = link; + if ((err = rtnl_link_set_type(peer, "veth")) < 0) { + rtnl_link_put(peer); + return err; + } + + link->l_info = peer; + return 0; +} + static struct rtnl_link_info_ops veth_info_ops = { .io_name = "veth", .io_parse = veth_parse, @@ -147,6 +172,7 @@ static struct rtnl_link_info_ops veth_info_ops = { [NL_DUMP_LINE] = veth_dump_line, [NL_DUMP_DETAILS] = veth_dump_details, }, + .io_alloc = veth_alloc, .io_clone = veth_clone, .io_put_attrs = veth_put_attrs, }; @@ -172,29 +198,16 @@ static struct rtnl_link_info_ops veth_info_ops = { */ struct rtnl_link *rtnl_link_veth_alloc(void) { - struct rtnl_link *link, *peer; + struct rtnl_link *link; int err; if (!(link = rtnl_link_alloc())) return NULL; - if (!(peer = rtnl_link_alloc())) { - rtnl_link_put(link); - return NULL; - } - if ((err = rtnl_link_set_type(link, "veth")) < 0) { - rtnl_link_put(peer); - rtnl_link_put(link); - return NULL; - } - if ((err = rtnl_link_set_type(peer, "veth")) < 0) { - rtnl_link_put(peer); rtnl_link_put(link); return NULL; } - link->l_info = peer; - peer->l_info = link; return link; } |