diff options
author | Ilya Maximets <i.maximets@samsung.com> | 2019-07-23 08:08:10 -0400 |
---|---|---|
committer | Alexei Starovoitov <ast@kernel.org> | 2019-07-23 18:14:35 -0400 |
commit | decb705e01a5d325c9876b9674043cde4b54f0db (patch) | |
tree | dfe665d20a2f6df6c47403f95faa527a771c656d /tools | |
parent | 7c8b87f012614697596b78841c0d0b1520b1f88a (diff) |
libbpf: fix using uninitialized ioctl results
'channels.max_combined' initialized only on ioctl success and
errno is only valid on ioctl failure.
The code doesn't produce any runtime issues, but makes memory
sanitizers angry:
Conditional jump or move depends on uninitialised value(s)
at 0x55C056F: xsk_get_max_queues (xsk.c:336)
by 0x55C05B2: xsk_create_bpf_maps (xsk.c:354)
by 0x55C089F: xsk_setup_xdp_prog (xsk.c:447)
by 0x55C0E57: xsk_socket__create (xsk.c:601)
Uninitialised value was created by a stack allocation
at 0x55C04CD: xsk_get_max_queues (xsk.c:318)
Additionally fixed warning on uninitialized bytes in ioctl arguments:
Syscall param ioctl(SIOCETHTOOL) points to uninitialised byte(s)
at 0x648D45B: ioctl (in /usr/lib64/libc-2.28.so)
by 0x55C0546: xsk_get_max_queues (xsk.c:330)
by 0x55C05B2: xsk_create_bpf_maps (xsk.c:354)
by 0x55C089F: xsk_setup_xdp_prog (xsk.c:447)
by 0x55C0E57: xsk_socket__create (xsk.c:601)
Address 0x1ffefff378 is on thread 1's stack
in frame #1, created by xsk_get_max_queues (xsk.c:318)
Uninitialised value was created by a stack allocation
at 0x55C04CD: xsk_get_max_queues (xsk.c:318)
CC: Magnus Karlsson <magnus.karlsson@intel.com>
Fixes: 1cad07884239 ("libbpf: add support for using AF_XDP sockets")
Signed-off-by: Ilya Maximets <i.maximets@samsung.com>
Acked-by: Andrii Nakryiko <andriin@fb.com>
Signed-off-by: Alexei Starovoitov <ast@kernel.org>
Diffstat (limited to 'tools')
-rw-r--r-- | tools/lib/bpf/xsk.c | 7 |
1 files changed, 3 insertions, 4 deletions
diff --git a/tools/lib/bpf/xsk.c b/tools/lib/bpf/xsk.c index 5007b5d4fd2c..e02025bbe36d 100644 --- a/tools/lib/bpf/xsk.c +++ b/tools/lib/bpf/xsk.c | |||
@@ -317,15 +317,14 @@ static int xsk_load_xdp_prog(struct xsk_socket *xsk) | |||
317 | 317 | ||
318 | static int xsk_get_max_queues(struct xsk_socket *xsk) | 318 | static int xsk_get_max_queues(struct xsk_socket *xsk) |
319 | { | 319 | { |
320 | struct ethtool_channels channels; | 320 | struct ethtool_channels channels = { .cmd = ETHTOOL_GCHANNELS }; |
321 | struct ifreq ifr; | 321 | struct ifreq ifr = {}; |
322 | int fd, err, ret; | 322 | int fd, err, ret; |
323 | 323 | ||
324 | fd = socket(AF_INET, SOCK_DGRAM, 0); | 324 | fd = socket(AF_INET, SOCK_DGRAM, 0); |
325 | if (fd < 0) | 325 | if (fd < 0) |
326 | return -errno; | 326 | return -errno; |
327 | 327 | ||
328 | channels.cmd = ETHTOOL_GCHANNELS; | ||
329 | ifr.ifr_data = (void *)&channels; | 328 | ifr.ifr_data = (void *)&channels; |
330 | strncpy(ifr.ifr_name, xsk->ifname, IFNAMSIZ - 1); | 329 | strncpy(ifr.ifr_name, xsk->ifname, IFNAMSIZ - 1); |
331 | ifr.ifr_name[IFNAMSIZ - 1] = '\0'; | 330 | ifr.ifr_name[IFNAMSIZ - 1] = '\0'; |
@@ -335,7 +334,7 @@ static int xsk_get_max_queues(struct xsk_socket *xsk) | |||
335 | goto out; | 334 | goto out; |
336 | } | 335 | } |
337 | 336 | ||
338 | if (channels.max_combined == 0 || errno == EOPNOTSUPP) | 337 | if (err || channels.max_combined == 0) |
339 | /* If the device says it has no channels, then all traffic | 338 | /* If the device says it has no channels, then all traffic |
340 | * is sent to a single stream, so max queues = 1. | 339 | * is sent to a single stream, so max queues = 1. |
341 | */ | 340 | */ |