2 * Copyright (c) 2017 JingPiao Chen <chenjingpiao@gmail.com>
3 * Copyright (c) 2017-2018 The strace developers.
6 * SPDX-License-Identifier: GPL-2.0-or-later
11 #ifdef HAVE_LINUX_FIB_RULES_H
14 # include <inttypes.h>
15 # include "test_nlattr.h"
16 # include <linux/fib_rules.h>
17 # include <linux/in.h>
18 # include <linux/ip.h>
19 # include <linux/rtnetlink.h>
23 #define FRA_UID_RANGE 20
24 #define FRA_PROTOCOL 21
25 #define FRA_IP_PROTO 22
26 #define FRA_SPORT_RANGE 23
27 #define FRA_DPORT_RANGE 24
29 # ifndef HAVE_STRUCT_FIB_RULE_PORT_RANGE
30 struct fib_rule_port_range {
34 # endif /* HAVE_STRUCT_FIB_RULE_PORT_RANGE */
37 init_rtmsg(struct nlmsghdr *const nlh, const unsigned int msg_len)
39 SET_STRUCT(struct nlmsghdr, nlh,
41 .nlmsg_type = RTM_GETRULE,
42 .nlmsg_flags = NLM_F_DUMP
45 struct rtmsg *const msg = NLMSG_DATA(nlh);
46 SET_STRUCT(struct rtmsg, msg,
47 .rtm_family = AF_UNIX,
48 .rtm_tos = IPTOS_LOWDELAY,
49 .rtm_table = RT_TABLE_UNSPEC,
50 .rtm_type = FR_ACT_TO_TBL,
51 .rtm_flags = FIB_RULE_INVERT
56 print_rtmsg(const unsigned int msg_len)
58 printf("{len=%u, type=RTM_GETRULE, flags=NLM_F_DUMP"
59 ", seq=0, pid=0}, {family=AF_UNIX"
60 ", dst_len=0, src_len=0"
61 ", tos=IPTOS_LOWDELAY"
62 ", table=RT_TABLE_UNSPEC"
63 ", action=FR_ACT_TO_TBL"
64 ", flags=FIB_RULE_INVERT}",
71 skip_if_unavailable("/proc/self/fd/");
73 const int fd = create_nl_socket(NETLINK_ROUTE);
74 const unsigned int hdrlen = sizeof(struct rtmsg);
75 void *nlh0 = midtail_alloc(NLMSG_SPACE(hdrlen), NLA_HDRLEN + 8);
77 static char pattern[4096];
78 fill_memory_ex(pattern, sizeof(pattern), 'a', 'z' - 'a' + 1);
80 const unsigned int nla_type = 0xffff & NLA_TYPE_MASK;
81 char nla_type_str[256];
82 sprintf(nla_type_str, "%#x /* FRA_??? */", nla_type);
83 TEST_NLATTR_(fd, nlh0, hdrlen,
84 init_rtmsg, print_rtmsg,
85 nla_type, nla_type_str,
87 print_quoted_hex(pattern, 4));
89 TEST_NLATTR(fd, nlh0, hdrlen,
90 init_rtmsg, print_rtmsg,
91 FRA_DST, 4, pattern, 4,
92 print_quoted_hex(pattern, 4));
94 const uint32_t table_id = RT_TABLE_DEFAULT;
95 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
96 init_rtmsg, print_rtmsg,
97 FRA_TABLE, pattern, table_id,
98 printf("RT_TABLE_DEFAULT"));
100 #ifdef HAVE_STRUCT_FIB_RULE_UID_RANGE
101 static const struct fib_rule_uid_range range = {
105 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
106 init_rtmsg, print_rtmsg,
107 FRA_UID_RANGE, pattern, range,
108 PRINT_FIELD_U("{", range, start);
109 PRINT_FIELD_U(", ", range, end);
112 #if defined HAVE_BE64TOH || defined be64toh
113 const uint64_t tun_id = 0xabcdcdbeedabadef;
114 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
115 init_rtmsg, print_rtmsg,
116 FRA_TUN_ID, pattern, tun_id,
117 printf("htobe64(%" PRIu64 ")", be64toh(tun_id)));
122 static const struct {
126 { ARG_STR(RTPROT_UNSPEC) },
127 { 5, "0x5 /* RTPROT_??? */" },
128 { 17, "RTPROT_MROUTED" },
129 { 42, "RTPROT_BABEL" },
130 { 43, "0x2b /* RTPROT_??? */" },
131 { ARG_STR(0xde) " /* RTPROT_??? */" },
134 for (unsigned i = 0; i < ARRAY_SIZE(proto_args); i++) {
135 proto = proto_args[i].arg;
136 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
137 init_rtmsg, print_rtmsg,
138 FRA_PROTOCOL, pattern, proto,
139 printf("%s", proto_args[i].str));
142 static const struct {
146 { ARG_STR(IPPROTO_TCP) },
147 { 254, "0xfe /* IPPROTO_??? */" },
148 { ARG_STR(IPPROTO_RAW) },
151 for (unsigned i = 0; i < ARRAY_SIZE(ipproto_args); i++) {
152 proto = ipproto_args[i].arg;
153 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
154 init_rtmsg, print_rtmsg,
155 FRA_IP_PROTO, pattern, proto,
156 printf("%s", ipproto_args[i].str));
159 static const struct fib_rule_port_range prange = {
163 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
164 init_rtmsg, print_rtmsg,
165 FRA_SPORT_RANGE, pattern, prange,
166 PRINT_FIELD_U("{", prange, start);
167 PRINT_FIELD_U(", ", prange, end);
169 TEST_NLATTR_OBJECT(fd, nlh0, hdrlen,
170 init_rtmsg, print_rtmsg,
171 FRA_DPORT_RANGE, pattern, prange,
172 PRINT_FIELD_U("{", prange, start);
173 PRINT_FIELD_U(", ", prange, end);
176 puts("+++ exited with 0 +++");
182 SKIP_MAIN_UNDEFINED("HAVE_LINUX_FIB_RULES_H")