Patch Detail
get:
Show a patch.
patch:
Update a patch.
put:
Update a patch.
GET /api/patches/813281/?format=api
{ "id": 813281, "url": "http://patchwork.ozlabs.org/api/patches/813281/?format=api", "web_url": "http://patchwork.ozlabs.org/project/netdev/patch/1505296780-8444-3-git-send-email-liuhangbin@gmail.com/", "project": { "id": 7, "url": "http://patchwork.ozlabs.org/api/projects/7/?format=api", "name": "Linux network development", "link_name": "netdev", "list_id": "netdev.vger.kernel.org", "list_email": "netdev@vger.kernel.org", "web_url": null, "scm_url": null, "webscm_url": null, "list_archive_url": "", "list_archive_url_format": "", "commit_url_format": "" }, "msgid": "<1505296780-8444-3-git-send-email-liuhangbin@gmail.com>", "list_archive_url": null, "date": "2017-09-13T09:59:40", "name": "[PATCHv2,iproute2,2/2] lib/libnetlink: update rtnl_talk to support malloc buff at run time", "commit_ref": null, "pull_url": null, "state": "superseded", "archived": true, "hash": "a383d09c22f2d4354dddaaf7c54fd81d2b1c9f40", "submitter": { "id": 15639, "url": "http://patchwork.ozlabs.org/api/people/15639/?format=api", "name": "Hangbin Liu", "email": "liuhangbin@gmail.com" }, "delegate": { "id": 389, "url": "http://patchwork.ozlabs.org/api/users/389/?format=api", "username": "shemminger", "first_name": "stephen", "last_name": "hemminger", "email": "shemminger@vyatta.com" }, "mbox": "http://patchwork.ozlabs.org/project/netdev/patch/1505296780-8444-3-git-send-email-liuhangbin@gmail.com/mbox/", "series": [ { "id": 2859, "url": "http://patchwork.ozlabs.org/api/series/2859/?format=api", "web_url": "http://patchwork.ozlabs.org/project/netdev/list/?series=2859", "date": "2017-09-13T09:59:38", "name": "libnetlink: malloc correct buff at run time", "version": 1, "mbox": "http://patchwork.ozlabs.org/series/2859/mbox/" } ], "comments": "http://patchwork.ozlabs.org/api/patches/813281/comments/", "check": "pending", "checks": "http://patchwork.ozlabs.org/api/patches/813281/checks/", "tags": {}, "related": [], "headers": { "Return-Path": "<netdev-owner@vger.kernel.org>", "X-Original-To": "patchwork-incoming@ozlabs.org", "Delivered-To": "patchwork-incoming@ozlabs.org", "Authentication-Results": [ "ozlabs.org;\n\tspf=none (mailfrom) smtp.mailfrom=vger.kernel.org\n\t(client-ip=209.132.180.67; helo=vger.kernel.org;\n\tenvelope-from=netdev-owner@vger.kernel.org;\n\treceiver=<UNKNOWN>)", "ozlabs.org; dkim=pass (2048-bit key;\n\tunprotected) header.d=gmail.com header.i=@gmail.com\n\theader.b=\"bQwolN+v\"; dkim-atps=neutral" ], "Received": [ "from vger.kernel.org (vger.kernel.org [209.132.180.67])\n\tby ozlabs.org (Postfix) with ESMTP id 3xscc51wsWz9s9Y\n\tfor <patchwork-incoming@ozlabs.org>;\n\tWed, 13 Sep 2017 20:00:37 +1000 (AEST)", "(majordomo@vger.kernel.org) by vger.kernel.org via listexpand\n\tid S1752098AbdIMKAe (ORCPT <rfc822;patchwork-incoming@ozlabs.org>);\n\tWed, 13 Sep 2017 06:00:34 -0400", "from mail-pg0-f68.google.com ([74.125.83.68]:38692 \"EHLO\n\tmail-pg0-f68.google.com\" rhost-flags-OK-OK-OK-OK) by vger.kernel.org\n\twith ESMTP id S1751317AbdIMKAX (ORCPT\n\t<rfc822;netdev@vger.kernel.org>); Wed, 13 Sep 2017 06:00:23 -0400", "by mail-pg0-f68.google.com with SMTP id m30so2461429pgn.5\n\tfor <netdev@vger.kernel.org>; Wed, 13 Sep 2017 03:00:22 -0700 (PDT)", "from leo.usersys.redhat.com ([209.132.188.80])\n\tby smtp.gmail.com with ESMTPSA id\n\ts62sm26284740pfe.91.2017.09.13.03.00.19\n\t(version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128);\n\tWed, 13 Sep 2017 03:00:21 -0700 (PDT)" ], "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=gmail.com; s=20161025;\n\th=from:to:cc:subject:date:message-id:in-reply-to:references;\n\tbh=PgVxbIbq45wU7riLsx03FqQqOW5ycFYhLWv+I7NRib0=;\n\tb=bQwolN+vPvpswdsDyOZL3sl8vVbDEci+AK6oDCGHuI8TJCVPuaFj7fBPtJnNOoS63L\n\t/kAHPSuVOC1+qOBOxmjxIT9Fi4S8amSoiAGIHSd/YXpTUHUtjDuEF1mUp/MKRmDcRPWD\n\tcZNfs3ZPsxcpSCzDZLfDe9ocgKeHMCanYMLIH8IxZtsEOHkO/9cqHgK81Pnjf6/hzQAp\n\tU30zjD70Vy85d2egb8MJ5sJsCM8wef5cAq85FMOqY/qcU3/S5ce2eoN4EvqJNBY1Epxe\n\t0qLKG3cvA72oFtFBTQf4oBI5ueh3oJBgIHK+2dMOy8xAcEND2+MpvHchn65gJFu+WUKG\n\tTvLQ==", "X-Google-DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n\td=1e100.net; s=20161025;\n\th=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to\n\t:references;\n\tbh=PgVxbIbq45wU7riLsx03FqQqOW5ycFYhLWv+I7NRib0=;\n\tb=MYMJFpgl0LBq3/CDsGZ1hwtLeQ/yLW6QELSJ6jF8tPrORLESW45PdubLZbzrylhzeb\n\tFlsqJn5ow2MHZZXENj8q2FszZrfGevb8a6/ST7p/K5ZFzvZsOrm0DRqY3Bf/J6JrWYH4\n\t+26rvqLejENIazfRUtzyWL9HR5R1JnNCEEFsTPGshyEjkHSWfgtXGsq4kKjTV5+OcMno\n\tMe56pp18abUdWfndtYzy1/riLpi3ap7kM8rqjEW05qy8SrJ58vmBaYxitFfO+4T77INz\n\ttO2TFWdCPeq6GRXJrGVxorJmFO/Qt3ExDes1/Fi3WqwlSZfMUU3hnzmtPtybNYmhayOI\n\tagBg==", "X-Gm-Message-State": "AHPjjUisjHGe19GZtuz5l+VwZqNLNIPZ3pyZNy3Ytrfn5eEZ3rPMpyNr\n\tzjgkqc0nTYSi4fJj", "X-Google-Smtp-Source": "ADKCNb7iZ7tvLAJtSJdk0XtGbFarR+9l5Nqh/Jcf8Bly5lp035Pb8Wm8GWfoKwjjNpZirvjsYk929A==", "X-Received": "by 10.98.206.15 with SMTP id y15mr12433379pfg.25.1505296821711; \n\tWed, 13 Sep 2017 03:00:21 -0700 (PDT)", "From": "Hangbin Liu <liuhangbin@gmail.com>", "To": "netdev@vger.kernel.org", "Cc": "Stephen Hemminger <stephen@networkplumber.org>,\n\tMichal Kubecek <mkubecek@suse.cz>, Phil Sutter <phil@nwl.cc>,\n\tHangbin Liu <liuhangbin@gmail.com>", "Subject": "[PATCHv2 iproute2 2/2] lib/libnetlink: update rtnl_talk to support\n\tmalloc buff at run time", "Date": "Wed, 13 Sep 2017 17:59:40 +0800", "Message-Id": "<1505296780-8444-3-git-send-email-liuhangbin@gmail.com>", "X-Mailer": "git-send-email 2.5.5", "In-Reply-To": "<1505296780-8444-1-git-send-email-liuhangbin@gmail.com>", "References": "<1505296780-8444-1-git-send-email-liuhangbin@gmail.com>", "Sender": "netdev-owner@vger.kernel.org", "Precedence": "bulk", "List-ID": "<netdev.vger.kernel.org>", "X-Mailing-List": "netdev@vger.kernel.org" }, "content": "This is an update for 460c03f3f3cc (\"iplink: double the buffer size also in\niplink_get()\"). After update, we will not need to double the buffer size\nevery time when VFs number increased.\n\nWith call like rtnl_talk(&rth, &req.n, NULL, 0), we can simply remove the\nlength parameter.\n\nWith call like rtnl_talk(&rth, nlh, nlh, sizeof(req), I add a new variable\nanswer to avoid overwrite data in nlh, because it may has more info after\nnlh. also this will avoid nlh buffer not enough issue.\n\nWe need to free answer after using.\n\nSigned-off-by: Hangbin Liu <liuhangbin@gmail.com>\nSigned-off-by: Phil Sutter <phil@nwl.cc>\n---\n bridge/fdb.c | 2 +-\n bridge/link.c | 2 +-\n bridge/mdb.c | 2 +-\n bridge/vlan.c | 2 +-\n genl/ctrl.c | 19 ++++++++++++-------\n include/libnetlink.h | 6 +++---\n ip/ipaddress.c | 4 ++--\n ip/ipaddrlabel.c | 4 ++--\n ip/ipfou.c | 4 ++--\n ip/ipila.c | 4 ++--\n ip/ipl2tp.c | 8 ++++----\n ip/iplink.c | 38 +++++++++++++++++++-------------------\n ip/iplink_vrf.c | 44 ++++++++++++++++++++------------------------\n ip/ipmacsec.c | 2 +-\n ip/ipneigh.c | 2 +-\n ip/ipnetns.c | 23 ++++++++++++++---------\n ip/ipntable.c | 2 +-\n ip/iproute.c | 26 +++++++++++++++++---------\n ip/iprule.c | 6 +++---\n ip/ipseg6.c | 8 +++++---\n ip/iptoken.c | 2 +-\n ip/link_gre.c | 11 +++++++----\n ip/link_gre6.c | 11 +++++++----\n ip/link_ip6tnl.c | 11 +++++++----\n ip/link_iptnl.c | 10 ++++++----\n ip/link_vti.c | 11 +++++++----\n ip/link_vti6.c | 11 +++++++----\n ip/tcp_metrics.c | 8 +++++---\n ip/xfrm_policy.c | 25 +++++++++++++------------\n ip/xfrm_state.c | 30 ++++++++++++++++--------------\n lib/libgenl.c | 9 +++++++--\n lib/libnetlink.c | 24 +++++++++++-------------\n misc/ss.c | 2 +-\n tc/m_action.c | 12 ++++++------\n tc/tc_class.c | 2 +-\n tc/tc_filter.c | 8 +++++---\n tc/tc_qdisc.c | 2 +-\n 37 files changed, 220 insertions(+), 177 deletions(-)", "diff": "diff --git a/bridge/fdb.c b/bridge/fdb.c\nindex e5cebf9..807914f 100644\n--- a/bridge/fdb.c\n+++ b/bridge/fdb.c\n@@ -535,7 +535,7 @@ static int fdb_modify(int cmd, int flags, int argc, char **argv)\n \t\treturn -1;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -1;\n \n \treturn 0;\ndiff --git a/bridge/link.c b/bridge/link.c\nindex 93472ad..cc29a2a 100644\n--- a/bridge/link.c\n+++ b/bridge/link.c\n@@ -426,7 +426,7 @@ static int brlink_modify(int argc, char **argv)\n \t\taddattr_nest_end(&req.n, nest);\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -1;\n \n \treturn 0;\ndiff --git a/bridge/mdb.c b/bridge/mdb.c\nindex 748091b..f38e326 100644\n--- a/bridge/mdb.c\n+++ b/bridge/mdb.c\n@@ -440,7 +440,7 @@ static int mdb_modify(int cmd, int flags, int argc, char **argv)\n \tentry.vid = vid;\n \taddattr_l(&req.n, sizeof(req), MDBA_SET_ENTRY, &entry, sizeof(entry));\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -1;\n \n \treturn 0;\ndiff --git a/bridge/vlan.c b/bridge/vlan.c\nindex ebcdace..5d68359 100644\n--- a/bridge/vlan.c\n+++ b/bridge/vlan.c\n@@ -133,7 +133,7 @@ static int vlan_modify(int cmd, int argc, char **argv)\n \n \taddattr_nest_end(&req.n, afspec);\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -1;\n \n \treturn 0;\ndiff --git a/genl/ctrl.c b/genl/ctrl.c\nindex 448988e..a6d31b0 100644\n--- a/genl/ctrl.c\n+++ b/genl/ctrl.c\n@@ -55,6 +55,7 @@ int genl_ctrl_resolve_family(const char *family)\n \t};\n \tstruct nlmsghdr *nlh = &req.n;\n \tstruct genlmsghdr *ghdr = &req.g;\n+\tstruct nlmsghdr *answer = NULL;\n \n \tif (rtnl_open_byproto(&rth, 0, NETLINK_GENERIC) < 0) {\n \t\tfprintf(stderr, \"Cannot open generic netlink socket\\n\");\n@@ -63,19 +64,19 @@ int genl_ctrl_resolve_family(const char *family)\n \n \taddattr_l(nlh, 128, CTRL_ATTR_FAMILY_NAME, family, strlen(family) + 1);\n \n-\tif (rtnl_talk(&rth, nlh, nlh, sizeof(req)) < 0) {\n+\tif (rtnl_talk(&rth, nlh, &answer) < 0) {\n \t\tfprintf(stderr, \"Error talking to the kernel\\n\");\n \t\tgoto errout;\n \t}\n \n \t{\n \t\tstruct rtattr *tb[CTRL_ATTR_MAX + 1];\n-\t\tint len = nlh->nlmsg_len;\n+\t\tint len = answer->nlmsg_len;\n \t\tstruct rtattr *attrs;\n \n-\t\tif (nlh->nlmsg_type != GENL_ID_CTRL) {\n+\t\tif (answer->nlmsg_type != GENL_ID_CTRL) {\n \t\t\tfprintf(stderr, \"Not a controller message, nlmsg_len=%d \"\n-\t\t\t\t\"nlmsg_type=0x%x\\n\", nlh->nlmsg_len, nlh->nlmsg_type);\n+\t\t\t\t\"nlmsg_type=0x%x\\n\", answer->nlmsg_len, answer->nlmsg_type);\n \t\t\tgoto errout;\n \t\t}\n \n@@ -88,10 +89,11 @@ int genl_ctrl_resolve_family(const char *family)\n \n \t\tif (len < 0) {\n \t\t\tfprintf(stderr, \"wrong controller message len %d\\n\", len);\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tattrs = (struct rtattr *) ((char *) ghdr + GENL_HDRLEN);\n+\t\tattrs = (struct rtattr *) ((char *) answer + NLMSG_LENGTH(GENL_HDRLEN));\n \t\tparse_rtattr(tb, CTRL_ATTR_MAX, attrs, len);\n \n \t\tif (tb[CTRL_ATTR_FAMILY_ID] == NULL) {\n@@ -103,6 +105,7 @@ int genl_ctrl_resolve_family(const char *family)\n \t}\n \n errout:\n+\tfree(answer);\n \trtnl_close(&rth);\n \treturn ret;\n }\n@@ -299,6 +302,7 @@ static int ctrl_list(int cmd, int argc, char **argv)\n \t\t.g.cmd = CTRL_CMD_GETFAMILY,\n \t};\n \tstruct nlmsghdr *nlh = &req.n;\n+\tstruct nlmsghdr *answer = NULL;\n \n \tif (rtnl_open_byproto(&rth, 0, NETLINK_GENERIC) < 0) {\n \t\tfprintf(stderr, \"Cannot open generic netlink socket\\n\");\n@@ -331,12 +335,12 @@ static int ctrl_list(int cmd, int argc, char **argv)\n \t\t\tgoto ctrl_done;\n \t\t}\n \n-\t\tif (rtnl_talk(&rth, nlh, nlh, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, nlh, &answer) < 0) {\n \t\t\tfprintf(stderr, \"Error talking to the kernel\\n\");\n \t\t\tgoto ctrl_done;\n \t\t}\n \n-\t\tif (print_ctrl2(NULL, nlh, (void *) stdout) < 0) {\n+\t\tif (print_ctrl2(NULL, answer, (void *) stdout) < 0) {\n \t\t\tfprintf(stderr, \"Dump terminated\\n\");\n \t\t\tgoto ctrl_done;\n \t\t}\n@@ -358,6 +362,7 @@ static int ctrl_list(int cmd, int argc, char **argv)\n \n \tret = 0;\n ctrl_done:\n+\tfree(answer);\n \trtnl_close(&rth);\n \treturn ret;\n }\ndiff --git a/include/libnetlink.h b/include/libnetlink.h\nindex 69257f0..77b6260 100644\n--- a/include/libnetlink.h\n+++ b/include/libnetlink.h\n@@ -93,13 +93,13 @@ int rtnl_dump_filter_nc(struct rtnl_handle *rth,\n #define rtnl_dump_filter(rth, filter, arg) \\\n \trtnl_dump_filter_nc(rth, filter, arg, 0)\n int rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t struct nlmsghdr *answer, size_t len)\n+\t struct nlmsghdr **answer)\n \t__attribute__((warn_unused_result));\n int rtnl_talk_extack(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t struct nlmsghdr *answer, size_t len, nl_ext_ack_fn_t errfn)\n+\t struct nlmsghdr **answer, nl_ext_ack_fn_t errfn)\n \t__attribute__((warn_unused_result));\n int rtnl_talk_suppress_rtnl_errmsg(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t\t\t\t struct nlmsghdr *answer, size_t len)\n+\t\t\t\t struct nlmsghdr **answer)\n \t__attribute__((warn_unused_result));\n int rtnl_send(struct rtnl_handle *rth, const void *buf, int)\n \t__attribute__((warn_unused_result));\ndiff --git a/ip/ipaddress.c b/ip/ipaddress.c\nindex 9797145..019dd1e 100644\n--- a/ip/ipaddress.c\n+++ b/ip/ipaddress.c\n@@ -1824,7 +1824,7 @@ static int restore_handler(const struct sockaddr_nl *nl,\n \n \tll_init_map(&rth);\n \n-\tret = rtnl_talk(&rth, n, n, sizeof(*n));\n+\tret = rtnl_talk(&rth, n, NULL);\n \tif ((ret < 0) && (errno == EEXIST))\n \t\tret = 0;\n \n@@ -2520,7 +2520,7 @@ static int ipaddr_modify(int cmd, int flags, int argc, char **argv)\n \t\treturn -1;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/ipaddrlabel.c b/ip/ipaddrlabel.c\nindex 1d324da..6ea9bff 100644\n--- a/ip/ipaddrlabel.c\n+++ b/ip/ipaddrlabel.c\n@@ -176,7 +176,7 @@ static int ipaddrlabel_modify(int cmd, int argc, char **argv)\n \tif (req.ifal.ifal_family == AF_UNSPEC)\n \t\treq.ifal.ifal_family = AF_INET6;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -203,7 +203,7 @@ static int flush_addrlabel(const struct sockaddr_nl *who, struct nlmsghdr *n, vo\n \t\tif (rtnl_open(&rth2, 0) < 0)\n \t\t\treturn -1;\n \n-\t\tif (rtnl_talk(&rth2, n, NULL, 0) < 0)\n+\t\tif (rtnl_talk(&rth2, n, NULL) < 0)\n \t\t\treturn -2;\n \n \t\trtnl_close(&rth2);\ndiff --git a/ip/ipfou.c b/ip/ipfou.c\nindex 00dbe15..23000dc 100644\n--- a/ip/ipfou.c\n+++ b/ip/ipfou.c\n@@ -116,7 +116,7 @@ static int do_add(int argc, char **argv)\n \n \tfou_parse_opt(argc, argv, &req.n, true);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -128,7 +128,7 @@ static int do_del(int argc, char **argv)\n \n \tfou_parse_opt(argc, argv, &req.n, false);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/ipila.c b/ip/ipila.c\nindex 843cc16..0403fc4 100644\n--- a/ip/ipila.c\n+++ b/ip/ipila.c\n@@ -220,7 +220,7 @@ static int do_add(int argc, char **argv)\n \n \tila_parse_opt(argc, argv, &req.n, true);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -232,7 +232,7 @@ static int do_del(int argc, char **argv)\n \n \tila_parse_opt(argc, argv, &req.n, false);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/ipl2tp.c b/ip/ipl2tp.c\nindex 88664c9..742adbe 100644\n--- a/ip/ipl2tp.c\n+++ b/ip/ipl2tp.c\n@@ -129,7 +129,7 @@ static int create_tunnel(struct l2tp_parm *p)\n \t\t\taddattr(&req.n, 1024, L2TP_ATTR_UDP_ZERO_CSUM6_RX);\n \t}\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -142,7 +142,7 @@ static int delete_tunnel(struct l2tp_parm *p)\n \n \taddattr32(&req.n, 128, L2TP_ATTR_CONN_ID, p->tunnel_id);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -185,7 +185,7 @@ static int create_session(struct l2tp_parm *p)\n \tif (p->ifname && p->ifname[0])\n \t\taddattrstrz(&req.n, 1024, L2TP_ATTR_IFNAME, p->ifname);\n \n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -198,7 +198,7 @@ static int delete_session(struct l2tp_parm *p)\n \n \taddattr32(&req.n, 1024, L2TP_ATTR_CONN_ID, p->tunnel_id);\n \taddattr32(&req.n, 1024, L2TP_ATTR_SESSION_ID, p->session_id);\n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/iplink.c b/ip/iplink.c\nindex ff5b56c..21a22cd 100644\n--- a/ip/iplink.c\n+++ b/ip/iplink.c\n@@ -249,19 +249,26 @@ static int nl_get_ll_addr_len(unsigned int dev_index)\n \t\t\t.ifi_index = dev_index,\n \t\t}\n \t};\n+\tstruct nlmsghdr *answer;\n \tstruct rtattr *tb[IFLA_MAX+1];\n \n-\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0)\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\treturn -1;\n \n-\tlen = req.n.nlmsg_len - NLMSG_LENGTH(sizeof(req.i));\n-\tif (len < 0)\n+\tlen = answer->nlmsg_len - NLMSG_LENGTH(sizeof(struct ifinfomsg));\n+\tif (len < 0) {\n+\t\tfree(answer);\n \t\treturn -1;\n+\t}\n \n-\tparse_rtattr_flags(tb, IFLA_MAX, IFLA_RTA(&req.i), len, NLA_F_NESTED);\n-\tif (!tb[IFLA_ADDRESS])\n+\tparse_rtattr_flags(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)),\n+\t\t\t len, NLA_F_NESTED);\n+\tif (!tb[IFLA_ADDRESS]) {\n+\t\tfree(answer);\n \t\treturn -1;\n+\t}\n \n+\tfree(answer);\n \treturn RTA_PAYLOAD(tb[IFLA_ADDRESS]);\n }\n \n@@ -913,7 +920,7 @@ static int iplink_modify(int cmd, unsigned int flags, int argc, char **argv)\n \n \t\t\treq.i.ifi_index = 0;\n \t\t\taddattr32(&req.n, sizeof(req), IFLA_GROUP, group);\n-\t\t\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\t\t\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\t\t\treturn -2;\n \t\t\treturn 0;\n \t\t}\n@@ -1008,7 +1015,7 @@ static int iplink_modify(int cmd, unsigned int flags, int argc, char **argv)\n \t\treturn -1;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -1023,10 +1030,7 @@ int iplink_get(unsigned int flags, char *name, __u32 filt_mask)\n \t\t.n.nlmsg_type = RTM_GETLINK,\n \t\t.i.ifi_family = preferred_family,\n \t};\n-\tstruct {\n-\t\tstruct nlmsghdr n;\n-\t\tchar buf[32768];\n-\t} answer;\n+\tstruct nlmsghdr *answer;\n \n \tif (name) {\n \t\tlen = strlen(name) + 1;\n@@ -1039,21 +1043,17 @@ int iplink_get(unsigned int flags, char *name, __u32 filt_mask)\n \t}\n \taddattr32(&req.n, sizeof(req), IFLA_EXT_MASK, filt_mask);\n \n-\tif (rtnl_talk(&rth, &req.n, &answer.n, sizeof(answer)) < 0)\n-\t\treturn -2;\n-\tif (answer.n.nlmsg_len > sizeof(answer.buf)) {\n-\t\tfprintf(stderr, \"Message truncated from %u to %lu\\n\",\n-\t\t\tanswer.n.nlmsg_len, sizeof(answer.buf));\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\treturn -2;\n-\t}\n \n \topen_json_object(NULL);\n \tif (brief)\n-\t\tprint_linkinfo_brief(NULL, &answer.n, stdout, NULL);\n+\t\tprint_linkinfo_brief(NULL, answer, stdout, NULL);\n \telse\n-\t\tprint_linkinfo(NULL, &answer.n, stdout);\n+\t\tprint_linkinfo(NULL, answer, stdout);\n \tclose_json_object();\n \n+\tfree(answer);\n \treturn 0;\n }\n \ndiff --git a/ip/iplink_vrf.c b/ip/iplink_vrf.c\nindex 7a1bb5e..e9dd0df 100644\n--- a/ip/iplink_vrf.c\n+++ b/ip/iplink_vrf.c\n@@ -119,10 +119,7 @@ __u32 ipvrf_get_table(const char *name)\n \t\t\t.ifi_family = preferred_family,\n \t\t},\n \t};\n-\tstruct {\n-\t\tstruct nlmsghdr n;\n-\t\tchar buf[8192];\n-\t} answer;\n+\tstruct nlmsghdr *answer;\n \tstruct rtattr *tb[IFLA_MAX+1];\n \tstruct rtattr *li[IFLA_INFO_MAX+1];\n \tstruct rtattr *vrf_attr[IFLA_VRF_MAX + 1];\n@@ -132,8 +129,7 @@ __u32 ipvrf_get_table(const char *name)\n \n \taddattr_l(&req.n, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);\n \n-\tif (rtnl_talk_suppress_rtnl_errmsg(&rth, &req.n,\n-\t\t\t\t\t &answer.n, sizeof(answer)) < 0) {\n+\tif (rtnl_talk_suppress_rtnl_errmsg(&rth, &req.n, &answer) < 0) {\n \t\t/* special case \"default\" vrf to be the main table */\n \t\tif (errno == ENODEV && !strcmp(name, \"default\"))\n \t\t\tif (rtnl_rttable_a2n(&tb_id, \"main\"))\n@@ -143,25 +139,25 @@ __u32 ipvrf_get_table(const char *name)\n \t\treturn tb_id;\n \t}\n \n-\tifi = NLMSG_DATA(&answer.n);\n-\tlen = answer.n.nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));\n+\tifi = NLMSG_DATA(answer);\n+\tlen = answer->nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));\n \tif (len < 0) {\n \t\tfprintf(stderr, \"BUG: Invalid response to link query.\\n\");\n-\t\treturn 0;\n+\t\tgoto out;\n \t}\n \n \tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);\n \n \tif (!tb[IFLA_LINKINFO])\n-\t\treturn 0;\n+\t\tgoto out;\n \n \tparse_rtattr_nested(li, IFLA_INFO_MAX, tb[IFLA_LINKINFO]);\n \n \tif (!li[IFLA_INFO_KIND] || !li[IFLA_INFO_DATA])\n-\t\treturn 0;\n+\t\tgoto out;\n \n \tif (strcmp(RTA_DATA(li[IFLA_INFO_KIND]), \"vrf\"))\n-\t\treturn 0;\n+\t\tgoto out;\n \n \tparse_rtattr_nested(vrf_attr, IFLA_VRF_MAX, li[IFLA_INFO_DATA]);\n \tif (vrf_attr[IFLA_VRF_TABLE])\n@@ -170,6 +166,8 @@ __u32 ipvrf_get_table(const char *name)\n \tif (!tb_id)\n \t\tfprintf(stderr, \"BUG: VRF %s is missing table id\\n\", name);\n \n+out:\n+\tfree(answer);\n \treturn tb_id;\n }\n \n@@ -189,10 +187,7 @@ int name_is_vrf(const char *name)\n \t\t\t.ifi_family = preferred_family,\n \t\t},\n \t};\n-\tstruct {\n-\t\tstruct nlmsghdr n;\n-\t\tchar buf[8192];\n-\t} answer;\n+\tstruct nlmsghdr *answer;\n \tstruct rtattr *tb[IFLA_MAX+1];\n \tstruct rtattr *li[IFLA_INFO_MAX+1];\n \tstruct ifinfomsg *ifi;\n@@ -200,29 +195,30 @@ int name_is_vrf(const char *name)\n \n \taddattr_l(&req.n, sizeof(req), IFLA_IFNAME, name, strlen(name) + 1);\n \n-\tif (rtnl_talk_suppress_rtnl_errmsg(&rth, &req.n,\n-\t\t\t\t\t &answer.n, sizeof(answer)) < 0)\n+\tif (rtnl_talk_suppress_rtnl_errmsg(&rth, &req.n, &answer) < 0)\n \t\treturn 0;\n \n-\tifi = NLMSG_DATA(&answer.n);\n-\tlen = answer.n.nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));\n+\tifi = NLMSG_DATA(answer);\n+\tlen = answer->nlmsg_len - NLMSG_LENGTH(sizeof(*ifi));\n \tif (len < 0) {\n \t\tfprintf(stderr, \"BUG: Invalid response to link query.\\n\");\n-\t\treturn 0;\n+\t\tgoto out;\n \t}\n \n \tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(ifi), len);\n \n \tif (!tb[IFLA_LINKINFO])\n-\t\treturn 0;\n+\t\tgoto out;\n \n \tparse_rtattr_nested(li, IFLA_INFO_MAX, tb[IFLA_LINKINFO]);\n \n \tif (!li[IFLA_INFO_KIND])\n-\t\treturn 0;\n+\t\tgoto out;\n \n \tif (strcmp(RTA_DATA(li[IFLA_INFO_KIND]), \"vrf\"))\n-\t\treturn 0;\n+\t\tgoto out;\n \n+out:\n+\tfree(answer);\n \treturn ifi->ifi_index;\n }\ndiff --git a/ip/ipmacsec.c b/ip/ipmacsec.c\nindex ecc371a..345a707 100644\n--- a/ip/ipmacsec.c\n+++ b/ip/ipmacsec.c\n@@ -421,7 +421,7 @@ static int do_modify_nl(enum cmd c, enum macsec_nl_commands cmd, int ifindex,\n \taddattr_nest_end(&req.n, attr_sa);\n \n talk:\n-\tif (rtnl_talk(&genl_rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&genl_rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/ipneigh.c b/ip/ipneigh.c\nindex 9c38a60..32f2d55 100644\n--- a/ip/ipneigh.c\n+++ b/ip/ipneigh.c\n@@ -184,7 +184,7 @@ static int ipneigh_modify(int cmd, int flags, int argc, char **argv)\n \t\treturn -1;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \treturn 0;\ndiff --git a/ip/ipnetns.c b/ip/ipnetns.c\nindex afb4978..bc70997 100644\n--- a/ip/ipnetns.c\n+++ b/ip/ipnetns.c\n@@ -95,12 +95,13 @@ static int get_netnsid_from_name(const char *name)\n \t\tstruct nlmsghdr n;\n \t\tstruct rtgenmsg g;\n \t\tchar buf[1024];\n-\t} answer, req = {\n+\t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(struct rtgenmsg)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n \t\t.n.nlmsg_type = RTM_GETNSID,\n \t\t.g.rtgen_family = AF_UNSPEC,\n \t};\n+\tstruct nlmsghdr *answer;\n \tstruct rtattr *tb[NETNSA_MAX + 1];\n \tstruct rtgenmsg *rthdr;\n \tint len, fd;\n@@ -110,26 +111,30 @@ static int get_netnsid_from_name(const char *name)\n \t\treturn fd;\n \n \taddattr32(&req.n, 1024, NETNSA_FD, fd);\n-\tif (rtnl_talk(&rtnsh, &req.n, &answer.n, sizeof(answer)) < 0) {\n+\tif (rtnl_talk(&rtnsh, &req.n, &answer) < 0) {\n \t\tclose(fd);\n \t\treturn -2;\n \t}\n \tclose(fd);\n \n \t/* Validate message and parse attributes */\n-\tif (answer.n.nlmsg_type == NLMSG_ERROR)\n-\t\treturn -1;\n+\tif (answer->nlmsg_type == NLMSG_ERROR)\n+\t\tgoto err_out;\n \n-\trthdr = NLMSG_DATA(&answer.n);\n-\tlen = answer.n.nlmsg_len - NLMSG_SPACE(sizeof(*rthdr));\n+\trthdr = NLMSG_DATA(answer);\n+\tlen = answer->nlmsg_len - NLMSG_SPACE(sizeof(*rthdr));\n \tif (len < 0)\n-\t\treturn -1;\n+\t\tgoto err_out;\n \n \tparse_rtattr(tb, NETNSA_MAX, NETNS_RTA(rthdr), len);\n \n-\tif (tb[NETNSA_NSID])\n+\tif (tb[NETNSA_NSID]) {\n+\t\tfree(answer);\n \t\treturn rta_getattr_u32(tb[NETNSA_NSID]);\n+\t}\n \n+err_out:\n+\tfree(answer);\n \treturn -1;\n }\n \n@@ -689,7 +694,7 @@ static int set_netnsid_from_name(const char *name, int nsid)\n \n \taddattr32(&req.n, 1024, NETNSA_FD, fd);\n \taddattr32(&req.n, 1024, NETNSA_NSID, nsid);\n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\terr = -2;\n \n \tclose(fd);\ndiff --git a/ip/ipntable.c b/ip/ipntable.c\nindex 88236ce..2f72c98 100644\n--- a/ip/ipntable.c\n+++ b/ip/ipntable.c\n@@ -304,7 +304,7 @@ static int ipntable_modify(int cmd, int flags, int argc, char **argv)\n \t\t\t RTA_PAYLOAD(parms_rta));\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \treturn 0;\ndiff --git a/ip/iproute.c b/ip/iproute.c\nindex a8733f4..e45a5f2 100644\n--- a/ip/iproute.c\n+++ b/ip/iproute.c\n@@ -1300,7 +1300,7 @@ static int iproute_modify(int cmd, unsigned int flags, int argc, char **argv)\n \tif (!type_ok && req.r.rtm_family == AF_MPLS)\n \t\treq.r.rtm_type = RTN_UNICAST;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\n@@ -1680,6 +1680,7 @@ static int iproute_get(int argc, char **argv)\n \t};\n \tchar *idev = NULL;\n \tchar *odev = NULL;\n+\tstruct nlmsghdr *answer;\n \tint connected = 0;\n \tint fib_match = 0;\n \tint from_ok = 0;\n@@ -1800,26 +1801,29 @@ static int iproute_get(int argc, char **argv)\n \tif (fib_match)\n \t\treq.r.rtm_flags |= RTM_F_FIB_MATCH;\n \n-\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0)\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\treturn -2;\n \n \tif (connected && !from_ok) {\n-\t\tstruct rtmsg *r = NLMSG_DATA(&req.n);\n-\t\tint len = req.n.nlmsg_len;\n+\t\tstruct rtmsg *r = NLMSG_DATA(answer);\n+\t\tint len = answer->nlmsg_len;\n \t\tstruct rtattr *tb[RTA_MAX+1];\n \n-\t\tif (print_route(NULL, &req.n, (void *)stdout) < 0) {\n+\t\tif (print_route(NULL, answer, (void *)stdout) < 0) {\n \t\t\tfprintf(stderr, \"An error :-)\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tif (req.n.nlmsg_type != RTM_NEWROUTE) {\n+\t\tif (answer->nlmsg_type != RTM_NEWROUTE) {\n \t\t\tfprintf(stderr, \"Not a route?\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \t\tlen -= NLMSG_LENGTH(sizeof(*r));\n \t\tif (len < 0) {\n \t\t\tfprintf(stderr, \"Wrong len %d\\n\", len);\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n@@ -1830,6 +1834,7 @@ static int iproute_get(int argc, char **argv)\n \t\t\tr->rtm_src_len = 8*RTA_PAYLOAD(tb[RTA_PREFSRC]);\n \t\t} else if (!tb[RTA_SRC]) {\n \t\t\tfprintf(stderr, \"Failed to connect the route\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \t\tif (!odev && tb[RTA_OIF])\n@@ -1843,15 +1848,18 @@ static int iproute_get(int argc, char **argv)\n \t\treq.n.nlmsg_flags = NLM_F_REQUEST;\n \t\treq.n.nlmsg_type = RTM_GETROUTE;\n \n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0)\n+\t\tfree(answer);\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\t\treturn -2;\n \t}\n \n-\tif (print_route(NULL, &req.n, (void *)stdout) < 0) {\n+\tif (print_route(NULL, answer, (void *)stdout) < 0) {\n \t\tfprintf(stderr, \"An error :-)\\n\");\n+\t\tfree(answer);\n \t\treturn -1;\n \t}\n \n+\tfree(answer);\n \treturn 0;\n }\n \n@@ -1895,7 +1903,7 @@ restore:\n \n \tll_init_map(&rth);\n \n-\tret = rtnl_talk(&rth, n, n, sizeof(*n));\n+\tret = rtnl_talk(&rth, n, NULL);\n \tif ((ret < 0) && (errno == EEXIST))\n \t\tret = 0;\n \ndiff --git a/ip/iprule.c b/ip/iprule.c\nindex 8313138..e64b4d7 100644\n--- a/ip/iprule.c\n+++ b/ip/iprule.c\n@@ -393,7 +393,7 @@ static int flush_rule(const struct sockaddr_nl *who, struct nlmsghdr *n,\n \t\tif (rtnl_open(&rth2, 0) < 0)\n \t\t\treturn -1;\n \n-\t\tif (rtnl_talk(&rth2, n, NULL, 0) < 0)\n+\t\tif (rtnl_talk(&rth2, n, NULL) < 0)\n \t\t\treturn -2;\n \n \t\trtnl_close(&rth2);\n@@ -553,7 +553,7 @@ static int restore_handler(const struct sockaddr_nl *nl,\n \n \tll_init_map(&rth);\n \n-\tret = rtnl_talk(&rth, n, n, sizeof(*n));\n+\tret = rtnl_talk(&rth, n, NULL);\n \tif ((ret < 0) && (errno == EEXIST))\n \t\tret = 0;\n \n@@ -760,7 +760,7 @@ static int iprule_modify(int cmd, int argc, char **argv)\n \tif (!table_ok && cmd == RTM_NEWRULE)\n \t\treq.r.rtm_table = RT_TABLE_MAIN;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/ipseg6.c b/ip/ipseg6.c\nindex a8f5c69..461a3c1 100644\n--- a/ip/ipseg6.c\n+++ b/ip/ipseg6.c\n@@ -125,6 +125,7 @@ static int process_msg(const struct sockaddr_nl *who, struct nlmsghdr *n,\n static int seg6_do_cmd(void)\n {\n \tSEG6_REQUEST(req, 1024, opts.cmd, NLM_F_REQUEST);\n+\tstruct nlmsghdr *answer;\n \tint repl = 0, dump = 0;\n \n \tif (genl_family < 0) {\n@@ -163,15 +164,16 @@ static int seg6_do_cmd(void)\n \t}\n \n \tif (!repl && !dump) {\n-\t\tif (rtnl_talk(&grth, &req.n, NULL, 0) < 0)\n+\t\tif (rtnl_talk(&grth, &req.n, NULL) < 0)\n \t\t\treturn -1;\n \t} else if (repl) {\n-\t\tif (rtnl_talk(&grth, &req.n, &req.n, sizeof(req)) < 0)\n+\t\tif (rtnl_talk(&grth, &req.n, &answer) < 0)\n \t\t\treturn -2;\n-\t\tif (process_msg(NULL, &req.n, stdout) < 0) {\n+\t\tif (process_msg(NULL, answer, stdout) < 0) {\n \t\t\tfprintf(stderr, \"Error parsing reply\\n\");\n \t\t\texit(1);\n \t\t}\n+\t\tfree(answer);\n \t} else {\n \t\treq.n.nlmsg_flags |= NLM_F_DUMP;\n \t\treq.n.nlmsg_seq = grth.dump = ++grth.seq;\ndiff --git a/ip/iptoken.c b/ip/iptoken.c\nindex 1869f76..0528bad 100644\n--- a/ip/iptoken.c\n+++ b/ip/iptoken.c\n@@ -166,7 +166,7 @@ static int iptoken_set(int argc, char **argv, bool delete)\n \taddattr_nest_end(&req.n, afs6);\n \taddattr_nest_end(&req.n, afs);\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn -2;\n \n \treturn 0;\ndiff --git a/ip/link_gre.c b/ip/link_gre.c\nindex 9ea2970..35782ca 100644\n--- a/ip/link_gre.c\n+++ b/ip/link_gre.c\n@@ -68,7 +68,6 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[16384];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -76,6 +75,7 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *greinfo[IFLA_GRE_MAX + 1];\n@@ -100,19 +100,20 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \t__u32 erspan_idx = 0;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -177,6 +178,8 @@ get_failed:\n \n \t\tif (greinfo[IFLA_GRE_ERSPAN_INDEX])\n \t\t\terspan_idx = rta_getattr_u32(greinfo[IFLA_GRE_ERSPAN_INDEX]);\n+\n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/link_gre6.c b/ip/link_gre6.c\nindex 7d07932..2eedec8 100644\n--- a/ip/link_gre6.c\n+++ b/ip/link_gre6.c\n@@ -78,7 +78,6 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[1024];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -86,6 +85,7 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *greinfo[IFLA_GRE_MAX + 1];\n@@ -108,19 +108,20 @@ static int gre_parse_opt(struct link_util *lu, int argc, char **argv,\n \t__u32 fwmark = 0;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -180,6 +181,8 @@ get_failed:\n \n \t\tif (greinfo[IFLA_GRE_FWMARK])\n \t\t\tfwmark = rta_getattr_u32(greinfo[IFLA_GRE_FWMARK]);\n+\n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/link_ip6tnl.c b/ip/link_ip6tnl.c\nindex a419900..2f8c3f3 100644\n--- a/ip/link_ip6tnl.c\n+++ b/ip/link_ip6tnl.c\n@@ -75,7 +75,6 @@ static int ip6tunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[2048];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -83,6 +82,7 @@ static int ip6tunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *iptuninfo[IFLA_IPTUN_MAX + 1];\n@@ -103,19 +103,20 @@ static int ip6tunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \t__u32 fwmark = 0;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -158,6 +159,8 @@ get_failed:\n \n \t\tif (iptuninfo[IFLA_IPTUN_FWMARK])\n \t\t\tfwmark = rta_getattr_u32(iptuninfo[IFLA_IPTUN_FWMARK]);\n+\n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/link_iptnl.c b/ip/link_iptnl.c\nindex 6a725e9..4940b8b 100644\n--- a/ip/link_iptnl.c\n+++ b/ip/link_iptnl.c\n@@ -76,7 +76,6 @@ static int iptunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[2048];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -84,6 +83,7 @@ static int iptunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *iptuninfo[IFLA_IPTUN_MAX + 1];\n@@ -108,19 +108,20 @@ static int iptunnel_parse_opt(struct link_util *lu, int argc, char **argv,\n \t__u32 fwmark = 0;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -188,6 +189,7 @@ get_failed:\n \t\tif (iptuninfo[IFLA_IPTUN_FWMARK])\n \t\t\tfwmark = rta_getattr_u32(iptuninfo[IFLA_IPTUN_FWMARK]);\n \n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/link_vti.c b/ip/link_vti.c\nindex 8bd4d90..07ac94e 100644\n--- a/ip/link_vti.c\n+++ b/ip/link_vti.c\n@@ -53,7 +53,6 @@ static int vti_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[1024];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -61,6 +60,7 @@ static int vti_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *vtiinfo[IFLA_VTI_MAX + 1];\n@@ -73,19 +73,20 @@ static int vti_parse_opt(struct link_util *lu, int argc, char **argv,\n \tint len;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -115,6 +116,8 @@ get_failed:\n \n \t\tif (vtiinfo[IFLA_VTI_FWMARK])\n \t\t\tfwmark = rta_getattr_u32(vtiinfo[IFLA_VTI_FWMARK]);\n+\n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/link_vti6.c b/ip/link_vti6.c\nindex 8198d46..6d08bfe 100644\n--- a/ip/link_vti6.c\n+++ b/ip/link_vti6.c\n@@ -48,7 +48,6 @@ static int vti6_parse_opt(struct link_util *lu, int argc, char **argv,\n \tstruct {\n \t\tstruct nlmsghdr n;\n \t\tstruct ifinfomsg i;\n-\t\tchar buf[1024];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(*ifi)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n@@ -56,6 +55,7 @@ static int vti6_parse_opt(struct link_util *lu, int argc, char **argv,\n \t\t.i.ifi_family = preferred_family,\n \t\t.i.ifi_index = ifi->ifi_index,\n \t};\n+\tstruct nlmsghdr *answer = NULL;\n \tstruct rtattr *tb[IFLA_MAX + 1];\n \tstruct rtattr *linkinfo[IFLA_INFO_MAX+1];\n \tstruct rtattr *vtiinfo[IFLA_VTI_MAX + 1];\n@@ -68,19 +68,20 @@ static int vti6_parse_opt(struct link_util *lu, int argc, char **argv,\n \tint len;\n \n \tif (!(n->nlmsg_flags & NLM_F_CREATE)) {\n-\t\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n get_failed:\n \t\t\tfprintf(stderr,\n \t\t\t\t\"Failed to get existing tunnel info.\\n\");\n+\t\t\tfree(answer);\n \t\t\treturn -1;\n \t\t}\n \n-\t\tlen = req.n.nlmsg_len;\n+\t\tlen = answer->nlmsg_len;\n \t\tlen -= NLMSG_LENGTH(sizeof(*ifi));\n \t\tif (len < 0)\n \t\t\tgoto get_failed;\n \n-\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(&req.i), len);\n+\t\tparse_rtattr(tb, IFLA_MAX, IFLA_RTA(NLMSG_DATA(answer)), len);\n \n \t\tif (!tb[IFLA_LINKINFO])\n \t\t\tgoto get_failed;\n@@ -110,6 +111,8 @@ get_failed:\n \n \t\tif (vtiinfo[IFLA_VTI_FWMARK])\n \t\t\tfwmark = rta_getattr_u32(vtiinfo[IFLA_VTI_FWMARK]);\n+\n+\t\tfree(answer);\n \t}\n \n \twhile (argc > 0) {\ndiff --git a/ip/tcp_metrics.c b/ip/tcp_metrics.c\nindex 8972acd..3f9790e 100644\n--- a/ip/tcp_metrics.c\n+++ b/ip/tcp_metrics.c\n@@ -306,6 +306,7 @@ static int process_msg(const struct sockaddr_nl *who, struct nlmsghdr *n,\n static int tcpm_do_cmd(int cmd, int argc, char **argv)\n {\n \tTCPM_REQUEST(req, 1024, TCP_METRICS_CMD_GET, NLM_F_REQUEST);\n+\tstruct nlmsghdr *answer;\n \tint atype = -1, stype = -1;\n \tint ack;\n \n@@ -457,15 +458,16 @@ static int tcpm_do_cmd(int cmd, int argc, char **argv)\n \t}\n \n \tif (ack) {\n-\t\tif (rtnl_talk(&grth, &req.n, NULL, 0) < 0)\n+\t\tif (rtnl_talk(&grth, &req.n, NULL) < 0)\n \t\t\treturn -2;\n \t} else if (atype >= 0) {\n-\t\tif (rtnl_talk(&grth, &req.n, &req.n, sizeof(req)) < 0)\n+\t\tif (rtnl_talk(&grth, &req.n, &answer) < 0)\n \t\t\treturn -2;\n-\t\tif (process_msg(NULL, &req.n, stdout) < 0) {\n+\t\tif (process_msg(NULL, answer, stdout) < 0) {\n \t\t\tfprintf(stderr, \"Dump terminated\\n\");\n \t\t\texit(1);\n \t\t}\n+\t\tfree(answer);\n \t} else {\n \t\treq.n.nlmsg_seq = grth.dump = ++grth.seq;\n \t\tif (rtnl_send(&grth, &req, req.n.nlmsg_len) < 0) {\ndiff --git a/ip/xfrm_policy.c b/ip/xfrm_policy.c\nindex de689c4..98460a0 100644\n--- a/ip/xfrm_policy.c\n+++ b/ip/xfrm_policy.c\n@@ -386,7 +386,7 @@ static int xfrm_policy_modify(int cmd, unsigned int flags, int argc, char **argv\n \tif (req.xpinfo.sel.family == AF_UNSPEC)\n \t\treq.xpinfo.sel.family = AF_INET;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\n@@ -548,7 +548,7 @@ int xfrm_policy_print(const struct sockaddr_nl *who, struct nlmsghdr *n,\n }\n \n static int xfrm_policy_get_or_delete(int argc, char **argv, int delete,\n-\t\t\t\t void *res_nlbuf, size_t res_size)\n+\t\t\t\t struct nlmsghdr **answer)\n {\n \tstruct rtnl_handle rth;\n \tstruct {\n@@ -659,7 +659,7 @@ static int xfrm_policy_get_or_delete(int argc, char **argv, int delete,\n \t\t\t (void *)&ctx, ctx.sctx.len);\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, res_nlbuf, res_size) < 0)\n+\tif (rtnl_talk(&rth, &req.n, answer) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\n@@ -669,21 +669,21 @@ static int xfrm_policy_get_or_delete(int argc, char **argv, int delete,\n \n static int xfrm_policy_delete(int argc, char **argv)\n {\n-\treturn xfrm_policy_get_or_delete(argc, argv, 1, NULL, 0);\n+\treturn xfrm_policy_get_or_delete(argc, argv, 1, NULL);\n }\n \n static int xfrm_policy_get(int argc, char **argv)\n {\n-\tchar buf[NLMSG_BUF_SIZE] = {};\n-\tstruct nlmsghdr *n = (struct nlmsghdr *)buf;\n+\tstruct nlmsghdr *n = NULL;\n \n-\txfrm_policy_get_or_delete(argc, argv, 0, n, sizeof(buf));\n+\txfrm_policy_get_or_delete(argc, argv, 0, &n);\n \n \tif (xfrm_policy_print(NULL, n, (void *)stdout) < 0) {\n \t\tfprintf(stderr, \"An error :-)\\n\");\n \t\texit(1);\n \t}\n \n+\tfree(n);\n \treturn 0;\n }\n \n@@ -1049,7 +1049,7 @@ static int xfrm_spd_setinfo(int argc, char **argv)\n \tif (rtnl_open_byproto(&rth, 0, NETLINK_XFRM) < 0)\n \t\texit(1);\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\n@@ -1063,22 +1063,23 @@ static int xfrm_spd_getinfo(int argc, char **argv)\n \tstruct {\n \t\tstruct nlmsghdr\t\t\tn;\n \t\t__u32\t\t\t\tflags;\n-\t\tchar\t\t\t\tans[128];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(__u32)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n \t\t.n.nlmsg_type = XFRM_MSG_GETSPDINFO,\n \t\t.flags = 0XFFFFFFFF,\n \t};\n+\tstruct nlmsghdr *answer;\n \n \tif (rtnl_open_byproto(&rth, 0, NETLINK_XFRM) < 0)\n \t\texit(1);\n \n-\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0)\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\texit(2);\n \n-\tprint_spdinfo(&req.n, (void *)stdout);\n+\tprint_spdinfo(answer, (void *)stdout);\n \n+\tfree(answer);\n \trtnl_close(&rth);\n \n \treturn 0;\n@@ -1123,7 +1124,7 @@ static int xfrm_policy_flush(int argc, char **argv)\n \tif (show_stats > 1)\n \t\tfprintf(stderr, \"Flush policy\\n\");\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\ndiff --git a/ip/xfrm_state.c b/ip/xfrm_state.c\nindex 4483fb8..a3d4fd7 100644\n--- a/ip/xfrm_state.c\n+++ b/ip/xfrm_state.c\n@@ -726,7 +726,7 @@ static int xfrm_state_modify(int cmd, unsigned int flags, int argc, char **argv)\n \tif (req.xsinfo.family == AF_UNSPEC)\n \t\treq.xsinfo.family = AF_INET;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\n@@ -757,8 +757,7 @@ static int xfrm_state_allocspi(int argc, char **argv)\n \tchar *minp = NULL;\n \tchar *maxp = NULL;\n \tstruct xfrm_mark mark = {0, 0};\n-\tchar res_buf[NLMSG_BUF_SIZE] = {};\n-\tstruct nlmsghdr *res_n = (struct nlmsghdr *)res_buf;\n+\tstruct nlmsghdr *answer;\n \n \twhile (argc > 0) {\n \t\tif (strcmp(*argv, \"mode\") == 0) {\n@@ -858,14 +857,15 @@ static int xfrm_state_allocspi(int argc, char **argv)\n \t\treq.xspi.info.family = AF_INET;\n \n \n-\tif (rtnl_talk(&rth, &req.n, res_n, sizeof(res_buf)) < 0)\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\texit(2);\n \n-\tif (xfrm_state_print(NULL, res_n, (void *)stdout) < 0) {\n+\tif (xfrm_state_print(NULL, answer, (void *)stdout) < 0) {\n \t\tfprintf(stderr, \"An error :-)\\n\");\n \t\texit(1);\n \t}\n \n+\tfree(answer);\n \trtnl_close(&rth);\n \n \treturn 0;\n@@ -1046,19 +1046,20 @@ static int xfrm_state_get_or_delete(int argc, char **argv, int delete)\n \t\treq.xsid.family = AF_INET;\n \n \tif (delete) {\n-\t\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\t\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\t\texit(2);\n \t} else {\n-\t\tchar buf[NLMSG_BUF_SIZE] = {};\n-\t\tstruct nlmsghdr *res_n = (struct nlmsghdr *)buf;\n+\t\tstruct nlmsghdr *answer;\n \n-\t\tif (rtnl_talk(&rth, &req.n, res_n, sizeof(req)) < 0)\n+\t\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\t\texit(2);\n \n-\t\tif (xfrm_state_print(NULL, res_n, (void *)stdout) < 0) {\n+\t\tif (xfrm_state_print(NULL, answer, (void *)stdout) < 0) {\n \t\t\tfprintf(stderr, \"An error :-)\\n\");\n \t\t\texit(1);\n \t\t}\n+\n+\t\tfree(answer);\n \t}\n \n \trtnl_close(&rth);\n@@ -1314,22 +1315,23 @@ static int xfrm_sad_getinfo(int argc, char **argv)\n \tstruct {\n \t\tstruct nlmsghdr\t\t\tn;\n \t\t__u32\t\t\t\tflags;\n-\t\tchar\t\t\t\tans[64];\n \t} req = {\n \t\t.n.nlmsg_len = NLMSG_LENGTH(sizeof(req.flags)),\n \t\t.n.nlmsg_flags = NLM_F_REQUEST,\n \t\t.n.nlmsg_type = XFRM_MSG_GETSADINFO,\n \t\t.flags = 0XFFFFFFFF,\n \t};\n+\tstruct nlmsghdr *answer;\n \n \tif (rtnl_open_byproto(&rth, 0, NETLINK_XFRM) < 0)\n \t\texit(1);\n \n-\tif (rtnl_talk(&rth, &req.n, &req.n, sizeof(req)) < 0)\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0)\n \t\texit(2);\n \n-\tprint_sadinfo(&req.n, (void *)stdout);\n+\tprint_sadinfo(answer, (void *)stdout);\n \n+\tfree(answer);\n \trtnl_close(&rth);\n \n \treturn 0;\n@@ -1376,7 +1378,7 @@ static int xfrm_state_flush(int argc, char **argv)\n \t\tfprintf(stderr, \"Flush state with XFRM-PROTO value \\\"%s\\\"\\n\",\n \t\t\tstrxf_xfrmproto(req.xsf.proto));\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\texit(2);\n \n \trtnl_close(&rth);\ndiff --git a/lib/libgenl.c b/lib/libgenl.c\nindex 50d2d92..bb5fbb5 100644\n--- a/lib/libgenl.c\n+++ b/lib/libgenl.c\n@@ -49,16 +49,21 @@ int genl_resolve_family(struct rtnl_handle *grth, const char *family)\n {\n \tGENL_REQUEST(req, 1024, GENL_ID_CTRL, 0, 0, CTRL_CMD_GETFAMILY,\n \t\t NLM_F_REQUEST);\n+\tstruct nlmsghdr *answer;\n+\tint fnum;\n \n \taddattr_l(&req.n, sizeof(req), CTRL_ATTR_FAMILY_NAME,\n \t\t family, strlen(family) + 1);\n \n-\tif (rtnl_talk(grth, &req.n, &req.n, sizeof(req)) < 0) {\n+\tif (rtnl_talk(grth, &req.n, &answer) < 0) {\n \t\tfprintf(stderr, \"Error talking to the kernel\\n\");\n \t\treturn -2;\n \t}\n \n-\treturn genl_parse_getfamily(&req.n);\n+\tfnum = genl_parse_getfamily(answer);\n+\tfree(answer);\n+\n+\treturn fnum;\n }\n \n int genl_init_handle(struct rtnl_handle *grth, const char *family,\ndiff --git a/lib/libnetlink.c b/lib/libnetlink.c\nindex e3fa7cf..8e2a416 100644\n--- a/lib/libnetlink.c\n+++ b/lib/libnetlink.c\n@@ -575,7 +575,7 @@ static void rtnl_talk_error(struct nlmsghdr *h, struct nlmsgerr *err,\n }\n \n static int __rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t\t struct nlmsghdr *answer, size_t maxlen,\n+\t\t struct nlmsghdr **answer,\n \t\t bool show_rtnl_err, nl_ext_ack_fn_t errfn)\n {\n \tint status;\n@@ -649,9 +649,9 @@ static int __rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n \t\t\t\t\tfprintf(stderr, \"ERROR truncated\\n\");\n \t\t\t\t} else if (!err->error) {\n \t\t\t\t\tif (answer)\n-\t\t\t\t\t\tmemcpy(answer, h,\n-\t\t\t\t\t\t MIN(maxlen, h->nlmsg_len));\n-\t\t\t\t\tfree(buf);\n+\t\t\t\t\t\t*answer = (struct nlmsghdr *)buf;\n+\t\t\t\t\telse\n+\t\t\t\t\t\tfree(buf);\n \t\t\t\t\treturn 0;\n \t\t\t\t}\n \n@@ -665,9 +665,7 @@ static int __rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n \t\t\t}\n \n \t\t\tif (answer) {\n-\t\t\t\tmemcpy(answer, h,\n-\t\t\t\t MIN(maxlen, h->nlmsg_len));\n-\t\t\t\tfree(buf);\n+\t\t\t\t*answer = (struct nlmsghdr *)buf;\n \t\t\t\treturn 0;\n \t\t\t}\n \n@@ -691,22 +689,22 @@ static int __rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n }\n \n int rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t struct nlmsghdr *answer, size_t maxlen)\n+\t struct nlmsghdr **answer)\n {\n-\treturn __rtnl_talk(rtnl, n, answer, maxlen, true, NULL);\n+\treturn __rtnl_talk(rtnl, n, answer, true, NULL);\n }\n \n int rtnl_talk_extack(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t\t struct nlmsghdr *answer, size_t maxlen,\n+\t\t struct nlmsghdr **answer,\n \t\t nl_ext_ack_fn_t errfn)\n {\n-\treturn __rtnl_talk(rtnl, n, answer, maxlen, true, errfn);\n+\treturn __rtnl_talk(rtnl, n, answer, true, errfn);\n }\n \n int rtnl_talk_suppress_rtnl_errmsg(struct rtnl_handle *rtnl, struct nlmsghdr *n,\n-\t\t\t\t struct nlmsghdr *answer, size_t maxlen)\n+\t\t\t\t struct nlmsghdr **answer)\n {\n-\treturn __rtnl_talk(rtnl, n, answer, maxlen, false, NULL);\n+\treturn __rtnl_talk(rtnl, n, answer, false, NULL);\n }\n \n int rtnl_listen_all_nsid(struct rtnl_handle *rth)\ndiff --git a/misc/ss.c b/misc/ss.c\nindex dd8dfaa..bf21d80 100644\n--- a/misc/ss.c\n+++ b/misc/ss.c\n@@ -2597,7 +2597,7 @@ static int kill_inet_sock(struct nlmsghdr *h, void *arg, struct sockstat *s)\n \t\traw->sdiag_raw_protocol = s->raw_prot;\n \t}\n \n-\treturn rtnl_talk(rth, &req.nlh, NULL, 0);\n+\treturn rtnl_talk(rth, &req.nlh, NULL);\n }\n \n static int show_one_inet_sock(const struct sockaddr_nl *addr,\ndiff --git a/tc/m_action.c b/tc/m_action.c\nindex 402228b..8cbf764 100644\n--- a/tc/m_action.c\n+++ b/tc/m_action.c\n@@ -518,18 +518,18 @@ static int tc_action_gd(int cmd, unsigned int flags, int *argc_p, char ***argv_p\n \ttail->rta_len = (void *) NLMSG_TAIL(&req.n) - (void *) tail;\n \n \treq.n.nlmsg_seq = rth.dump = ++rth.seq;\n-\tif (cmd == RTM_GETACTION)\n-\t\tans = &req.n;\n \n-\tif (rtnl_talk(&rth, &req.n, ans, MAX_MSG) < 0) {\n+\tif (rtnl_talk(&rth, &req.n, &ans) < 0) {\n \t\tfprintf(stderr, \"We have an error talking to the kernel\\n\");\n \t\treturn 1;\n \t}\n \n-\tif (ans && print_action(NULL, &req.n, (void *)stdout) < 0) {\n+\tif (cmd == RTM_GETACTION && print_action(NULL, ans, stdout) < 0) {\n \t\tfprintf(stderr, \"Dump terminated\\n\");\n+\t\tfree(ans);\n \t\treturn 1;\n \t}\n+\tfree(ans);\n \n \t*argc_p = argc;\n \t*argv_p = argv;\n@@ -562,7 +562,7 @@ static int tc_action_modify(int cmd, unsigned int flags, int *argc_p, char ***ar\n \t}\n \ttail->rta_len = (void *) NLMSG_TAIL(&req.n) - (void *) tail;\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0) {\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0) {\n \t\tfprintf(stderr, \"We have an error talking to the kernel\\n\");\n \t\tret = -1;\n \t}\n@@ -653,7 +653,7 @@ static int tc_act_list_or_flush(int *argc_p, char ***argv_p, int event)\n \t\treq.n.nlmsg_type = RTM_DELACTION;\n \t\treq.n.nlmsg_flags |= NLM_F_ROOT;\n \t\treq.n.nlmsg_flags |= NLM_F_REQUEST;\n-\t\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0) {\n+\t\tif (rtnl_talk(&rth, &req.n, NULL) < 0) {\n \t\t\tfprintf(stderr, \"We have an error flushing\\n\");\n \t\t\treturn 1;\n \t\t}\ndiff --git a/tc/tc_class.c b/tc/tc_class.c\nindex 1a1f1fa..0214775 100644\n--- a/tc/tc_class.c\n+++ b/tc/tc_class.c\n@@ -149,7 +149,7 @@ static int tc_class_modify(int cmd, unsigned int flags, int argc, char **argv)\n \t\t}\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn 2;\n \n \treturn 0;\ndiff --git a/tc/tc_filter.c b/tc/tc_filter.c\nindex cf290ae..8dbebf1 100644\n--- a/tc/tc_filter.c\n+++ b/tc/tc_filter.c\n@@ -194,7 +194,7 @@ static int tc_filter_modify(int cmd, unsigned int flags, int argc, char **argv)\n \t\t}\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0) {\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0) {\n \t\tfprintf(stderr, \"We have an error talking to the kernel\\n\");\n \t\treturn 2;\n \t}\n@@ -331,6 +331,7 @@ static int tc_filter_get(int cmd, unsigned int flags, int argc, char **argv)\n \t\t.t.tcm_parent = TC_H_UNSPEC,\n \t\t.t.tcm_family = AF_UNSPEC,\n \t};\n+\tstruct nlmsghdr *answer;\n \tstruct filter_util *q = NULL;\n \t__u32 prio = 0;\n \t__u32 protocol = 0;\n@@ -484,13 +485,14 @@ static int tc_filter_get(int cmd, unsigned int flags, int argc, char **argv)\n \t\treturn -1;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, &req.n, MAX_MSG) < 0) {\n+\tif (rtnl_talk(&rth, &req.n, &answer) < 0) {\n \t\tfprintf(stderr, \"We have an error talking to the kernel\\n\");\n \t\treturn 2;\n \t}\n \n-\tprint_filter(NULL, &req.n, (void *)stdout);\n+\tprint_filter(NULL, answer, (void *)stdout);\n \n+\tfree(answer);\n \treturn 0;\n }\n \ndiff --git a/tc/tc_qdisc.c b/tc/tc_qdisc.c\nindex 1e9d909..c52114a 100644\n--- a/tc/tc_qdisc.c\n+++ b/tc/tc_qdisc.c\n@@ -190,7 +190,7 @@ static int tc_qdisc_modify(int cmd, unsigned int flags, int argc, char **argv)\n \t\treq.t.tcm_ifindex = idx;\n \t}\n \n-\tif (rtnl_talk(&rth, &req.n, NULL, 0) < 0)\n+\tif (rtnl_talk(&rth, &req.n, NULL) < 0)\n \t\treturn 2;\n \n \treturn 0;\n", "prefixes": [ "PATCHv2", "iproute2", "2/2" ] }