]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blob - queue-5.0/net-ethtool-not-call-vzalloc-for-zero-sized-memory-r.patch
net patches from davem for 5.0
[thirdparty/kernel/stable-queue.git] / queue-5.0 / net-ethtool-not-call-vzalloc-for-zero-sized-memory-r.patch
1 From 02b3cbc135549e2ad979efa8e30bd457afd82c5f Mon Sep 17 00:00:00 2001
2 From: Li RongQing <lirongqing@baidu.com>
3 Date: Fri, 29 Mar 2019 09:18:02 +0800
4 Subject: net: ethtool: not call vzalloc for zero sized memory request
5
6 [ Upstream commit 3d8830266ffc28c16032b859e38a0252e014b631 ]
7
8 NULL or ZERO_SIZE_PTR will be returned for zero sized memory
9 request, and derefencing them will lead to a segfault
10
11 so it is unnecessory to call vzalloc for zero sized memory
12 request and not call functions which maybe derefence the
13 NULL allocated memory
14
15 this also fixes a possible memory leak if phy_ethtool_get_stats
16 returns error, memory should be freed before exit
17
18 Signed-off-by: Li RongQing <lirongqing@baidu.com>
19 Reviewed-by: Wang Li <wangli39@baidu.com>
20 Reviewed-by: Michal Kubecek <mkubecek@suse.cz>
21 Signed-off-by: David S. Miller <davem@davemloft.net>
22 Signed-off-by: Sasha Levin <sashal@kernel.org>
23 ---
24 net/core/ethtool.c | 46 ++++++++++++++++++++++++++++++----------------
25 1 file changed, 30 insertions(+), 16 deletions(-)
26
27 diff --git a/net/core/ethtool.c b/net/core/ethtool.c
28 index 158264f7cfaf..3a7f19a61768 100644
29 --- a/net/core/ethtool.c
30 +++ b/net/core/ethtool.c
31 @@ -1794,11 +1794,16 @@ static int ethtool_get_strings(struct net_device *dev, void __user *useraddr)
32 WARN_ON_ONCE(!ret);
33
34 gstrings.len = ret;
35 - data = vzalloc(array_size(gstrings.len, ETH_GSTRING_LEN));
36 - if (gstrings.len && !data)
37 - return -ENOMEM;
38
39 - __ethtool_get_strings(dev, gstrings.string_set, data);
40 + if (gstrings.len) {
41 + data = vzalloc(array_size(gstrings.len, ETH_GSTRING_LEN));
42 + if (!data)
43 + return -ENOMEM;
44 +
45 + __ethtool_get_strings(dev, gstrings.string_set, data);
46 + } else {
47 + data = NULL;
48 + }
49
50 ret = -EFAULT;
51 if (copy_to_user(useraddr, &gstrings, sizeof(gstrings)))
52 @@ -1894,11 +1899,15 @@ static int ethtool_get_stats(struct net_device *dev, void __user *useraddr)
53 return -EFAULT;
54
55 stats.n_stats = n_stats;
56 - data = vzalloc(array_size(n_stats, sizeof(u64)));
57 - if (n_stats && !data)
58 - return -ENOMEM;
59
60 - ops->get_ethtool_stats(dev, &stats, data);
61 + if (n_stats) {
62 + data = vzalloc(array_size(n_stats, sizeof(u64)));
63 + if (!data)
64 + return -ENOMEM;
65 + ops->get_ethtool_stats(dev, &stats, data);
66 + } else {
67 + data = NULL;
68 + }
69
70 ret = -EFAULT;
71 if (copy_to_user(useraddr, &stats, sizeof(stats)))
72 @@ -1938,16 +1947,21 @@ static int ethtool_get_phy_stats(struct net_device *dev, void __user *useraddr)
73 return -EFAULT;
74
75 stats.n_stats = n_stats;
76 - data = vzalloc(array_size(n_stats, sizeof(u64)));
77 - if (n_stats && !data)
78 - return -ENOMEM;
79
80 - if (dev->phydev && !ops->get_ethtool_phy_stats) {
81 - ret = phy_ethtool_get_stats(dev->phydev, &stats, data);
82 - if (ret < 0)
83 - return ret;
84 + if (n_stats) {
85 + data = vzalloc(array_size(n_stats, sizeof(u64)));
86 + if (!data)
87 + return -ENOMEM;
88 +
89 + if (dev->phydev && !ops->get_ethtool_phy_stats) {
90 + ret = phy_ethtool_get_stats(dev->phydev, &stats, data);
91 + if (ret < 0)
92 + goto out;
93 + } else {
94 + ops->get_ethtool_phy_stats(dev, &stats, data);
95 + }
96 } else {
97 - ops->get_ethtool_phy_stats(dev, &stats, data);
98 + data = NULL;
99 }
100
101 ret = -EFAULT;
102 --
103 2.19.1
104