From 0fceb64d25ff3d9586549bb43d971c5eef904330 Mon Sep 17 00:00:00 2001 From: Ralf Baechle Date: Mon, 7 Jun 1999 10:23:42 +0200 Subject: Import ax25-apps 0.0.1 from tarball --- listen/listen.c | 293 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 293 insertions(+) create mode 100644 listen/listen.c (limited to 'listen/listen.c') diff --git a/listen/listen.c b/listen/listen.c new file mode 100644 index 0000000..df6f770 --- /dev/null +++ b/listen/listen.c @@ -0,0 +1,293 @@ +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#include +#include "listen.h" + +static void display_port(char *dev) +{ + char *port; + + if ((port = ax25_config_get_name(dev)) == NULL) + port = dev; + + lprintf(T_PORT, "Port %s: ", port); +} + +static void display_timestamp(void) +{ + time_t timenow; + char *timestring; + + time(&timenow); + + timestring = ctime(&timenow); + timestring[24] = '\0'; + + lprintf(T_TIMESTAMP, "[%s]\n", timestring); +} + +#define ASCII 0 +#define HEX 1 +#define READABLE 2 + +#define BUFSIZE 1500 + +int main(int argc, char **argv) +{ + unsigned char buffer[BUFSIZE]; + int timestamp = 0; + int dumpstyle = ASCII; + int size; + int s; + char *port = NULL, *dev = NULL; + struct sockaddr sa; + int asize = sizeof(sa); + struct ifreq ifr; + int proto = ETH_P_AX25; + + while ((s = getopt(argc, argv, "8achip:rtv")) != -1) { + switch (s) { + case '8': + sevenbit = 0; + break; + case 'a': + proto = ETH_P_ALL; + break; + case 'c': + color = 1; + break; + case 'h': + dumpstyle = HEX; + break; + case 'i': + ibmhack = 1; + break; + case 'p': + port = optarg; + break; + case 'r': + dumpstyle = READABLE; + break; + case 't': + timestamp = 1; + break; + case 'v': + printf("listen: %s\n", VERSION); + return 0; + case ':': + fprintf(stderr, "listen: option -p needs a port name\n"); + return 1; + case '?': + fprintf(stderr, "Usage: listen [-8] [-a] [-c] [-h] [-i] [-p port] [-r] [-t] [-v]\n"); + return 1; + } + } + + if (ax25_config_load_ports() == 0) + fprintf(stderr, "listen: no AX.25 port data configured\n"); + + if (port != NULL) { + if ((dev = ax25_config_get_dev(port)) == NULL) { + fprintf(stderr, "listen: invalid port name - %s\n", port); + return 1; + } + } + + if ((s = socket(AF_INET, SOCK_PACKET, htons(proto))) == -1) { + perror("socket"); + return 1; + } + + if (color) { + color = initcolor(); /* Initialize color support */ + if (!color) + printf("Could not initialize color support.\n"); + } + + setservent(1); + + for (;;) { + asize = sizeof(sa); + + if ((size = recvfrom(s, buffer, sizeof(buffer), 0, &sa, &asize)) == -1) { + perror("recv"); + return 1; + } + + if (dev != NULL && strcmp(dev, sa.sa_data) != 0) + continue; + + if (proto == ETH_P_ALL) { + strcpy(ifr.ifr_name, sa.sa_data); + if (ioctl(s, SIOCGIFHWADDR, &ifr) < 0) + perror("GIFADDR"); + + if (ifr.ifr_hwaddr.sa_family == AF_AX25) { + if (timestamp) + display_timestamp(); + display_port(sa.sa_data); + ki_dump(buffer, size, dumpstyle); + lprintf(T_DATA, "\n"); + } + } else { + if (timestamp) + display_timestamp(); + display_port(sa.sa_data); + ki_dump(buffer, size, dumpstyle); + lprintf(T_DATA, "\n"); + } + if (color) + refresh(); + } +} + +static void ascii_dump(unsigned char *data, int length) +{ + unsigned char c; + int i, j; + char buf[100]; + + for (i = 0; length > 0; i += 64) { + sprintf(buf, "%04X ", i); + + for (j = 0; j < 64 && length > 0; j++) { + c = *data++; + length--; + + if ((c != '\0') && (c != '\n')) + strncat(buf, &c, 1); + else + strcat(buf, "."); + } + + lprintf(T_DATA, "%s\n", buf); + } +} + +static void readable_dump(unsigned char *data, int length) +{ + unsigned char c; + int i; + int cr = 1; + char buf[BUFSIZE]; + + for (i = 0; length > 0; i++) { + + c = *data++; + length--; + + switch (c) { + case 0x00: + buf[i] = ' '; + case 0x0A: /* hum... */ + case 0x0D: + if (cr) + buf[i] = '\n'; + else + i--; + break; + default: + buf[i] = c; + } + cr = (buf[i] != '\n'); + } + if (cr) + buf[i++] = '\n'; + buf[i++] = '\0'; + lprintf(T_DATA, "%s", buf); +} + +static void hex_dump(unsigned char *data, int length) +{ + int i, j, length2; + unsigned char c; + char *data2; + + char buf[4], hexd[49], ascd[17]; + + length2 = length; + data2 = data; + + for (i = 0; length > 0; i += 16) { + + hexd[0] = '\0'; + for (j = 0; j < 16; j++) { + c = *data2++; + length2--; + + if (length2 >= 0) + sprintf(buf, "%2.2X ", c); + else + strcpy(buf, " "); + strcat(hexd, buf); + } + + ascd[0] = '\0'; + for (j = 0; j < 16 && length > 0; j++) { + c = *data++; + length--; + + sprintf(buf, "%c", ((c != '\0') && (c != '\n')) ? c : '.'); + strcat(ascd, buf); + } + + lprintf(T_DATA, "%04X %s | %s\n", i, hexd, ascd); + } +} + +void data_dump(unsigned char *data, int length, int dumpstyle) +{ + switch (dumpstyle) { + + case READABLE: + readable_dump(data, length); + break; + case HEX: + hex_dump(data, length); + break; + default: + ascii_dump(data, length); + } +} + +int get16(unsigned char *cp) +{ + int x; + + x = *cp++; + x <<= 8; + x |= *cp++; + + return(x); +} + +int get32(unsigned char *cp) +{ + int x; + + x = *cp++; + x <<= 8; + x |= *cp++; + x <<= 8; + x |= *cp++; + x <<= 8; + x |= *cp; + + return(x); +} -- cgit v1.2.3