/* l2tpd.c * Copyright (C) 1997-2000 SpellCaster Telecommunications Inc. * $Id: l2tpd.c,v 1.3 2004/07/12 18:41:46 bcrl Exp $ * Released under the GNU Public License. See LICENSE file for details. * * Userland component of L2TP session handling. Manages control packets of * sessions. */ #define PKT_SIZE 4096 #include #include #include #include #include #include #include "l2tp_linux.h" #if 0 #include "l2tp.h" #endif void dump_packet(unsigned char *buf, int len); static unsigned long strtoip(char *str) { unsigned long a, b, c, d; if (4 != sscanf(str, "%lu.%lu.%lu.%lu", &a, &b, &c, &d)) { fprintf(stderr, "invalid ip address.\n"); exit(1); } return (a << 24 | b << 16 | c << 8 | d); } int main(int argc, char *argv[]) { struct sockaddr_in addr; unsigned char *buf; int s; if (argc < 3) { fprintf(stderr, "need ip addresses .\n"); exit(1); } s = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); if (s < 0) { perror("socket"); return 1; } addr.sin_family = AF_INET; addr.sin_addr.s_addr = htonl(strtoip(argv[1])); //htonl(INADDR_ANY); addr.sin_port = htons(1701); if (bind(s, (struct sockaddr *)&addr, sizeof(addr)) < 0) { perror("bind"); return 1; } addr.sin_family = AF_INET; addr.sin_addr.s_addr = htonl(strtoip(argv[2])); //htonl(INADDR_ANY); addr.sin_addr.s_addr = htonl(INADDR_ANY); addr.sin_port = htons(1701); if (connect(s, (struct sockaddr *)&addr, sizeof(addr)) < 0) { perror("connect"); return 1; } #if 0 switch (fork()) { case 0: break; case -1: perror("fork"); return 1; default: return 0; } close(0); close(1); close(2); /* we're a daemon now =) */ #endif buf = malloc(PKT_SIZE); for (;;) { int addrlen = sizeof(addr); int len; len = recvfrom(s, buf, PKT_SIZE, 0, (struct sockaddr *)&addr, &addrlen); if (len > 0) { //struct sk_buff *skb = calloc(sizeof(skb), 1); //skb->len = len; //skb->head = skb->data = buf; printf("from: %08x:%04x\n", (int)ntohl(addr.sin_addr.s_addr), ntohs(addr.sin_port)); dump_packet(buf, len); //l2tp_udp_recv(skb); buf = malloc(PKT_SIZE); } } return 0; } #include static inline char tohex(unsigned char foo) { if (foo >= 10) return 'a' + foo - 0xa; return foo + '0'; } void dump_packet(unsigned char *buf, int len) { char line[80]; int x, i; printf("Packet len: %d = 0x%x\n\n", len, len); for (x=i=0; i> 12) & 0xf); line[x++] = tohex((i >> 8) & 0xf); line[x++] = tohex((i >> 4) & 0xf); line[x++] = tohex(i & 0xf); line[x++] = ':'; x++; } line[x++] = tohex(buf[i] >> 4); line[x++] = tohex(buf[i] & 0xf); if (3 == (i % 4)) x++; line[(i % 16) + 48] = isprint(buf[i]) ? buf[i] : '.'; if (15 == (i % 16)) { line[16 + 48] = 0; puts(line); x = 0; } } if (i % 16) { line[48 + (i % 16)] = 0; for (; i % 16; i++) { line[x++] = ' '; line[x++] = ' '; if (3 == (i % 4)) x++; } puts(line); } putchar('\n'); }