Skip to content

Instantly share code, notes, and snippets.

@thongntit
Last active March 12, 2019 19:18
Show Gist options
  • Save thongntit/98ae9be1d2cc1360a79ec749482f3289 to your computer and use it in GitHub Desktop.
Save thongntit/98ae9be1d2cc1360a79ec749482f3289 to your computer and use it in GitHub Desktop.
Applet using raw socket to send and receive packet with ICMP protocal OUTPUT is packet in hexa format. Can print as %c to see data. IP header is 20bytes. ICMP header is 8bytes. The rest is data
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include <inttypes.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <netinet/ip_icmp.h>
#include <arpa/inet.h>
unsigned short checksumCalc(unsigned short *addr, int len)
{
int nleft = len;
int sum = 0;
unsigned short *w = addr;
unsigned short answer = 0;
while (nleft > 1) {
sum += *w++;
nleft -= 2;
}
if (nleft == 1) {
*(unsigned char *) (&answer) = *(unsigned char *) w;
sum += answer;
}
sum = (sum >> 16) + (sum & 0xFFFF);
sum += (sum >> 16);
answer = ~sum;
return answer;
}
int main(int argc, char **argv)
{
uint8_t *packet;
packet = malloc(500);
struct ip ip;
ip.ip_hl = 0x5;
ip.ip_v = 0x4;
ip.ip_tos = 0x0;
ip.ip_len = htons(60);
ip.ip_id = htons(12830);
ip.ip_off = 0x0;
ip.ip_ttl = 1;
ip.ip_p = IPPROTO_ICMP;
ip.ip_sum = 0x0;
ip.ip_src.s_addr = inet_addr("192.168.74.57");
ip.ip_dst.s_addr = inet_addr("192.168.74.58");
ip.ip_sum = checksumCalc((unsigned short *)&ip, sizeof(ip));
memcpy(packet, &ip, sizeof(ip));
struct icmp icmp;
icmp.icmp_type = 8; // 8 means ICMP_ECHO
icmp.icmp_code = 0;
icmp.icmp_id = 1000;
icmp.icmp_seq = 0;
char icmpData[500];
char msg[500]="helloworld";
/*printf("Enter the data you want to send: \n");*/
/*fgets(msg, 499, stdin);*/
// first: doing it to calculate checksum
memcpy(icmpData, &icmp, 8);
memcpy(icmpData + 8, msg, strlen(msg));
icmp.icmp_cksum = checksumCalc((short unsigned int*)&icmpData, 8 + strlen(msg));
// second: doing it to include the checksum in the packet this time
memcpy(icmpData, &icmp, 8);
memcpy(icmpData + 8, msg, strlen(msg));
memcpy(packet + 20, icmpData, 8 + strlen(msg));
int sock;
if ((sock = socket(AF_INET, SOCK_RAW, 1)) < 0) { // 1 for icmp
perror("Error creating socket. Are you root? \n");
exit(1);
}
const int on = 1;
if (setsockopt(sock, IPPROTO_IP, IP_HDRINCL, &on, sizeof(on)) < 0) {
perror("Couldn't set socket options. \n");
exit(1);
}
struct sockaddr_in send;
//memset(&sin, 0, sizeof(sin));
send.sin_family = AF_INET;
send.sin_port = 0;
send.sin_addr.s_addr = ip.ip_dst.s_addr;
struct sockaddr receive;
uint32_t receiveSize;
uint8_t *receivePacket = malloc(500);
int sent =sendto(sock, packet, 60, 0, (struct sockaddr *)&send, sizeof(struct sockaddr));
if (sent < 0) {
perror("Failed to send. \n");
exit(1);
}
int response = recvfrom(sock, receivePacket, 60, 0, &receive, &receiveSize);
struct iphdr *ih = (struct iphdr*)receivePacket;
struct icmphdr *ich =(struct icmphdr*) (receivePacket+sizeof(struct iphdr));
printf("protocal %d\n",ih->version);
if(response > 0)
{
unsigned int i;
for(i=0;i<60;++i){
printf("%02x ",receivePacket[i]);
}
}
/*}*/
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment