// SPDX-License-Identifier: GPL-2.0-or-later
#include <errno.h>
#include <error.h>
#include <netdb.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <unistd.h>
#include <linux/errqueue.h>
#include <linux/icmp.h>
#include <linux/icmpv6.h>
#include <linux/net_tstamp.h>
#include <linux/types.h>
#include <linux/udp.h>
#include <sys/socket.h>

#include "../kselftest.h"

enum {
	ERN_SUCCESS = 0,
	/* Well defined errors, callers may depend on these */
	ERN_SEND = 1,
	/* Informational, can reorder */
	ERN_HELP,
	ERN_SEND_SHORT,
	ERN_SOCK_CREATE,
	ERN_RESOLVE,
	ERN_CMSG_WR,
	ERN_SOCKOPT,
	ERN_GETTIME,
	ERN_RECVERR,
	ERN_CMSG_RD,
	ERN_CMSG_RCV,
	ERN_SEND_MORE,
};

struct option_cmsg_u32 {
	bool ena;
	unsigned int val;
};

struct options {
	bool silent_send;
	const char *host;
	const char *service;
	unsigned int size;
	unsigned int num_pkt;
	bool msg_more;
	struct {
		unsigned int mark;
		unsigned int dontfrag;
		unsigned int tclass;
		unsigned int hlimit;
		unsigned int priority;
	} sockopt;
	struct {
		unsigned int family;
		unsigned int type;
		unsigned int proto;
	} sock;
	struct option_cmsg_u32 mark;
	struct option_cmsg_u32 priority;
	struct {
		bool ena;
		unsigned int delay;
	} txtime;
	struct {
		bool ena;
	} ts;
	struct {
		struct option_cmsg_u32 dontfrag;
		struct option_cmsg_u32 tclass;
		struct option_cmsg_u32 hlimit;
		struct option_cmsg_u32 exthdr;
	} cmsg;
} opt = {
	.size = 13,
	.num_pkt = 1,
	.sock = {
		.family	= AF_UNSPEC,
		.type	= SOCK_DGRAM,
		.proto	= IPPROTO_UDP,
	},
};

static struct timespec time_start_real;
static struct timespec time_start_mono;

static void __attribute__((noreturn)) cs_usage(const char *bin)
{
	printf("Usage: %s [opts] <dst host> <dst port / service>\n", bin);
	printf("Options:\n"
	       "\t\t-s      Silent send() failures\n"
	       "\t\t-S      send() size\n"
	       "\t\t-4/-6   Force IPv4 / IPv6 only\n"
	       "\t\t-p prot Socket protocol\n"
	       "\t\t        (u = UDP (default); i = ICMP; r = RAW;\n"
	       "\t\t         U = UDP with MSG_MORE)\n"
	       "\n"
	       "\t\t-m val  Set SO_MARK with given value\n"
	       "\t\t-M val  Set SO_MARK via setsockopt\n"
	       "\t\t-P val  Set SO_PRIORITY via setsockopt\n"
	       "\t\t-Q val  Set SO_PRIORITY via cmsg\n"
	       "\t\t-d val  Set SO_TXTIME with given delay (usec)\n"
	       "\t\t-t      Enable time stamp reporting\n"
	       "\t\t-f val  Set don't fragment via cmsg\n"
	       "\t\t-F val  Set don't fragment via setsockopt\n"
	       "\t\t-c val  Set TOS/TCLASS via cmsg\n"
	       "\t\t-C val  Set TOS/TCLASS via setsockopt\n"
	       "\t\t-l val  Set TTL/HOPLIMIT via cmsg\n"
	       "\t\t-L val  Set TTL/HOPLIMIT via setsockopt\n"
	       "\t\t-H type Add an IPv6 header option\n"
	       "\t\t        (h = HOP; d = DST; r = RTDST)\n"
	       "\n");
	exit(ERN_HELP);
}

