From 3fb6640115279c12b6ca0edbbca83d297ec6141e Mon Sep 17 00:00:00 2001 From: Philip Homburg Date: Tue, 8 Nov 2005 14:02:36 +0000 Subject: [PATCH] Added tcpstat and udpstat. --- commands/simple/Makefile | 20 +++ commands/simple/tcpstat.c | 327 ++++++++++++++++++++++++++++++++++++++ commands/simple/udpstat.c | 300 ++++++++++++++++++++++++++++++++++ 3 files changed, 647 insertions(+) create mode 100644 commands/simple/tcpstat.c create mode 100644 commands/simple/udpstat.c diff --git a/commands/simple/Makefile b/commands/simple/Makefile index 4b5da6a6e..65fbce5d7 100755 --- a/commands/simple/Makefile +++ b/commands/simple/Makefile @@ -2,6 +2,7 @@ CFLAGS = -D_MINIX -D_POSIX_SOURCE SYS = ../.. +SERVERS = ../../servers CCLD = $(CC) -i $(CFLAGS) CC = exec cc @@ -175,6 +176,7 @@ ALL = \ tar \ tcpd \ tcpdp \ + tcpstat \ tee \ term \ termcap \ @@ -186,6 +188,7 @@ ALL = \ tsort \ ttt \ tty \ + udpstat \ umount \ uname \ unexpand \ @@ -751,6 +754,10 @@ tcpdp: tcpd.c $(CCLD) -o $@ -DPARANOID=1 tcpd.c @install -S 8kw $@ +tcpstat: tcpstat.c + $(CCLD) -o $@ -I$(SERVERS) tcpstat.c + @install -S 8kw $@ + tee: tee.c $(CCLD) -o $@ $? @install -S 4kw $@ @@ -795,6 +802,10 @@ tty: tty.c $(CCLD) -o $@ $? @install -S 4kw $@ +udpstat: udpstat.c + $(CCLD) -o $@ -I$(SERVERS) $? + @install -S 32k $@ + umount: umount.c $(CCLD) -o $@ $? @install -S 4kw $@ @@ -1025,6 +1036,7 @@ install: \ /usr/bin/tar \ /usr/bin/tcpd \ /usr/bin/tcpdp \ + /usr/bin/tcpstat \ /usr/bin/tee \ /usr/bin/term \ /usr/bin/termcap \ @@ -1036,6 +1048,7 @@ install: \ /usr/bin/tsort \ /usr/bin/ttt \ /usr/bin/tty \ + /usr/bin/udpstat \ /usr/bin/umount \ /usr/bin/uname \ /usr/bin/arch \ @@ -1056,6 +1069,7 @@ install: \ /usr/bin/writeisofs \ /usr/bin/xargs \ /usr/bin/yes \ + /usr/bin/udpstat \ /bin/cat \ /bin/date \ /bin/fsck \ @@ -1527,6 +1541,9 @@ install: \ /usr/bin/tcpdp: tcpdp install -cs -o bin $? $@ +/usr/bin/tcpstat: tcpstat + install -cs -o bin $? $@ + /usr/bin/tee: tee install -cs -o bin $? $@ @@ -1560,6 +1577,9 @@ install: \ /usr/bin/tty: tty install -cs -o bin $? $@ +/usr/bin/udpstat: udpstat + install -cs -o bin $? $@ + /usr/bin/umount: umount install -cs -o root -m 4755 $? $@ diff --git a/commands/simple/tcpstat.c b/commands/simple/tcpstat.c new file mode 100644 index 000000000..94d44d790 --- /dev/null +++ b/commands/simple/tcpstat.c @@ -0,0 +1,327 @@ +/* +tcpstat.c + +Created: June 1995 by Philip Homburg +*/ + +#define _MINIX_SOURCE +#define _POSIX_C_SOURCE 2 + +#include +#undef printf + +#include +#include +#include +#include +#include +#ifndef __minix_vmd +#include +#endif +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +char *prog_name; +tcp_conn_t tcp_conn_table[TCP_CONN_NR]; +char values[2 * sizeof(tcp_conn_table) + 1]; +int inclListen, numerical, verbose; + +void print_conn(int i, clock_t now); +void usage(void); + +int main(int argc, char*argv[]) +{ + char *tcp_device; + int fd, i; + struct svrqueryparam qpar; + char *pval; + struct timeval uptime; + clock_t now; + int fl; + int a_flag, n_flag, v_flag; + + (prog_name=strrchr(argv[0], '/')) ? prog_name++ : (prog_name=argv[0]); + + a_flag= 0; + n_flag= 0; + v_flag= 0; + while ((fl= getopt(argc, argv, "?anv")) != -1) + { + switch(fl) + { + case '?': + usage(); + case 'a': + a_flag= 1; + break; + case 'n': + n_flag= 1; + break; + case 'v': + v_flag= 1; + break; + default: + fprintf(stderr, "%s: getopt failed: '%c'\n", + prog_name, fl); + exit(1); + } + } + inclListen= !!a_flag; + numerical= !!n_flag; + verbose= !!v_flag; + + tcp_device= TCP_DEVICE; + if ((fd= open(tcp_device, O_RDWR)) == -1) + { + fprintf(stderr, "%s: unable to open '%s': %s\n", prog_name, + tcp_device, strerror(errno)); + exit(1); + } + + qpar.param = "tcp_conn_table"; + qpar.psize = strlen(qpar.param); + qpar.value = values; + qpar.vsize = sizeof(values); + if (ioctl(fd, NWIOQUERYPARAM, &qpar) == -1) + { + fprintf(stderr, "%s: queryparam failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + pval= values; + if (paramvalue(&pval, tcp_conn_table, sizeof(tcp_conn_table)) != + sizeof(tcp_conn_table)) + { + fprintf(stderr, + "%s: unable to decode the results from queryparam\n", + prog_name); + exit(1); + } + +#ifdef __minix_vmd + /* Get the uptime in clock ticks. */ + if (sysutime(UTIME_UPTIME, &uptime) == -1) + { + fprintf(stderr, "%s: sysutime failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + now= uptime.tv_sec * HZ + (uptime.tv_usec*HZ/1000000); +#else /* Minix 3 */ + now= times(NULL); +#endif + + for (i= 0; itc_flags & TCF_INUSE)) + return; + if (tcp_conn->tc_state == TCS_LISTEN && !inclListen) + return; + if (tcp_conn->tc_state == TCS_CLOSED && tcp_conn->tc_fd == NULL && + tcp_conn->tc_senddis < now) + { + return; + } + + printf("%3d", i); + + a1= tcp_conn->tc_locaddr; + p1= tcp_conn->tc_locport; + a2= tcp_conn->tc_remaddr; + p2= tcp_conn->tc_remport; + + if (a1 == 0) + addr_str= "*"; + else if (!numerical && + (hostent= gethostbyaddr((char *)&a1, + sizeof(a1), AF_INET)) != NULL) + { + addr_str= hostent->h_name; + } + else + addr_str= inet_ntoa(a1); + printf(" %s:", addr_str); + + if (p1 == 0) + printf("*"); + else if ((servent= getservbyport(p1, "tcp")) != NULL) + { + printf("%s", servent->s_name); + } + else + printf("%u", ntohs(p1)); + + if (tcp_conn->tc_orglisten) + printf(" <- "); + else + printf(" -> "); + + if (a2 == 0) + addr_str= "*"; + else if (!numerical && + (hostent= gethostbyaddr((char *)&a2, + sizeof(a2), AF_INET)) != NULL) + { + addr_str= hostent->h_name; + } + else + addr_str= inet_ntoa(a2); + printf("%s:", addr_str); + + if (p2 == 0) + printf("*"); + else if ((servent= getservbyport(p2, "tcp")) != + NULL) + { + printf("%s", servent->s_name); + } + else + printf("%u", ntohs(p2)); + + printf(" "); + no_verbose= 0; + switch(tcp_conn->tc_state) + { + case TCS_CLOSED: printf("CLOSED"); + if (tcp_conn->tc_senddis >= now) + { + printf("(time wait %ld s)", + (tcp_conn->tc_senddis-now)/HZ); + } + no_verbose= 1; + break; + case TCS_LISTEN: printf("LISTEN"); no_verbose= 1; break; + case TCS_SYN_RECEIVED: printf("SYN_RECEIVED"); break; + case TCS_SYN_SENT: printf("SYN_SENT"); break; + case TCS_ESTABLISHED: printf("ESTABLISHED"); break; + case TCS_CLOSING: printf("CLOSING"); break; + default: printf("state(%d)", tcp_conn->tc_state); + break; + } + + if (tcp_conn->tc_flags & TCF_FIN_RECV) + printf(" F<"); + if (tcp_conn->tc_flags & TCF_FIN_SENT) + { + printf(" F>"); + if (tcp_conn->tc_SND_UNA == tcp_conn->tc_SND_NXT) + printf("+"); + } + if (tcp_conn->tc_state != TCS_CLOSED && + tcp_conn->tc_state != TCS_LISTEN) + { + printf("\n\t"); + printf("RQ: %lu, SQ: %lu, RWnd: %u, SWnd: %lu, SWThresh: %lu", + tcp_conn->tc_RCV_NXT - tcp_conn->tc_RCV_LO, + tcp_conn->tc_SND_NXT - tcp_conn->tc_SND_UNA, + tcp_conn->tc_rcv_wnd, + tcp_conn->tc_snd_cwnd - tcp_conn->tc_SND_UNA, + tcp_conn->tc_snd_cthresh); + } + + printf("\n"); + + if (!verbose || no_verbose) + return; + rtt= tcp_conn->tc_rtt; + artt= tcp_conn->tc_artt; + drtt= tcp_conn->tc_drtt; + printf("\tmss %u, mtu %u%s, rtt %.3f (%.3f+%d*%.3f) s\n", + tcp_conn->tc_max_mtu-IP_TCP_MIN_HDR_SIZE, + tcp_conn->tc_mtu, + (tcp_conn->tc_flags & TCF_PMTU) ? "" : " (no PMTU)", + rtt/(HZ+0.0), + artt/(HZ+0.0)/TCP_RTT_SCALE, TCP_DRTT_MULT, + drtt/(HZ+0.0)/TCP_RTT_SCALE); + flags= tcp_conn->tc_flags; + printf("\tflags:"); + if (!flags) + printf(" TCF_EMPTY"); + if (flags & TCF_INUSE) + flags &= ~TCF_INUSE; + if (flags & TCF_FIN_RECV) + { + printf(" TCF_FIN_RECV"); + flags &= ~TCF_FIN_RECV; + } + if (flags & TCF_RCV_PUSH) + { + printf(" TCF_RCV_PUSH"); + flags &= ~TCF_RCV_PUSH; + } + if (flags & TCF_MORE2WRITE) + { + printf(" TCF_MORE2WRITE"); + flags &= ~TCF_MORE2WRITE; + } + if (flags & TCF_SEND_ACK) + { + printf(" TCF_SEND_ACK"); + flags &= ~TCF_SEND_ACK; + } + if (flags & TCF_FIN_SENT) + { + printf(" TCF_FIN_SENT"); + flags &= ~TCF_FIN_SENT; + } + if (flags & TCF_BSD_URG) + { + printf(" TCF_BSD_URG"); + flags &= ~TCF_BSD_URG; + } + if (flags & TCF_NO_PUSH) + { + printf(" TCF_NO_PUSH"); + flags &= ~TCF_NO_PUSH; + } + if (flags & TCF_PUSH_NOW) + { + printf(" TCF_PUSH_NOW"); + flags &= ~TCF_PUSH_NOW; + } + if (flags & TCF_PMTU) + flags &= ~TCF_PMTU; + if (flags) + printf(" 0x%x", flags); + printf("\n"); + printf("\ttimer: ref %d, time %f, active %d\n", + tcp_conn->tc_transmit_timer.tim_ref, + (0.0+tcp_conn->tc_transmit_timer.tim_time-now)/HZ, + tcp_conn->tc_transmit_timer.tim_active); +} + +void usage(void) +{ + fprintf(stderr, "Usage: %s [-anv]\n", prog_name); + exit(1); +} + +/* + * $PchId: tcpstat.c,v 1.8 2005/01/30 01:04:38 philip Exp $ + */ diff --git a/commands/simple/udpstat.c b/commands/simple/udpstat.c new file mode 100644 index 000000000..baf1b5f6e --- /dev/null +++ b/commands/simple/udpstat.c @@ -0,0 +1,300 @@ +/* +udpstat.c + +Created: March 2001 by Philip Homburg +*/ + +#define _MINIX_SOURCE +#define _POSIX_C_SOURCE 2 + +#include +#undef printf + +#include +#include +#include +#include +#include +#include +#ifndef __minix_vmd +#include +#endif +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +char *prog_name; +udp_fd_t udp_fd_table[UDP_FD_NR]; +udp_port_t *udp_port_table; +udp_port_t *udp_port_tablep; +size_t udp_port_table_s; +size_t udp_port_table_rs; +int udp_port_nr; +char values[6 * sizeof(void *) + 3]; +char *valuesl= NULL; +size_t v_size; +int inclSel, numerical; + +void print_fd(int i, clock_t now); +void usage(void); + +int main(int argc, char*argv[]) +{ + char *udp_device; + int fd, i; + struct svrqueryparam qpar; + char *pval; + struct timeval uptime; + clock_t now; + int fl; + int a_flag, n_flag; + + (prog_name=strrchr(argv[0], '/')) ? prog_name++ : (prog_name=argv[0]); + + a_flag= 0; + n_flag= 0; + while ((fl= getopt(argc, argv, "?an")) != -1) + { + switch(fl) + { + case '?': + usage(); + case 'a': + a_flag= 1; + break; + case 'n': + n_flag= 1; + break; + default: + fprintf(stderr, "%s: getopt failed: '%c'\n", + prog_name, fl); + exit(1); + } + } + inclSel= !!a_flag; + numerical= !!n_flag; + + udp_device= UDP_DEVICE; + if ((fd= open(udp_device, O_RDWR)) == -1) + { + fprintf(stderr, "%s: unable to open '%s': %s\n", prog_name, + udp_device, strerror(errno)); + exit(1); + } + + v_size= 2*sizeof(udp_fd_table)+1; + valuesl= realloc(valuesl, v_size); + if (!valuesl) + { + fprintf(stderr, "%s: unable to malloc %u bytes for valuesl\n", + prog_name, v_size); + exit(1); + } + + qpar.param = "udp_fd_table"; + qpar.psize = strlen(qpar.param); + qpar.value = valuesl; + qpar.vsize = v_size; + if (ioctl(fd, NWIOQUERYPARAM, &qpar) == -1) + { + fprintf(stderr, "%s: queryparam failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + pval= valuesl; + if (paramvalue(&pval, udp_fd_table, sizeof(udp_fd_table)) != + sizeof(udp_fd_table)) + { + fprintf(stderr, + "%s: unable to decode the results from queryparam (udp_fd_table)\n", + prog_name); + exit(1); + } + + /* Get address, size, and element size of the UDP port table */ + qpar.param = "&udp_port_table,$udp_port_table,$udp_port_table[0]"; + qpar.psize = strlen(qpar.param); + qpar.value = values; + qpar.vsize = sizeof(values); + if (ioctl(fd, NWIOQUERYPARAM, &qpar) == -1) + { + fprintf(stderr, "%s: queryparam failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + pval= values; + if (paramvalue(&pval, &udp_port_tablep, sizeof(udp_port_tablep)) != + sizeof(udp_port_tablep) || + paramvalue(&pval, &udp_port_table_s, sizeof(udp_port_table_s)) + != sizeof(udp_port_table_s) || + paramvalue(&pval, &udp_port_table_rs, sizeof(udp_port_table_rs)) + != sizeof(udp_port_table_rs)) + { + fprintf(stderr, +"%s: unable to decode the results from queryparam (&udp_port_table, ...)\n", + prog_name); + exit(1); + } + + if (udp_port_table_rs != sizeof(udp_port_table[0])) + { + fprintf(stderr, + "%s: size mismatch in udp_port_table (different version of inet?)\n", + prog_name); + exit(1); + } + udp_port_nr= udp_port_table_s/udp_port_table_rs; + assert(udp_port_table_s == udp_port_nr*udp_port_table_rs); + udp_port_table= malloc(udp_port_table_s); + if (!udp_port_table) + { + fprintf(stderr, + "%s: unable to malloc %u bytes for udp_port_table\n", + prog_name, udp_port_table_s); + exit(1); + } + v_size= 2*udp_port_table_s+1; + valuesl= realloc(valuesl, v_size); + if (!valuesl) + { + fprintf(stderr, "%s: unable to malloc %u bytes for valuesl\n", + prog_name, v_size); + exit(1); + } + + qpar.param = "udp_port_table"; + qpar.psize = strlen(qpar.param); + qpar.value = valuesl; + qpar.vsize = v_size; + if (ioctl(fd, NWIOQUERYPARAM, &qpar) == -1) + { + fprintf(stderr, "%s: queryparam failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + pval= valuesl; + if (paramvalue(&pval, udp_port_table, udp_port_table_s) != + udp_port_table_s) + { + fprintf(stderr, + "%s: unable to decode the results from queryparam (udp_port_table)\n", + prog_name); + exit(1); + } + + /* Get the uptime in clock ticks. */ +#ifdef __minix_vmd + if (sysutime(UTIME_UPTIME, &uptime) == -1) + { + fprintf(stderr, "%s: sysutime failed: %s\n", prog_name, + strerror(errno)); + exit(1); + } + now= uptime.tv_sec * HZ + (uptime.tv_usec*HZ/1000000); +#else /* Minix 3 */ + now= times(NULL); +#endif + + for (i= 0; iuf_flags & UFF_INUSE)) + return; + uf_udpopt= udp_fd->uf_udpopt; + nwuo_flags= uf_udpopt.nwuo_flags; + if (((nwuo_flags & NWUO_LOCPORT_MASK) != NWUO_LP_SET) && !inclSel) + return; + + port_nr= udp_fd->uf_port-udp_port_tablep; + udp_port= &udp_port_table[port_nr]; + + printf("%3d", i); + + if (nwuo_flags & NWUO_EN_LOC) + { + if (!numerical && (hostent= + gethostbyaddr((char *)&udp_port->up_ipaddr, + sizeof(ipaddr_t), AF_INET)) != NULL) + { + locaddr_str= hostent->h_name; + } + else + locaddr_str= inet_ntoa(udp_port->up_ipaddr); + } + else if (nwuo_flags & NWUO_EN_BROAD) + locaddr_str= "255.255.255.255"; + else + locaddr_str= "0.0.0.0"; + + printf(" %s:", locaddr_str); + + if ((nwuo_flags & NWUO_LOCPORT_MASK) != NWUO_LP_SEL && + (nwuo_flags & NWUO_LOCPORT_MASK) != NWUO_LP_SET) + { + printf("*"); + } + else if ((servent= getservbyport(uf_udpopt.nwuo_locport, "udp")) != + NULL) + { + printf("%s", servent->s_name); + } + else + printf("%u", ntohs(uf_udpopt.nwuo_locport)); + + printf(" -> "); + + if (!(nwuo_flags & NWUO_RA_SET)) + remaddr_str= "*"; + else if (!numerical && + (hostent= gethostbyaddr((char *)&uf_udpopt.nwuo_remaddr, + sizeof(ipaddr_t), AF_INET)) != NULL) + { + remaddr_str= hostent->h_name; + } + else + remaddr_str= inet_ntoa(uf_udpopt.nwuo_remaddr); + printf("%s:", remaddr_str); + + if (!(nwuo_flags & NWUO_RP_SET)) + printf("*"); + else if ((servent= getservbyport(uf_udpopt.nwuo_remport, "udp")) != + NULL) + { + printf("%s", servent->s_name); + } + else + printf("%u", ntohs(uf_udpopt.nwuo_remport)); + printf("\n"); +} + +void usage(void) +{ + fprintf(stderr, "Usage: %s [-a] [-n]\n", prog_name); + exit(1); +} + +/* + * $PchId: udpstat.c,v 1.4 2005/01/30 01:04:57 philip Exp $ + */ -- 2.44.0