summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEugene Syromyatnikov <evgsyr@gmail.com>2023-04-28 21:07:12 +0200
committerEugene Syromyatnikov <evgsyr@gmail.com>2023-04-28 21:07:12 +0200
commit2c29d44acf9b84d0d24f78d03fe313d3938181c6 (patch)
treec4eef670c10bf255b3a8b63548c72add0275e07c
parent45cae1542f07deb04dc90e4186d3bb7b61a5b516 (diff)
downloadstrace-esyr/ip-local-port-range.tar.gz
net: implement IP_LOCAL_PORT_RANGE socket option decodingesyr/ip-local-port-range
Introduced by Linux kernel commit v6.3-rc1~162^2~206^2~1. * src/net.c (+print_port_range): New function. (print_getsockopt) <case SOL_IP> <case IP_LOCAL_PORT_RANGE>: Call it. (print_setsockopt) <case SOL_IP> <case IP_LOCAL_PORT_RANGE>: Ditto. * tests/.gitignore: Add ip_local_port_range, ip_local_port_range-Xabbrev, ip_local_port_range-Xraw, ip_local_port_range-Xverbose, ip_local_port_range-success, ip_local_port_range-success-Xabbrev, ip_local_port_range-success-Xraw, and ip_local_port_range-success-Xverbose. * tests/Makefile.am (check_PROGRAMS): Add ip_local_port_range-success, ip_local_port_range-success-Xabbrev, ip_local_port_range-success-Xraw, and ip_local_port_range-success-Xverbose. * tests/gen_tests.in (ip_local_port_range, ip_local_port_range-Xabbrev, ip_local_port_range-Xraw, ip_local_port_range-Xverbose, ip_local_port_range-success, ip_local_port_range-success-Xabbrev, ip_local_port_range-success-Xraw, ip_local_port_range-success-Xverbose): New tests. * tests/pure_executables.list: Add ip_local_port_range, ip_local_port_range-Xabbrev, ip_local_port_range-Xraw, and ip_local_port_range-Xverbose. * tests/ip_local_port_range.c: New file. * tests/ip_local_port_range-Xabbrev.c: Likewise. * tests/ip_local_port_range-Xraw.c: Likewise. * tests/ip_local_port_range-Xverbose.c: Likewise. * tests/ip_local_port_range-success-Xabbrev.c: Likewise. * tests/ip_local_port_range-success-Xraw.c: Likewise. * tests/ip_local_port_range-success-Xverbose.c: Likewise. * tests/ip_local_port_range-success.c: Likewise. * NEWS: Mention it.
-rw-r--r--NEWS3
-rw-r--r--src/net.c38
-rw-r--r--tests/.gitignore8
-rw-r--r--tests/Makefile.am4
-rw-r--r--tests/gen_tests.in8
-rw-r--r--tests/ip_local_port_range-Xabbrev.c2
-rw-r--r--tests/ip_local_port_range-Xraw.c2
-rw-r--r--tests/ip_local_port_range-Xverbose.c2
-rw-r--r--tests/ip_local_port_range-success-Xabbrev.c2
-rw-r--r--tests/ip_local_port_range-success-Xraw.c2
-rw-r--r--tests/ip_local_port_range-success-Xverbose.c2
-rw-r--r--tests/ip_local_port_range-success.c2
-rw-r--r--tests/ip_local_port_range.c185
-rwxr-xr-xtests/pure_executables.list4
14 files changed, 263 insertions, 1 deletions
diff --git a/NEWS b/NEWS
index 964b868e6..c7798adf0 100644
--- a/NEWS
+++ b/NEWS
@@ -8,10 +8,11 @@ Noteworthy changes in release ?.? (????-??-??)
after capturing the specified number of syscalls.
* Implemented decoding of PR_GET_MDWE and PR_SET_MDWE operations of prctl
syscall.
+ * Implemented decoding of IP_LOCAL_PORT_RANGE socket option.
* Implemented decoding of IFLA_BRPORT_MCAST_N_GROUPS,
IFLA_BRPORT_MCAST_MAX_GROUPS, IFLA_GSO_IPV4_MAX_SIZE,
IFLA_GRO_IPV4_MAX_SIZE, and TCA_EXT_WARN_MSG netlink attributes.
- * Updated lists of F_SEAL_*, IFLA_*, IORING_*, IP_*, MFD_*, NFT_*, TCA_*,
+ * Updated lists of F_SEAL_*, IFLA_*, IORING_*, MFD_*, NFT_*, TCA_*,
and V4L2_PIX_FMT_* constants.
* Updated lists of ioctl commands from Linux 6.3.
diff --git a/src/net.c b/src/net.c
index 01f1c34f8..4c84928b8 100644
--- a/src/net.c
+++ b/src/net.c
@@ -734,6 +734,33 @@ print_txrehash(struct tcb *const tcp, const kernel_ulong_t addr, const int len)
}
static void
+print_port_range(struct tcb *const tcp, const kernel_ulong_t addr,
+ const unsigned int len)
+{
+ unsigned int ports;
+
+ if (len != sizeof(ports)) {
+ printstr_ex(tcp, addr, len, QUOTE_FORCE_HEX);
+ return;
+ }
+
+ if (umove_or_printaddr(tcp, addr, &ports))
+ return;
+
+ tprint_indirect_begin();
+ PRINT_VAL_X(ports);
+ if (xlat_verbose(xlat_verbosity) != XLAT_STYLE_RAW) {
+ unsigned short lo = ports & 0xffff;
+ unsigned short hi = ports >> 16;
+
+ if (ports && (!lo || !hi || lo <= hi))
+ tprintf_comment("%.0hu..%.0hu", lo, hi);
+ }
+ tprint_indirect_end();
+}
+
+
+static void
print_tpacket_stats(struct tcb *const tcp, const kernel_ulong_t addr,
unsigned int len)
{
@@ -910,6 +937,14 @@ print_getsockopt(struct tcb *const tcp, const unsigned int level,
}
break;
+ case SOL_IP:
+ switch (name) {
+ case IP_LOCAL_PORT_RANGE:
+ print_port_range(tcp, addr, rlen);
+ return;
+ }
+ break;
+
case SOL_PACKET:
switch (name) {
case PACKET_STATISTICS:
@@ -1189,6 +1224,9 @@ print_setsockopt(struct tcb *const tcp, const unsigned int level,
case MCAST_LEAVE_GROUP:
print_group_req(tcp, addr, len);
return;
+ case IP_LOCAL_PORT_RANGE:
+ print_port_range(tcp, addr, len);
+ return;
}
break;
diff --git a/tests/.gitignore b/tests/.gitignore
index a39408627..4c753e324 100644
--- a/tests/.gitignore
+++ b/tests/.gitignore
@@ -417,6 +417,14 @@ ioprio--pidns-translation
ioprio-Xabbrev
ioprio-Xraw
ioprio-Xverbose
+ip_local_port_range
+ip_local_port_range-Xabbrev
+ip_local_port_range-Xraw
+ip_local_port_range-Xverbose
+ip_local_port_range-success
+ip_local_port_range-success-Xabbrev
+ip_local_port_range-success-Xraw
+ip_local_port_range-success-Xverbose
ip_mreq
ipc
ipc_msg
diff --git a/tests/Makefile.am b/tests/Makefile.am
index 170876eed..f25c2a506 100644
--- a/tests/Makefile.am
+++ b/tests/Makefile.am
@@ -242,6 +242,10 @@ check_PROGRAMS = $(PURE_EXECUTABLES) \
ioctl_v4l2-success-v-Xraw \
ioctl_v4l2-success-v-Xverbose \
ioprio--pidns-translation \
+ ip_local_port_range-success \
+ ip_local_port_range-success-Xabbrev \
+ ip_local_port_range-success-Xraw \
+ ip_local_port_range-success-Xverbose \
is_linux_mips_n64 \
kcmp-y--pidns-translation \
kill--pidns-translation \
diff --git a/tests/gen_tests.in b/tests/gen_tests.in
index db70ee1b4..1316ad6e8 100644
--- a/tests/gen_tests.in
+++ b/tests/gen_tests.in
@@ -435,6 +435,14 @@ ioprio--pidns-translation test_pidns -a18 -e trace=ioprio_get,ioprio_set
ioprio-Xabbrev -a18 -e trace=ioprio_get,ioprio_set -Xabbrev
ioprio-Xraw -a18 -e trace=ioprio_get,ioprio_set -Xraw
ioprio-Xverbose -a18 -e trace=ioprio_get,ioprio_set -Xverbose
+ip_local_port_range -e trace=getsockopt,setsockopt -a50
+ip_local_port_range-Xabbrev -e trace=getsockopt,setsockopt -Xabbrev -a50
+ip_local_port_range-Xraw -e trace=getsockopt,setsockopt -Xraw -a30
+ip_local_port_range-Xverbose -e trace=getsockopt,setsockopt -Xverbose -a69
+ip_local_port_range-success -einject=getsockopt,setsockopt:retval=42 -etrace=getsockopt,setsockopt -a50
+ip_local_port_range-success-Xabbrev -einject=getsockopt,setsockopt:retval=42 -etrace=getsockopt,setsockopt -Xabbrev -a50
+ip_local_port_range-success-Xraw -einject=getsockopt,setsockopt:retval=42 -etrace=getsockopt,setsockopt -Xraw -a30
+ip_local_port_range-success-Xverbose -einject=getsockopt,setsockopt:retval=42 -etrace=getsockopt,setsockopt -Xverbose -a69
ip_mreq -e trace=setsockopt
ipc -a19
ipc_msg +ipc.sh -a26
diff --git a/tests/ip_local_port_range-Xabbrev.c b/tests/ip_local_port_range-Xabbrev.c
new file mode 100644
index 000000000..c6e9fa1e6
--- /dev/null
+++ b/tests/ip_local_port_range-Xabbrev.c
@@ -0,0 +1,2 @@
+#define XLAT_ABBREV 1
+#include "ip_local_port_range.c"
diff --git a/tests/ip_local_port_range-Xraw.c b/tests/ip_local_port_range-Xraw.c
new file mode 100644
index 000000000..73faec1c8
--- /dev/null
+++ b/tests/ip_local_port_range-Xraw.c
@@ -0,0 +1,2 @@
+#define XLAT_RAW 1
+#include "ip_local_port_range.c"
diff --git a/tests/ip_local_port_range-Xverbose.c b/tests/ip_local_port_range-Xverbose.c
new file mode 100644
index 000000000..1487b5608
--- /dev/null
+++ b/tests/ip_local_port_range-Xverbose.c
@@ -0,0 +1,2 @@
+#define XLAT_VERBOSE 1
+#include "ip_local_port_range.c"
diff --git a/tests/ip_local_port_range-success-Xabbrev.c b/tests/ip_local_port_range-success-Xabbrev.c
new file mode 100644
index 000000000..da0e11849
--- /dev/null
+++ b/tests/ip_local_port_range-success-Xabbrev.c
@@ -0,0 +1,2 @@
+#define XLAT_ABBREV 1
+#include "ip_local_port_range-success.c"
diff --git a/tests/ip_local_port_range-success-Xraw.c b/tests/ip_local_port_range-success-Xraw.c
new file mode 100644
index 000000000..8c5be6f02
--- /dev/null
+++ b/tests/ip_local_port_range-success-Xraw.c
@@ -0,0 +1,2 @@
+#define XLAT_RAW 1
+#include "ip_local_port_range-success.c"
diff --git a/tests/ip_local_port_range-success-Xverbose.c b/tests/ip_local_port_range-success-Xverbose.c
new file mode 100644
index 000000000..e5e2d2412
--- /dev/null
+++ b/tests/ip_local_port_range-success-Xverbose.c
@@ -0,0 +1,2 @@
+#define XLAT_VERBOSE 1
+#include "ip_local_port_range-success.c"
diff --git a/tests/ip_local_port_range-success.c b/tests/ip_local_port_range-success.c
new file mode 100644
index 000000000..9e4c28ab2
--- /dev/null
+++ b/tests/ip_local_port_range-success.c
@@ -0,0 +1,2 @@
+#define INJSTR " (INJECTED)"
+#include "ip_local_port_range.c"
diff --git a/tests/ip_local_port_range.c b/tests/ip_local_port_range.c
new file mode 100644
index 000000000..e4449d455
--- /dev/null
+++ b/tests/ip_local_port_range.c
@@ -0,0 +1,185 @@
+/*
+ * Copyright (c) 2023 Eugene Syromyatnikov <evgsyr@gmail.com>
+ * All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ */
+
+#include "tests.h"
+
+#include <limits.h>
+#include <stdio.h>
+#include <unistd.h>
+#include <arpa/inet.h>
+#include <netinet/in.h>
+#include <sys/socket.h>
+
+#ifndef IP_LOCAL_PORT_RANGE
+# define IP_LOCAL_PORT_RANGE 51
+#endif
+
+#ifndef INJSTR
+# define INJSTR ""
+#endif
+
+int
+main(void)
+{
+ static const struct strval32 opts[] = {
+ { 0, NULL },
+ { 1, "1.." },
+ { 12345, "12345.." },
+ { 0xbeef, "48879.." },
+ { 0x10000, "..1" },
+ { 12345 << 16, "..12345" },
+ { 0x12341234U, "4660..4660" },
+ { 0x87654321U, "17185..34661" },
+ { 0xbadc0dedU, "3565..47836" },
+ { 0xbeef0000U, "..48879" },
+ { 0xbeef0001U, "1..48879" },
+ { 0xbeefbeefU, "48879..48879" },
+ { 0xbeeffaceU, NULL },
+ };
+
+ TAIL_ALLOC_OBJECT_CONST_PTR(unsigned int, ports);
+ TAIL_ALLOC_OBJECT_CONST_ARR(unsigned int, big_ports, 2);
+ const char *errstr;
+ socklen_t len;
+ int rc;
+
+ for (unsigned int i = 0; i < ARRAY_SIZE(opts); ++i) {
+ *ports = opts[i].val;
+
+ /* optlen < 0, EINVAL */
+ len = -1;
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, len);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, -1) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports, sprintrc(rc));
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, &len);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, [-1]) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports, sprintrc(rc));
+
+
+ /* optlen = 0, EINVAL */
+ len = 0;
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, len);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", \"\", 0) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ sprintrc(rc));
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, &len);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, [0]) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports, sprintrc(rc));
+
+
+ /* optlen < sizeof(int), EINVAL */
+ len = sizeof(*ports) - 1;
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, len);
+ errstr = sprintrc(rc);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", ",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE));
+ print_quoted_hex(ports, len);
+ printf(", 3) = %s" INJSTR "\n", errstr);
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, &len);
+ errstr = sprintrc(rc);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", ",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE));
+ if (INJSTR[0])
+ print_quoted_hex(ports, len);
+ else
+ printf("%p", ports);
+ printf(", [3]) = %s" INJSTR "\n", errstr);
+
+
+ /* optval EFAULT */
+ len = sizeof(*ports);
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports + 1, len);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, 4) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports + 1, sprintrc(rc));
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports + 1, &len);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, [4]) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports + 1, sprintrc(rc));
+
+
+ /* classic */
+ len = sizeof(*ports);
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, len);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", [%#x%s%s%s]"
+ ", 4) = %s" INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ *ports,
+ !XLAT_RAW && opts[i].str ? " /* " : "",
+ !XLAT_RAW && opts[i].str ? opts[i].str : "",
+ !XLAT_RAW && opts[i].str ? " */" : "",
+ sprintrc(rc));
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, &len);
+ errstr = sprintrc(rc);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", ",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE));
+ if (INJSTR[0]) {
+ printf("[%#x%s%s%s]",
+ *ports,
+ !XLAT_RAW && opts[i].str ? " /* " : "",
+ !XLAT_RAW && opts[i].str ? opts[i].str : "",
+ !XLAT_RAW && opts[i].str ? " */" : "");
+ } else {
+ printf("%p", ports);
+ }
+ printf(", [4]) = %s" INJSTR "\n", errstr);
+
+
+ /* optval > sizeof(int), EFAULT */
+ len = sizeof(*ports) + 1;
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, len);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, 5) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports, sprintrc(rc));
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, ports, &len);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", %p, [5]) = %s"
+ INJSTR "\n",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE),
+ ports, sprintrc(rc));
+
+
+ /* optlen > sizeof(int), EINVAL */
+ len = sizeof(*ports) * 2;
+ big_ports[0] = opts[i].val;
+ big_ports[1] = opts[i].val;
+ rc = setsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, big_ports, len);
+ errstr = sprintrc(rc);
+ printf("setsockopt(0, " XLAT_FMT ", " XLAT_FMT ", ",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE));
+ print_quoted_hex(big_ports, len);
+ printf(", 8) = %s" INJSTR "\n", errstr);
+
+ rc = getsockopt(0, SOL_IP, IP_LOCAL_PORT_RANGE, big_ports, &len);
+ errstr = sprintrc(rc);
+ printf("getsockopt(0, " XLAT_FMT ", " XLAT_FMT ", ",
+ XLAT_ARGS(SOL_IP), XLAT_ARGS(IP_LOCAL_PORT_RANGE));
+ if (INJSTR[0])
+ print_quoted_hex(big_ports, len);
+ else
+ printf("%p", big_ports);
+ printf(", [8]) = %s" INJSTR "\n", errstr);
+ }
+
+ puts("+++ exited with 0 +++");
+ return 0;
+}
diff --git a/tests/pure_executables.list b/tests/pure_executables.list
index 331c4e1c7..a1315f64e 100755
--- a/tests/pure_executables.list
+++ b/tests/pure_executables.list
@@ -270,6 +270,10 @@ ioprio
ioprio-Xabbrev
ioprio-Xraw
ioprio-Xverbose
+ip_local_port_range
+ip_local_port_range-Xabbrev
+ip_local_port_range-Xraw
+ip_local_port_range-Xverbose
ip_mreq
ipc
ipc_msg