static void cs_parse_args(int argc, char *argv[])
{
	int o;

	while ((o = getopt(argc, argv, "46sS:p:P:m:M:n:d:tf:F:c:C:l:L:H:Q:")) != -1) {
		switch (o) {
		case 's':
			opt.silent_send = true;
			break;
		case 'S':
			opt.size = atoi(optarg);
			break;
		case '4':
			opt.sock.family = AF_INET;
			break;
		case '6':
			opt.sock.family = AF_INET6;
			break;
		case 'p':
			if (*optarg == 'u') {
				opt.sock.proto = IPPROTO_UDP;
			} else if (*optarg == 'U') {
				opt.sock.proto = IPPROTO_UDP;
				opt.msg_more = true;
			} else if (*optarg == 'i' || *optarg == 'I') {
				opt.sock.proto = IPPROTO_ICMP;
			} else if (*optarg == 'r') {
				opt.sock.type = SOCK_RAW;
			} else {
				printf("Error: unknown protocol: %s\n", optarg);
				cs_usage(argv[0]);
			}
			break;
		case 'P':
			opt.sockopt.priority = atoi(optarg);
			break;
		case 'm':
			opt.mark.ena = true;
			opt.mark.val = atoi(optarg);
			break;
		case 'Q':
			opt.priority.ena = true;
			opt.priority.val = atoi(optarg);
			break;
		case 'M':
			opt.sockopt.mark = atoi(optarg);
			break;
		case 'n':
			opt.num_pkt = atoi(optarg);
			break;
		case 'd':
			opt.txtime.ena = true;
			opt.txtime.delay = atoi(optarg);
			break;
		case 't':
			opt.ts.ena = true;
			break;
		case 'f':
			opt.cmsg.dontfrag.ena = true;
			opt.cmsg.dontfrag.val = atoi(optarg);
			break;
		case 'F':
			opt.sockopt.dontfrag = atoi(optarg);
			break;
		case 'c':
			opt.cmsg.tclass.ena = true;
			opt.cmsg.tclass.val = atoi(optarg);
			break;
		case 'C':
			opt.sockopt.tclass = atoi(optarg);
			break;
		case 'l':
			opt.cmsg.hlimit.ena = true;
			opt.cmsg.hlimit.val = atoi(optarg);
			break;
		case 'L':
			opt.sockopt.hlimit = atoi(optarg);
			break;
		case 'H':
			opt.cmsg.exthdr.ena = true;
			switch (optarg[0]) {
			case 'h':
				opt.cmsg.exthdr.val = IPV6_HOPOPTS;
				break;
			case 'd':
				opt.cmsg.exthdr.val = IPV6_DSTOPTS;
				break;
			case 'r':
				opt.cmsg.exthdr.val = IPV6_RTHDRDSTOPTS;
				break;
			default:
				printf("Error: hdr type: %s\n", optarg);
				break;
			}
			break;
		}
	}

	if (optind != argc - 2)
		cs_usage(argv[0]);

	opt.host = argv[optind];
	opt.service = argv[optind + 1];
}

static void memrnd(void *s, size_t n)
{
	int *dword = s;
	char *byte;

	for (; n >= 4; n -= 4)
		*dword++ = rand();
	byte = (void *)dword;
	while (n--)
		*byte++ = rand();
}

static void
ca_write_cmsg_u32(char *cbuf, size_t cbuf_sz, size_t *cmsg_len,
		  int level, int optname, struct option_cmsg_u32 *uopt)
{
	struct cmsghdr *cmsg;

	if (!uopt->ena)
		return;

	cmsg = (struct cmsghdr *)(cbuf + *cmsg_len);
	*cmsg_len += CMSG_SPACE(sizeof(__u32));
	if (cbuf_sz < *cmsg_len)
		error(ERN_CMSG_WR, EFAULT, "cmsg buffer too small");

	cmsg->cmsg_level = level;
	cmsg->cmsg_type = optname;
	cmsg->cmsg_len = CMSG_LEN(sizeof(__u32));
	*(__u32 *)CMSG_DATA(cmsg) = uopt->val;
}

