/* ----------------------------------------- REMOTE promiscuous ethernet detector. Compiles and runs ok on RH5/GlibC ----------------------------------------- (c) 1998 savage@apostols.org ----------------------------------------- Scan your subnet, and detect promiscuous machinez. It really works, not a joke. ----------------------------------------- */ #include #include #include #include #include #include #include #include #include #include #include /*#include */ #include #include #include #include #define MAX_PACK_LEN 2000 #define ETHER_HEADER_LEN 14 #define ARPREQUEST 1 #define ARPREPLY 2 #define perr(s) fprintf(stderr,s) struct ether_hdr { u_char dst_mac[6], src_mac[6], pkt_type[2]; u_short hw_type, pro_type; u_char hw_len, pro_len; u_short arp_op; u_char sender_eth[6]; u_char sender_ip[4]; u_char target_eth[6]; u_char target_ip[4]; }; union { u_char full_packet[MAX_PACK_LEN]; struct ether_hdr ether_header; } a; #define full_packet a.full_packet #define ether_header a.ether_header char * inetaddr ( u_int32_t ip ) { struct in_addr in; in.s_addr = ip; return inet_ntoa(in); } char * hwaddr (u_char * s) { static char buf[30]; sprintf (buf, "%02X:%02X:%02X:%02X:%02X:%02X", s[0], s[1], s[2], s[3], s[4], s[5]); return buf; } void main (int argc, char **argv) { int rec; int len, from_len, rsflags; struct ifreq if_data; struct sockaddr from; u_int8_t myMAC[6]; u_int32_t myIP, myNETMASK, myBROADCAST, ip, dip; if (geteuid () != 0) { perr ("You must be root to run this program!\n"); exit (0); } if (argc != 2) { perr ("Usage: scanpromisc eth0\n"); exit (0); } if ((rec = socket (AF_INET, SOCK_PACKET, htons (ETH_P_ARP))) < 0) { perror("socket"); exit (0); } printf ("----------------------------------------------------------\n"); strcpy (if_data.ifr_name, argv[1]); if (ioctl (rec, SIOCGIFHWADDR, &if_data) < 0) perr ("can't get HW addres of my interface!\n"); memcpy (myMAC, if_data.ifr_hwaddr.sa_data, 6); printf ("> My HW Addr: %s\n", hwaddr (myMAC)); if (ioctl (rec, SIOCGIFADDR, &if_data) < 0) perr ("can't get IP addres of my interface!\n"); memcpy ((void *) &ip, (void *) &if_data.ifr_addr.sa_data + 2, 4); myIP = ntohl (ip); printf ("> My IP Addr: %s\n", inetaddr(ip)); if (ioctl (rec, SIOCGIFNETMASK, &if_data) < 0) perr ("can't get NETMASK addres of my interface!\n"); memcpy ((void *) &ip, (void *) &if_data.ifr_netmask.sa_data + 2, 4); myNETMASK = ntohl (ip); printf ("> My NETMASK: %s\n", inetaddr(ip)); if (ioctl (rec, SIOCGIFBRDADDR, &if_data) < 0) perr ("can't get BROADCAST addres of my interface!\n"); memcpy ((void *) &ip, (void *) &if_data.ifr_broadaddr.sa_data + 2, 4); myBROADCAST = ntohl (ip); printf ("> My BROADCAST: %s\n", inetaddr(ip)); printf ("----------------------------------------------------------\n"); printf("> Waiting for an ARP pkt (don't ask why) ... "); fflush(stdout); len = recvfrom (rec, full_packet, MAX_PACK_LEN, 0, &from, &from_len); printf("Ok!\n"); if ((rsflags = fcntl (rec, F_GETFL)) == -1) { perror ("fcntl F_GETFL"); exit (1); } if (fcntl (rec, F_SETFL, rsflags | O_NONBLOCK) == -1) { perror ("fcntl F_SETFL"); exit (1); } printf ("----------------------------------------------------------\n"); printf ("> Scanning ....\n"); for (dip = (myIP & myNETMASK) + 1; dip < myBROADCAST; dip++) { memcpy (ether_header.dst_mac, "666666", 6); memcpy (ether_header.target_eth, "\0\0\0\0\0\0", 6); ip = htonl (dip); memcpy (ether_header.target_ip, &ip, 4); memcpy (ether_header.src_mac, myMAC, 6); memcpy (ether_header.sender_eth, ether_header.src_mac, 6); ip = htonl (myIP); memcpy (ether_header.sender_ip, &ip, 4); ether_header.arp_op = htons (ARPREQUEST); ether_header.hw_type = 0x0100; ether_header.hw_len = 6; ether_header.pro_type = 8; ether_header.pro_len = 4; if( sendto (rec, full_packet, sizeof (struct ether_hdr), 0, &from, from_len) < 0) perror ("sendto"); usleep (333); len = recvfrom (rec, full_packet, MAX_PACK_LEN, 0, &from, &from_len); if (len <= ETHER_HEADER_LEN) continue; memcpy (&ip, ether_header.target_ip, 4); if (ntohs (ether_header.arp_op) == ARPREPLY && ntohl (ip) == myIP) { memcpy (&ip, ether_header.sender_ip, 4); printf ("*> Host %s, %s **** Promiscuous mode detected !!!\n", inetaddr (ip), hwaddr (ether_header.sender_eth)); } } printf ("> End.\n"); exit (0); }