提交 77e7c13b 编写于 作者: S Stefan Berger

macvtap: convert nl msg construction to use libnl

In a first step I am converting the netlink message construction in
macvtap code to use libnl. It's pretty much a 1:1 conversion except that
now the message needs to be allocated and deallocated.
上级 76654409
...@@ -191,51 +191,6 @@ err_exit: ...@@ -191,51 +191,6 @@ err_exit:
} }
static struct rtattr *
rtattrCreate(char *buffer, int bufsize, int type,
const void *data, int datalen)
{
struct rtattr *r = (struct rtattr *)buffer;
r->rta_type = type;
r->rta_len = RTA_LENGTH(datalen);
if (r->rta_len > bufsize)
return NULL;
memcpy(RTA_DATA(r), data, datalen);
return r;
}
static void
nlInit(struct nlmsghdr *nlm, int flags, int type)
{
nlm->nlmsg_len = NLMSG_LENGTH(0);
nlm->nlmsg_flags = flags;
nlm->nlmsg_type = type;
}
static void
nlAlign(struct nlmsghdr *nlm)
{
nlm->nlmsg_len = NLMSG_ALIGN(nlm->nlmsg_len);
}
static void *
nlAppend(struct nlmsghdr *nlm, int totlen, const void *data, int datalen)
{
char *pos;
nlAlign(nlm);
if (nlm->nlmsg_len + NLMSG_ALIGN(datalen) > totlen)
return NULL;
pos = (char *)nlm + nlm->nlmsg_len;
memcpy(pos, data, datalen);
nlm->nlmsg_len += datalen;
nlAlign(nlm);
return pos;
}
# if WITH_MACVTAP # if WITH_MACVTAP
static int static int
...@@ -247,74 +202,63 @@ link_add(const char *type, ...@@ -247,74 +202,63 @@ link_add(const char *type,
int *retry) int *retry)
{ {
int rc = 0; int rc = 0;
char nlmsgbuf[NLMSGBUF_SIZE]; struct nlmsghdr *resp;
struct nlmsghdr *nlm = (struct nlmsghdr *)nlmsgbuf, *resp;
struct nlmsgerr *err; struct nlmsgerr *err;
char rtattbuf[RATTBUF_SIZE];
struct rtattr *rta, *rta1, *li;
struct ifinfomsg ifinfo = { .ifi_family = AF_UNSPEC }; struct ifinfomsg ifinfo = { .ifi_family = AF_UNSPEC };
int ifindex; int ifindex;
char *recvbuf = NULL; char *recvbuf = NULL;
unsigned int recvbuflen; unsigned int recvbuflen;
struct nl_msg *nl_msg;
struct nlattr *linkinfo, *info_data;
if (ifaceGetIndex(true, srcdev, &ifindex) != 0) if (ifaceGetIndex(true, srcdev, &ifindex) != 0)
return -1; return -1;
*retry = 0; *retry = 0;
memset(&nlmsgbuf, 0, sizeof(nlmsgbuf)); nl_msg = nlmsg_alloc_simple(RTM_NEWLINK,
NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL);
nlInit(nlm, NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL, RTM_NEWLINK); if (!nl_msg) {
virReportOOMError();
return -1;
}
if (!nlAppend(nlm, sizeof(nlmsgbuf), &ifinfo, sizeof(ifinfo))) if (nlmsg_append(nl_msg, &ifinfo, sizeof(ifinfo), NLMSG_ALIGNTO) < 0)
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_LINK, if (nla_put_u32(nl_msg, IFLA_LINK, ifindex) < 0)
&ifindex, sizeof(ifindex));
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_ADDRESS, if (nla_put(nl_msg, IFLA_ADDRESS, macaddrsize, macaddress) < 0)
macaddress, macaddrsize);
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
if (ifname) { if (ifname &&
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_IFNAME, nla_put(nl_msg, IFLA_IFNAME, strlen(ifname)+1, ifname) < 0)
ifname, strlen(ifname) + 1); goto buffer_too_small;
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small;
}
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_LINKINFO, NULL, 0); if (!(linkinfo = nla_nest_start(nl_msg, IFLA_LINKINFO)))
if (!rta ||
!(li = nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len)))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_INFO_KIND, if (nla_put(nl_msg, IFLA_INFO_KIND, strlen(type), type) < 0)
type, strlen(type));
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
if (macvlan_mode > 0) { if (macvlan_mode > 0) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_INFO_DATA, if (!(info_data = nla_nest_start(nl_msg, IFLA_INFO_DATA)))
NULL, 0);
if (!rta ||
!(rta1 = nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len)))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_MACVLAN_MODE, if (nla_put(nl_msg, IFLA_MACVLAN_MODE, sizeof(macvlan_mode),
&macvlan_mode, sizeof(macvlan_mode)); &macvlan_mode) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
rta1->rta_len = (char *)nlm + nlm->nlmsg_len - (char *)rta1; nla_nest_end(nl_msg, info_data);
} }
li->rta_len = (char *)nlm + nlm->nlmsg_len - (char *)li; nla_nest_end(nl_msg, linkinfo);
if (nlComm(nlm, &recvbuf, &recvbuflen, 0) < 0) if (nlComm(nlmsg_hdr(nl_msg), &recvbuf, &recvbuflen, 0) < 0) {
return -1; rc = -1;
goto err_exit;
}
if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL) if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL)
goto malformed_resp; goto malformed_resp;
...@@ -352,50 +296,58 @@ link_add(const char *type, ...@@ -352,50 +296,58 @@ link_add(const char *type,
goto malformed_resp; goto malformed_resp;
} }
err_exit:
nlmsg_free(nl_msg);
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return rc; return rc;
malformed_resp: malformed_resp:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("malformed netlink response message")); _("malformed netlink response message"));
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return -1; return -1;
buffer_too_small: buffer_too_small:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("internal buffer is too small")); _("allocated netlink buffer is too small"));
return -1; return -1;
} }
static int static int
link_del(const char *name) link_del(const char *ifname)
{ {
int rc = 0; int rc = 0;
char nlmsgbuf[NLMSGBUF_SIZE]; struct nlmsghdr *resp;
struct nlmsghdr *nlm = (struct nlmsghdr *)nlmsgbuf, *resp;
struct nlmsgerr *err; struct nlmsgerr *err;
char rtattbuf[RATTBUF_SIZE];
struct rtattr *rta;
struct ifinfomsg ifinfo = { .ifi_family = AF_UNSPEC }; struct ifinfomsg ifinfo = { .ifi_family = AF_UNSPEC };
char *recvbuf = NULL; char *recvbuf = NULL;
unsigned int recvbuflen; unsigned int recvbuflen;
struct nl_msg *nl_msg;
memset(&nlmsgbuf, 0, sizeof(nlmsgbuf)); nl_msg = nlmsg_alloc_simple(RTM_DELLINK,
NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL);
nlInit(nlm, NLM_F_REQUEST | NLM_F_CREATE | NLM_F_EXCL, RTM_DELLINK); if (!nl_msg) {
virReportOOMError();
return -1;
}
if (!nlAppend(nlm, sizeof(nlmsgbuf), &ifinfo, sizeof(ifinfo))) if (nlmsg_append(nl_msg, &ifinfo, sizeof(ifinfo), NLMSG_ALIGNTO) < 0)
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_IFNAME, if (nla_put(nl_msg, IFLA_IFNAME, strlen(ifname)+1, ifname) < 0)
name, strlen(name)+1);
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
if (nlComm(nlm, &recvbuf, &recvbuflen, 0) < 0) if (nlComm(nlmsg_hdr(nl_msg), &recvbuf, &recvbuflen, 0) < 0) {
return -1; rc = -1;
goto err_exit;
}
if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL) if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL)
goto malformed_resp; goto malformed_resp;
...@@ -411,7 +363,7 @@ link_del(const char *name) ...@@ -411,7 +363,7 @@ link_del(const char *name)
if (err->error) { if (err->error) {
virReportSystemError(-err->error, virReportSystemError(-err->error,
_("error destroying %s interface"), _("error destroying %s interface"),
name); ifname);
rc = -1; rc = -1;
} }
break; break;
...@@ -423,19 +375,26 @@ link_del(const char *name) ...@@ -423,19 +375,26 @@ link_del(const char *name)
goto malformed_resp; goto malformed_resp;
} }
err_exit:
nlmsg_free(nl_msg);
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return rc; return rc;
malformed_resp: malformed_resp:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("malformed netlink response message")); _("malformed netlink response message"));
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return -1; return -1;
buffer_too_small: buffer_too_small:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("internal buffer is too small")); _("allocated netlink buffer is too small"));
return -1; return -1;
} }
...@@ -783,40 +742,44 @@ link_dump(bool nltarget_kernel, const char *ifname, int ifindex, ...@@ -783,40 +742,44 @@ link_dump(bool nltarget_kernel, const char *ifname, int ifindex,
struct nlattr **tb, char **recvbuf) struct nlattr **tb, char **recvbuf)
{ {
int rc = 0; int rc = 0;
char nlmsgbuf[NLMSGBUF_SIZE] = { 0, }; struct nlmsghdr *resp;
struct nlmsghdr *nlm = (struct nlmsghdr *)nlmsgbuf, *resp;
struct nlmsgerr *err; struct nlmsgerr *err;
char rtattbuf[RATTBUF_SIZE];
struct rtattr *rta;
struct ifinfomsg ifinfo = { struct ifinfomsg ifinfo = {
.ifi_family = AF_UNSPEC, .ifi_family = AF_UNSPEC,
.ifi_index = ifindex .ifi_index = ifindex
}; };
unsigned int recvbuflen; unsigned int recvbuflen;
uint32_t pid = 0; uint32_t pid = 0;
struct nl_msg *nl_msg;
*recvbuf = NULL; *recvbuf = NULL;
nlInit(nlm, NLM_F_REQUEST, RTM_GETLINK); nl_msg = nlmsg_alloc_simple(RTM_GETLINK, NLM_F_REQUEST);
if (!nl_msg) {
virReportOOMError();
return -1;
}
if (!nlAppend(nlm, sizeof(nlmsgbuf), &ifinfo, sizeof(ifinfo))) if (nlmsg_append(nl_msg, &ifinfo, sizeof(ifinfo), NLMSG_ALIGNTO) < 0)
goto buffer_too_small; goto buffer_too_small;
if (ifindex < 0 && ifname) { if (ifindex < 0 && ifname) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_IFNAME, if (nla_put(nl_msg, IFLA_IFNAME, strlen(ifname)+1, ifname) < 0)
ifname, strlen(ifname) + 1);
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
if (!nltarget_kernel) { if (!nltarget_kernel) {
pid = getLldpadPid(); pid = getLldpadPid();
if (pid == 0) if (pid == 0) {
return -1; rc = -1;
goto err_exit;
}
} }
if (nlComm(nlm, recvbuf, &recvbuflen, pid) < 0) if (nlComm(nlmsg_hdr(nl_msg), recvbuf, &recvbuflen, pid) < 0) {
return -1; rc = -1;
goto err_exit;
}
if (recvbuflen < NLMSG_LENGTH(0) || *recvbuf == NULL) if (recvbuflen < NLMSG_LENGTH(0) || *recvbuf == NULL)
goto malformed_resp; goto malformed_resp;
...@@ -852,17 +815,24 @@ link_dump(bool nltarget_kernel, const char *ifname, int ifindex, ...@@ -852,17 +815,24 @@ link_dump(bool nltarget_kernel, const char *ifname, int ifindex,
if (rc != 0) if (rc != 0)
VIR_FREE(*recvbuf); VIR_FREE(*recvbuf);
err_exit:
nlmsg_free(nl_msg);
return rc; return rc;
malformed_resp: malformed_resp:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("malformed netlink response message")); _("malformed netlink response message"));
VIR_FREE(*recvbuf); VIR_FREE(*recvbuf);
return -1; return -1;
buffer_too_small: buffer_too_small:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("internal buffer is too small")); _("allocated netlink buffer is too small"));
return -1; return -1;
} }
...@@ -1046,11 +1016,8 @@ doPortProfileOpSetLink(bool nltarget_kernel, ...@@ -1046,11 +1016,8 @@ doPortProfileOpSetLink(bool nltarget_kernel,
uint8_t op) uint8_t op)
{ {
int rc = 0; int rc = 0;
char nlmsgbuf[NLMSGBUF_SIZE]; struct nlmsghdr *resp;
struct nlmsghdr *nlm = (struct nlmsghdr *)nlmsgbuf, *resp;
struct nlmsgerr *err; struct nlmsgerr *err;
char rtattbuf[RATTBUF_SIZE];
struct rtattr *rta, *vfports = NULL, *vfport;
struct ifinfomsg ifinfo = { struct ifinfomsg ifinfo = {
.ifi_family = AF_UNSPEC, .ifi_family = AF_UNSPEC,
.ifi_index = ifindex, .ifi_index = ifindex,
...@@ -1058,23 +1025,24 @@ doPortProfileOpSetLink(bool nltarget_kernel, ...@@ -1058,23 +1025,24 @@ doPortProfileOpSetLink(bool nltarget_kernel,
char *recvbuf = NULL; char *recvbuf = NULL;
unsigned int recvbuflen = 0; unsigned int recvbuflen = 0;
uint32_t pid = 0; uint32_t pid = 0;
struct nl_msg *nl_msg;
struct nlattr *vfports = NULL, *vfport;
memset(&nlmsgbuf, 0, sizeof(nlmsgbuf)); nl_msg = nlmsg_alloc_simple(RTM_SETLINK, NLM_F_REQUEST);
if (!nl_msg) {
nlInit(nlm, NLM_F_REQUEST, RTM_SETLINK); virReportOOMError();
return -1;
}
if (!nlAppend(nlm, sizeof(nlmsgbuf), &ifinfo, sizeof(ifinfo))) if (nlmsg_append(nl_msg, &ifinfo, sizeof(ifinfo), NLMSG_ALIGNTO) < 0)
goto buffer_too_small; goto buffer_too_small;
if (ifname) { if (ifname &&
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_IFNAME, nla_put(nl_msg, IFLA_IFNAME, strlen(ifname)+1, ifname) < 0)
ifname, strlen(ifname) + 1); goto buffer_too_small;
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small;
}
if (macaddr && vlanid >= 0) { if (macaddr && vlanid >= 0) {
struct rtattr *vfinfolist, *vfinfo; struct nlattr *vfinfolist, *vfinfo;
struct ifla_vf_mac ifla_vf_mac = { struct ifla_vf_mac ifla_vf_mac = {
.vf = vf, .vf = vf,
.mac = { 0, }, .mac = { 0, },
...@@ -1087,110 +1055,88 @@ doPortProfileOpSetLink(bool nltarget_kernel, ...@@ -1087,110 +1055,88 @@ doPortProfileOpSetLink(bool nltarget_kernel,
memcpy(ifla_vf_mac.mac, macaddr, 6); memcpy(ifla_vf_mac.mac, macaddr, 6);
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VFINFO_LIST, if (!(vfinfolist = nla_nest_start(nl_msg, IFLA_VFINFO_LIST)))
NULL, 0);
if (!rta ||
!(vfinfolist = nlAppend(nlm, sizeof(nlmsgbuf),
rtattbuf, rta->rta_len)))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VF_INFO, if (!(vfinfo = nla_nest_start(nl_msg, IFLA_VF_INFO)))
NULL, 0);
if (!rta ||
!(vfinfo = nlAppend(nlm, sizeof(nlmsgbuf),
rtattbuf, rta->rta_len)))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VF_MAC, if (!nla_put(nl_msg, IFLA_VF_MAC, sizeof(ifla_vf_mac),
&ifla_vf_mac, sizeof(ifla_vf_mac)); &ifla_vf_mac) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VF_VLAN, if (!nla_put(nl_msg, IFLA_VF_VLAN, sizeof(ifla_vf_vlan),
&ifla_vf_vlan, sizeof(ifla_vf_vlan)); &ifla_vf_vlan) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
vfinfo->rta_len = (char *)nlm + nlm->nlmsg_len - (char *)vfinfo; nla_nest_end(nl_msg, vfinfo);
nla_nest_end(nl_msg, vfinfolist);
vfinfolist->rta_len = (char *)nlm + nlm->nlmsg_len -
(char *)vfinfolist;
} }
if (vf == PORT_SELF_VF && nltarget_kernel) { if (vf == PORT_SELF_VF && nltarget_kernel) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_SELF, NULL, 0); if (!(vfport = nla_nest_start(nl_msg, IFLA_PORT_SELF)))
goto buffer_too_small;
} else { } else {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VF_PORTS, NULL, 0); if (!(vfports = nla_nest_start(nl_msg, IFLA_VF_PORTS)))
if (!rta ||
!(vfports = nlAppend(nlm, sizeof(nlmsgbuf),
rtattbuf, rta->rta_len)))
goto buffer_too_small; goto buffer_too_small;
/* begin nesting vfports */ /* begin nesting vfports */
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_VF_PORT, NULL, 0); if (!(vfport = nla_nest_start(nl_msg, IFLA_VF_PORT)))
goto buffer_too_small;
} }
if (!rta ||
!(vfport = nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len)))
goto buffer_too_small;
if (profileId) { if (profileId) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_PROFILE, if (nla_put(nl_msg, IFLA_PORT_PROFILE, strlen(profileId) + 1,
profileId, strlen(profileId) + 1); profileId) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
if (portVsi) { if (portVsi) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_VSI_TYPE, if (nla_put(nl_msg, IFLA_PORT_VSI_TYPE, sizeof(*portVsi),
portVsi, sizeof(*portVsi)); portVsi) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
if (instanceId) { if (instanceId) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_INSTANCE_UUID, if (nla_put(nl_msg, IFLA_PORT_INSTANCE_UUID, VIR_UUID_BUFLEN,
instanceId, VIR_UUID_BUFLEN); instanceId) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
if (hostUUID) { if (hostUUID) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_HOST_UUID, if (nla_put(nl_msg, IFLA_PORT_HOST_UUID, VIR_UUID_BUFLEN,
hostUUID, VIR_UUID_BUFLEN); hostUUID) < 0)
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
if (vf != PORT_SELF_VF) { if (vf != PORT_SELF_VF) {
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_VF, if (nla_put(nl_msg, IFLA_PORT_VF, sizeof(vf), &vf) < 0)
&vf, sizeof(vf));
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
} }
rta = rtattrCreate(rtattbuf, sizeof(rtattbuf), IFLA_PORT_REQUEST, if (nla_put(nl_msg, IFLA_PORT_REQUEST, sizeof(op), &op) < 0)
&op, sizeof(op));
if (!rta || !nlAppend(nlm, sizeof(nlmsgbuf), rtattbuf, rta->rta_len))
goto buffer_too_small; goto buffer_too_small;
/* end nesting of vport */ /* end nesting of vport */
vfport->rta_len = (char *)nlm + nlm->nlmsg_len - (char *)vfport; nla_nest_end(nl_msg, vfport);
if (vfports) { if (vfports) {
/* end nesting of vfports */ /* end nesting of vfports */
vfports->rta_len = (char *)nlm + nlm->nlmsg_len - (char *)vfports; nla_nest_end(nl_msg, vfports);
} }
if (!nltarget_kernel) { if (!nltarget_kernel) {
pid = getLldpadPid(); pid = getLldpadPid();
if (pid == 0) if (pid == 0) {
return -1; rc = -1;
goto err_exit;
}
} }
if (nlComm(nlm, &recvbuf, &recvbuflen, pid) < 0) if (nlComm(nlmsg_hdr(nl_msg), &recvbuf, &recvbuflen, pid) < 0) {
return -1; rc = -1;
goto err_exit;
}
if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL) if (recvbuflen < NLMSG_LENGTH(0) || recvbuf == NULL)
goto malformed_resp; goto malformed_resp;
...@@ -1218,19 +1164,26 @@ doPortProfileOpSetLink(bool nltarget_kernel, ...@@ -1218,19 +1164,26 @@ doPortProfileOpSetLink(bool nltarget_kernel,
goto malformed_resp; goto malformed_resp;
} }
err_exit:
nlmsg_free(nl_msg);
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return rc; return rc;
malformed_resp: malformed_resp:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("malformed netlink response message")); _("malformed netlink response message"));
VIR_FREE(recvbuf); VIR_FREE(recvbuf);
return -1; return -1;
buffer_too_small: buffer_too_small:
nlmsg_free(nl_msg);
macvtapError(VIR_ERR_INTERNAL_ERROR, "%s", macvtapError(VIR_ERR_INTERNAL_ERROR, "%s",
_("internal buffer is too small")); _("allocated netlink buffer is too small"));
return -1; return -1;
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册