static void
cs_write_cmsg(int fd, struct msghdr *msg, char *cbuf, size_t cbuf_sz)
{
	struct cmsghdr *cmsg;
	size_t cmsg_len;

	msg->msg_control = cbuf;
	cmsg_len = 0;

	ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
			  SOL_SOCKET, SO_MARK, &opt.mark);
	ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
			  SOL_SOCKET, SO_PRIORITY, &opt.priority);

	if (opt.sock.family == AF_INET) {
		ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
				  SOL_IP, IP_TOS, &opt.cmsg.tclass);
		ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
				  SOL_IP, IP_TTL, &opt.cmsg.hlimit);
	} else {
		ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
				  SOL_IPV6, IPV6_DONTFRAG, &opt.cmsg.dontfrag);
		ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
				  SOL_IPV6, IPV6_TCLASS, &opt.cmsg.tclass);
		ca_write_cmsg_u32(cbuf, cbuf_sz, &cmsg_len,
				  SOL_IPV6, IPV6_HOPLIMIT, &opt.cmsg.hlimit);
	}

	if (opt.txtime.ena) {
		__u64 txtime;

		txtime = time_start_mono.tv_sec * (1000ULL * 1000 * 1000) +
			 time_start_mono.tv_nsec +
			 opt.txtime.delay * 1000;

		cmsg = (struct cmsghdr *)(cbuf + cmsg_len);
		cmsg_len += CMSG_SPACE(sizeof(txtime));
		if (cbuf_sz < cmsg_len)
			error(ERN_CMSG_WR, EFAULT, "cmsg buffer too small");

		cmsg->cmsg_level = SOL_SOCKET;
		cmsg->cmsg_type = SCM_TXTIME;
		cmsg->cmsg_len = CMSG_LEN(sizeof(txtime));
		memcpy(CMSG_DATA(cmsg), &txtime, sizeof(txtime));
	}
	if (opt.ts.ena) {
		cmsg = (struct cmsghdr *)(cbuf + cmsg_len);
		cmsg_len += CMSG_SPACE(sizeof(__u32));
		if (cbuf_sz < cmsg_len)
			error(ERN_CMSG_WR, EFAULT, "cmsg buffer too small");

		cmsg->cmsg_level = SOL_SOCKET;
		cmsg->cmsg_type = SO_TIMESTAMPING;
		cmsg->cmsg_len = CMSG_LEN(sizeof(__u32));
		*(__u32 *)CMSG_DATA(cmsg) = SOF_TIMESTAMPING_TX_SCHED |
					    SOF_TIMESTAMPING_TX_SOFTWARE;
	}
	if (opt.cmsg.exthdr.ena) {
		cmsg = (struct cmsghdr *)(cbuf + cmsg_len);
		cmsg_len += CMSG_SPACE(8);
		if (cbuf_sz < cmsg_len)
			error(ERN_CMSG_WR, EFAULT, "cmsg buffer too small");

		cmsg->cmsg_level = SOL_IPV6;
		cmsg->cmsg_type = opt.cmsg.exthdr.val;
		cmsg->cmsg_len = CMSG_LEN(8);
		*(__u64 *)CMSG_DATA(cmsg) = 0;
	}

	if (cmsg_len)
		msg->msg_controllen = cmsg_len;
	else
		msg->msg_control = NULL;
}

static const char *cs_ts_info2str(unsigned int info)
{
	static const char *names[] = {
		[SCM_TSTAMP_SND]	= "SND",
		[SCM_TSTAMP_SCHED]	= "SCHED",
		[SCM_TSTAMP_ACK]	= "ACK",
	};

	if (info < ARRAY_SIZE(names))
		return names[info];
	return "unknown";
}

