000056
EOF
arp_test "fe80::6af7:28ff:fefa:d136" "12:34:56:78:9a:bc"
+
+tcp_run ()
+{
+ $VALGRIND system_socket_test tcp "$@" >"$out_file" || exit $?
+ od -A x -t x1 "$out_file"
+}
+
+tcp_test ()
+{
+ unit_test_notrace tcp_run "$@"
+}
+
+ok <<EOF
+000000 45 00 00 08 00 00 00 00 ff 06 00 00 c0 a8 01 19
+000010 c0 a8 02 4b 01 bd d4 31 00 00 00 00 00 00 00 00
+000020 50 10 04 d2 50 5f 00 00
+000028
+EOF
+tcp_test "192.168.1.25:445" "192.168.2.75:54321" 0 0 0
+
+ok <<EOF
+000000 45 00 00 08 00 00 00 00 ff 06 00 00 c0 a8 01 19
+000010 c0 a8 02 4b 01 bd d4 31 00 00 00 00 00 00 00 00
+000020 50 14 04 d2 50 5b 00 00
+000028
+EOF
+tcp_test "192.168.1.25:445" "192.168.2.75:54321" 0 0 1
+
+ok <<EOF
+000000 45 00 00 08 00 00 00 00 ff 06 00 00 c0 a8 01 19
+000010 c0 a8 02 4b 01 bd d4 31 39 30 00 00 a0 5b 00 00
+000020 50 14 04 d2 76 cf 00 00
+000028
+EOF
+tcp_test "192.168.1.25:445" "192.168.2.75:54321" 12345 23456 1
+
+ok <<EOF
+000000 60 00 00 00 00 14 06 40 fe 80 00 00 00 00 00 00
+000010 6a f7 28 ff fe fa d1 36 fe 80 00 00 00 00 00 00
+000020 6a f7 28 ff fe fb d1 37 01 bd d4 31 00 00 00 00
+000030 00 00 00 00 50 10 04 d2 0f c0 00 00
+00003c
+EOF
+tcp_test "fe80::6af7:28ff:fefa:d136:445" "fe80::6af7:28ff:fefb:d137:54321" 0 0 0
+
+ok <<EOF
+000000 60 00 00 00 00 14 06 40 fe 80 00 00 00 00 00 00
+000010 6a f7 28 ff fe fa d1 36 fe 80 00 00 00 00 00 00
+000020 6a f7 28 ff fe fb d1 37 01 bd d4 31 00 00 00 00
+000030 00 00 00 00 50 14 04 d2 0f bc 00 00
+00003c
+EOF
+tcp_test "fe80::6af7:28ff:fefa:d136:445" "fe80::6af7:28ff:fefb:d137:54321" 0 0 1
+
+ok <<EOF
+000000 60 00 00 00 00 14 06 40 fe 80 00 00 00 00 00 00
+000010 6a f7 28 ff fe fa d1 36 fe 80 00 00 00 00 00 00
+000020 6a f7 28 ff fe fb d1 37 01 bd d4 31 39 30 00 00
+000030 a0 5b 00 00 50 14 04 d2 36 30 00 00
+00003c
+EOF
+tcp_test "fe80::6af7:28ff:fefa:d136:445" \
+ "fe80::6af7:28ff:fefb:d137:54321" 12345 23456 1
#endif /* HAVE_PACKETSOCKET */
+static void test_tcp(const char *src_str,
+ const char *dst_str,
+ const char *seq_str,
+ const char *ack_str,
+ const char *rst_str)
+{
+ ctdb_sock_addr src, dst;
+ uint32_t seq, ack;
+ int rst;
+ uint8_t buf[512];
+ struct ether_header *eth;
+ size_t expected_len, len;
+ int ret;
+
+ ret = ctdb_sock_addr_from_string(src_str, &src, true);
+ assert(ret == 0);
+
+ ret = ctdb_sock_addr_from_string(dst_str, &dst, true);
+ assert(ret == 0);
+
+ seq = atoi(seq_str);
+ ack = atoi(ack_str);
+ rst = atoi(rst_str);
+
+ /* Need to fake this up */
+ eth = (struct ether_header *) buf;
+ memset(eth, 0, sizeof(*eth));
+
+ switch (src.ip.sin_family) {
+ case AF_INET:
+ eth->ether_type = htons(ETHERTYPE_IP);
+ expected_len = 40;
+ ret = tcp4_build(buf + sizeof(struct ether_header),
+ sizeof(buf) - sizeof(struct ether_header),
+ &src.ip,
+ &dst.ip,
+ seq,
+ ack,
+ rst,
+ &len);
+ break;
+ case AF_INET6:
+ eth->ether_type = htons(ETHERTYPE_IP6);
+ expected_len = 60;
+ ret = tcp6_build(buf + sizeof(struct ether_header),
+ sizeof(buf) - sizeof(struct ether_header),
+ &src.ip6,
+ &dst.ip6,
+ seq,
+ ack,
+ rst,
+ &len);
+ break;
+ default:
+ abort();
+ }
+
+ assert(ret == 0);
+ assert(len == expected_len);
+
+ write(STDOUT_FILENO, buf + sizeof(struct ether_header), len);
+}
+
static void usage(const char *prog)
{
fprintf(stderr, "usage: %s <cmd> [<arg> ...]\n", prog);
fprintf(stderr, " commands:\n");
fprintf(stderr, " types\n");
fprintf(stderr, " arp <ipaddr> <hwaddr> [reply]\n");
+ fprintf(stderr, " tcp <src> <dst> <seq> <ack> <rst>\n");
exit(1);
}
usage(argv[0]);
}
test_arp(argv[2], argv[3], (argc == 5));
+ } else if (strcmp(argv[1], "tcp") == 0) {
+ if (argc != 7) {
+ usage(argv[0]);
+ }
+ test_tcp(argv[2], argv[3], argv[4], argv[5], argv[6]);
} else {
usage(argv[0]);
}