Alguns
dos bugs mais exploitados nos ultimos dias foram os de named.
Por issu decidi fazer um programa que scaneie a versao dos binds. O bind
scan v1.1 criado por mim tinha o problema de que usava o dig para
verificar a versao do bind remoto.
A versao atualizada, publicada aki, conecta-se ao named e pega o
version.bind dele, sem necessidade de nenhum outro programa. Alem dissu,
verifica se a versao eh vulneravel aos bugs mais conhecidos.
O bind scan v2.1 scaneia uma lista de ips que pode ser feita com o
bind host scan. O bhs apenas tenta conectar ao ip (X.X.X.1 a X.X.X.255)
pela porta 53(NAMESERVER_PORT) e coloca o resultado no arquivo "hosts".
Vamos a um exemplo de como usa-los, depois os sources...
~# gcc bhs.c
-o bhs
~# ./bhs 127.0.0
-=-= Binds hosts scanner by Cheat Struck =-=-
Result in filename : hosts
127.0.0.1
~# gcc bscan21.c -o bscan
~# ./bscan hosts
Bind Scan v2.1 - by Cheat Struck <[email protected]>
_START_
127.0.0.1 - 8.1.2 is not vul.
_END_
~#
<++>
bindscan/bhs.c
/* Bind Host Scanner v1.0 by Cheat Struck <[email protected]>
*
* Scaneia ips X.X.X.[1 a 255] que estejam rodando named.
*
* Modo de uso:
* gcc bhs.c -o bhs
* ./bhs <X.X.X>
*
* Exemplo:
* ./bhs 200.24.131
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/types.h>
main( int
argc, char *argv[] ) {
int s0ck,
i=0;
struct sockaddr_in addr;
char ip[16];
char *duh;
FILE *fp;
printf("
-=-= Binds hosts scanner by Cheat Struck =-=-\n");
if( argc < 2 ) {
printf("Use: %s <X.X.X>\n",argv[0]);
exit(1);
}
printf(" Result in filename : hosts \n");
duh = argv[1];
fp = fopen("hosts", "a");
while (i < 255) {
i++;
sprintf(ip, "%s.%d\n", duh,i);
s0ck = socket(AF_INET,
SOCK_STREAM, 0);
addr.sin_family = AF_INET;
addr.sin_port = htons(53);
addr.sin_addr.s_addr = inet_addr(ip);
bzero(&(addr.sin_zero), 8);
if( connect(
s0ck, (struct sockaddr *)&addr, sizeof(addr) ) >= 0) {
fprintf(fp, "%s",ip);
printf("%s FIND!",ip);
}
close(s0ck);
}
fclose(fp);
}
<-->
<++> bindscan/bscan21.c
/* Bind Scan v2.1
* by Cheat Struck <[email protected]>
*
* Scan a ip list and show the BIND version and bugs.
*
* usage: ./bindscan <ip_list>
*
*/
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/nameser.h>
int make_keypkt(char *pktbuf);
void print_ver(int vul, char *buf);
int main(int
argc, char *argv[]) {
struct sockaddr_in ra;
int sd, pktlen;
char iquery[512], vquery[512], ip[16];
HEADER *dh = (HEADER *)iquery;
FILE *fp;
printf("Bind Scan v2.1 - by Cheat Struck <[email protected]>\n");
if(argc != 2) {
printf("usage: %s <ip_list>\n", argv[0]);
exit(0);
}
// OPEN FILE...
if((fp = fopen(argv[1],"r")) == 0) {
printf("Where is this file???\n");
exit(0);
}
// START THE L00PING...
printf("_START_\n");
while( !feof(fp) ) {
bzero((char *)&ip, sizeof(ip));
if(fgets(ip, 16, fp) == NULL) break;
ip[strlen(ip)-1] = 0x00;
printf("%s - ",ip);
// LET'Z CONNECT....
ra.sin_family = AF_INET;
ra.sin_port = htons(NAMESERVER_PORT);
ra.sin_addr.s_addr = inet_addr(ip);
if (((sd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) ||
(connect(sd, (struct sockaddr *)&ra, sizeof(ra)) == -1)) {
if (sd != -1) close(sd);
}
//SEND A QUERY AND GET THE VERSION...
memset(vquery, 0, sizeof(vquery));
pktlen = make_keypkt(vquery);
if (!write(sd, vquery, pktlen)) {
close(sd);
}
pktlen = read(sd, vquery, sizeof(vquery));
close(sd);
//NOW PRINT THE VERSION...
print_ver(dh->rcode == 0, vquery);
}
fclose(fp);
printf("_END_\n");
}
int
make_keypkt(pktbuf)
char *pktbuf;
{
HEADER *dnsh;
char *ptr = pktbuf;
int pktlen = 0;
char qstr[] = "\007version\004bind\000";
int qlen = strlen(qstr) + 1;
dnsh = (HEADER
*) ptr;
dnsh->qdcount
= htons(1);
pktlen += sizeof(HEADER);
ptr += sizeof(HEADER);
memcpy(ptr,
qstr, qlen);
ptr += qlen;
pktlen += qlen;
PUTSHORT(T_TXT, ptr);
PUTSHORT(C_CHAOS, ptr);
pktlen += sizeof(short) * 2;
return pktlen;
}
void
print_ver(vul, buf)
char *buf;
int vul;
{
HEADER *dnsh = (HEADER *)buf;
char *ptr;
if (dnsh->rcode
!= 0) {
return;
}
ptr = (buf
+ sizeof(HEADER));
while (*ptr != '\0')
ptr++;
ptr += 1 + (sizeof(short) * 2);
while (*ptr != '\0')
ptr++;
ptr += 1 + (sizeof(long) + (sizeof(short) * 2));
// GETSHORT(len, ptr);
if(!strcmp(&ptr[3],""))
printf("can't get a version.\n");
else
if((!strncmp(&ptr[3],"8.2",strlen(&ptr[3])))
||
(!strncmp(&ptr[3],"8.2.1",strlen(&ptr[3])))) {
printf("%s is NXT remote overflow VULNERABLE\n",&ptr[3]);
return;
} else
if((!strncmp(&ptr[3],"4.9.5-REL",strlen(&ptr[3])))
||
(!strncmp(&ptr[3],"4.9.5-P1",strlen(&ptr[3]))) ||
(!strncmp(&ptr[3],"4.9.6-REL",strlen(&ptr[3]))) ||
(!strncmp(&ptr[3],"8.1-REL",strlen(&ptr[3]))) ||
(!strncmp(&ptr[3],"8.1.1",strlen(&ptr[3])))) {
printf("%s is IQUERY remote overflow VULNERABLE\n",&ptr[3]);
return;
} else {
printf("%s is not vul.\n",&ptr[3]);
return;
}
}
<-->
|