static unsigned long
cs_read_cmsg(int fd, struct msghdr *msg, char *cbuf, size_t cbuf_sz)
{
	struct sock_extended_err *see;
	struct scm_timestamping *ts;
	unsigned long ts_seen = 0;
	struct cmsghdr *cmsg;
	int i, err;

	if (!opt.ts.ena)
		return 0;
	msg->msg_control = cbuf;
	msg->msg_controllen = cbuf_sz;

	while (true) {
		ts = NULL;
		see = NULL;
		memset(cbuf, 0, cbuf_sz);

		err = recvmsg(fd, msg, MSG_ERRQUEUE);
		if (err < 0) {
			if (errno == EAGAIN)
				break;
			error(ERN_RECVERR, errno, "recvmsg ERRQ");
		}

		for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL;
		     cmsg = CMSG_NXTHDR(msg, cmsg)) {
			if (cmsg->cmsg_level == SOL_SOCKET &&
			    cmsg->cmsg_type == SO_TIMESTAMPING_OLD) {
				if (cmsg->cmsg_len < sizeof(*ts))
					error(ERN_CMSG_RD, EINVAL, "TS cmsg");

				ts = (void *)CMSG_DATA(cmsg);
			}
			if ((cmsg->cmsg_level == SOL_IP &&
			     cmsg->cmsg_type == IP_RECVERR) ||
			    (cmsg->cmsg_level == SOL_IPV6 &&
			     cmsg->cmsg_type == IPV6_RECVERR)) {
				if (cmsg->cmsg_len < sizeof(*see))
					error(ERN_CMSG_RD, EINVAL, "sock_err cmsg");

				see = (void *)CMSG_DATA(cmsg);
			}
		}

		if (!ts)
			error(ERN_CMSG_RCV, ENOENT, "TS cmsg not found");
		if (!see)
			error(ERN_CMSG_RCV, ENOENT, "sock_err cmsg not found");

		for (i = 0; i < 3; i++) {
			unsigned long long rel_time;

			if (!ts->ts[i].tv_sec && !ts->ts[i].tv_nsec)
				continue;

			rel_time = (ts->ts[i].tv_sec - time_start_real.tv_sec) *
				(1000ULL * 1000) +
				(ts->ts[i].tv_nsec - time_start_real.tv_nsec) /
				1000;
			printf(" %5s ts%d %lluus\n",
			       cs_ts_info2str(see->ee_info),
			       i, rel_time);
			ts_seen |= 1 << see->ee_info;
		}
	}

	return ts_seen;
}

static void ca_set_sockopts(int fd)
{
	if (opt.sockopt.mark &&
	    setsockopt(fd, SOL_SOCKET, SO_MARK,
		       &opt.sockopt.mark, sizeof(opt.sockopt.mark)))
		error(ERN_SOCKOPT, errno, "setsockopt SO_MARK");
	if (opt.sockopt.priority &&
	    setsockopt(fd, SOL_SOCKET, SO_PRIORITY,
		       &opt.sockopt.priority, sizeof(opt.sockopt.priority)))
		error(ERN_SOCKOPT, errno, "setsockopt SO_PRIORITY");

	if (opt.sock.family == AF_INET) {
		if (opt.sockopt.tclass &&
		    setsockopt(fd, SOL_IP, IP_TOS,
			       &opt.sockopt.tclass, sizeof(opt.sockopt.tclass)))
			error(ERN_SOCKOPT, errno, "setsockopt IP_TOS");
		if (opt.sockopt.hlimit &&
		    setsockopt(fd, SOL_IP, IP_TTL,
			       &opt.sockopt.hlimit, sizeof(opt.sockopt.hlimit)))
			error(ERN_SOCKOPT, errno, "setsockopt IP_TTL");
	} else {
		if (opt.sockopt.dontfrag &&
		    setsockopt(fd, SOL_IPV6, IPV6_DONTFRAG,
			       &opt.sockopt.dontfrag, sizeof(opt.sockopt.dontfrag)))
			error(ERN_SOCKOPT, errno, "setsockopt IPV6_DONTFRAG");
		if (opt.sockopt.tclass &&
		    setsockopt(fd, SOL_IPV6, IPV6_TCLASS,
			       &opt.sockopt.tclass, sizeof(opt.sockopt.tclass)))
			error(ERN_SOCKOPT, errno, "setsockopt IPV6_TCLASS");
		if (opt.sockopt.hlimit &&
		    setsockopt(fd, SOL_IPV6, IPV6_UNICAST_HOPS,
			       &opt.sockopt.hlimit, sizeof(opt.sockopt.hlimit)))
			error(ERN_SOCKOPT, errno, "setsockopt IPV6_HOPLIMIT");
	}

	if (opt.txtime.ena) {
		struct sock_txtime so_txtime = {
			.clockid = CLOCK_MONOTONIC,
		};

		if (setsockopt(fd, SOL_SOCKET, SO_TXTIME,
			       &so_txtime, sizeof(so_txtime)))
			error(ERN_SOCKOPT, errno, "setsockopt TXTIME");
	}
	if (opt.ts.ena) {
		__u32 val = SOF_TIMESTAMPING_SOFTWARE |
			SOF_TIMESTAMPING_OPT_TSONLY;

		if (setsockopt(fd, SOL_SOCKET, SO_TIMESTAMPING,
			       &val, sizeof(val)))
			error(ERN_SOCKOPT, errno, "setsockopt TIMESTAMPING");
	}
}

int main(int argc, char *argv[])
{
	struct addrinfo hints, *ai;
	struct iovec iov[1];
	unsigned char *buf;
	struct msghdr msg;
	char cbuf[1024];
	int err;
	int fd;
	int i;

	cs_parse_args(argc, argv);

	buf = malloc(opt.size);
	memrnd(buf, opt.size);

	memset(&hints, 0, sizeof(hints));
	hints.ai_family = opt.sock.family;

	ai = NULL;
	err = getaddrinfo(opt.host, opt.service, &hints, &ai);
	if (err) {
		fprintf(stderr, "Can't resolve address [%s]:%s\n",
			opt.host, opt.service);
		err = ERN_SOCK_CREATE;
		goto err_free_buff;
	}

	if (ai->ai_family == AF_INET6 && opt.sock.proto == IPPROTO_ICMP)
		opt.sock.proto = IPPROTO_ICMPV6;

	fd = socket(ai->ai_family, opt.sock.type, opt.sock.proto);
	if (fd < 0) {
		fprintf(stderr, "Can't open socket: %s\n", strerror(errno));
		err = ERN_RESOLVE;
		goto err_free_info;
	}

	if (opt.sock.proto == IPPROTO_ICMP) {
		buf[0] = ICMP_ECHO;
		buf[1] = 0;
	} else if (opt.sock.proto == IPPROTO_ICMPV6) {
		buf[0] = ICMPV6_ECHO_REQUEST;
		buf[1] = 0;
	} else if (opt.sock.type == SOCK_RAW) {
		struct udphdr hdr = { 1, 2, htons(opt.size), 0 };
		struct sockaddr_in6 *sin6 = (void *)ai->ai_addr;

		memcpy(buf, &hdr, sizeof(hdr));
		sin6->sin6_port = htons(opt.sock.proto);
	}

	ca_set_sockopts(fd);

	if (clock_gettime(CLOCK_REALTIME, &time_start_real))
		error(ERN_GETTIME, errno, "gettime REALTIME");
	if (clock_gettime(CLOCK_MONOTONIC, &time_start_mono))
		error(ERN_GETTIME, errno, "gettime MONOTONIC");

	iov[0].iov_base = buf;
	iov[0].iov_len = opt.size;

	memset(&msg, 0, sizeof(msg));
	msg.msg_name = ai->ai_addr;
	msg.msg_namelen = ai->ai_addrlen;
	msg.msg_iov = iov;
	msg.msg_iovlen = 1;

	cs_write_cmsg(fd, &msg, cbuf, sizeof(cbuf));

	for (i = 0; i < opt.num_pkt; i++) {
		err = sendmsg(fd, &msg, opt.msg_more ? MSG_MORE : 0);
		if (err < 0) {
			if (!opt.silent_send)
				fprintf(stderr, "send failed: %s\n", strerror(errno));
			err = ERN_SEND;
			goto err_out;
		} else if (err != (int)opt.size) {
			fprintf(stderr, "short send\n");
			err = ERN_SEND_SHORT;
			goto err_out;
		}
		if (opt.msg_more) {
			err = write(fd, NULL, 0);
			if (err < 0) {
				fprintf(stderr, "send more: %s\n", strerror(errno));
				err = ERN_SEND_MORE;
				goto err_out;
			}
		}
	}
	err = ERN_SUCCESS;

	if (opt.ts.ena) {
		unsigned long seen;
		int i;

		/* Make sure all timestamps have time to loop back */
		for (i = 0; i < 40; i++) {
			seen = cs_read_cmsg(fd, &msg, cbuf, sizeof(cbuf));
			if (seen & (1 << SCM_TSTAMP_SND))
				break;
			usleep(opt.txtime.delay / 20);
		}
	}

err_out:
	close(fd);
err_free_info:
	freeaddrinfo(ai);
err_free_buff:
	free(buf);
	return err;
}
