Commit 69d7d09e authored by 's avatar
Browse files

test


git-svn-id: file:///home/svn/mapi/trunk@922 8d5bb341-7cf1-0310-8cf6-ba355fef3186
parent 880852a2
......@@ -11,125 +11,500 @@
#include <mapi.h>
#include "../test.h"
int main(int argc, char *argv[])
{
int fd,fid;
mapi_results_t *cnt, *cnt2;
mapi_results_t* res;
int err_no=0;
char error[512];
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/time.h>
#include <time.h>
#include <ctype.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
if(argc!=2){
fprintf(stderr, "Wrong Arguments\n");
return -1;
#include <net/ethernet.h>
#include <netinet/ip.h>
#include <netinet/tcp.h>
#include <netinet/udp.h>
#include <netinet/ip_icmp.h>
#include <netdb.h>
#include "util.h"
void CreateTCPFlagString(struct tcphdr *tcph, char *flagBuffer);
void print_mapi_pkt(struct mapipkt *rec, int print_payload){
unsigned char *p;
unsigned char *nextlayer;
unsigned char *payload;
int i=0, j=0;
char abuf[17]; // for payload print
char tcpFlags[9];
struct ether_header *eth;
uint16_t ethertype;
struct iphdr *iph;
struct tcphdr *tcph;
struct udphdr *udph;
struct icmp *icmph;
struct protoent *pt; //protocol name
//printf("caplen: %u, wlen: %u\n", rec->caplen, rec->wlen);
p = &(rec->pkt);
// lay the Ethernet header struct over the packet data
eth = (struct ether_header *)p;
// Datalink layer
// TODO: timestamp info goes here..
for(j=0; j<ETH_ALEN; j++) {
printf("%X", eth->ether_shost[j]);
if(j != 5) printf(":");
}
printf(" > ");
for(j=0; j<ETH_ALEN; j++){
printf("%X", eth->ether_dhost[j]);
if(j != 5) printf(":");
}
ethertype = ntohs(eth->ether_type);
printf(" type 0x%x ", ethertype);
switch (ethertype) {
case ETHERTYPE_IP: printf("IPv4\n"); break;
case ETHERTYPE_ARP: printf("ARP\n"); break;
case ETHERTYPE_REVARP: printf("Reverse ARP\n"); break;
default: printf("\n"); break;
}
/*while((opt = getopt(argc, argv, "i:r:")) != EOF)
// skip ethernet header (14 bytes)
nextlayer = (unsigned char *) (p + ETH_HLEN);
// IP
if (ethertype == ETHERTYPE_IP) {
// lay the IP header struct over the packet data
iph = (struct iphdr *)nextlayer;
// skip IP header
nextlayer += iph->ihl * 4;
switch (iph->protocol) {
case IPPROTO_TCP:
// lay the TCP header struct over the packet data
tcph = (struct tcphdr *)nextlayer;
// skip TCP header
nextlayer += tcph->doff * 4;
printf("%s:%d > ", inet_ntoa(*(struct in_addr *)&(iph->saddr)), ntohs(tcph->source));
printf("%s:%d", inet_ntoa(*(struct in_addr *)&(iph->daddr)), ntohs(tcph->dest));
printf(" TCP TTL:%d TOS:0x%X ID:%d IpLen:%d DgmLen:%d\n",
iph->ttl, iph->tos, ntohs(iph->id),
iph->ihl << 2, ntohs(iph->tot_len));
// print TCP flags
CreateTCPFlagString(tcph, tcpFlags);
printf("%s ", tcpFlags);
// print other TCP info
printf(" Seq: 0x%lX Ack: 0x%lX Win: 0x%X TcpLen: %d\n",
(u_long) ntohl(tcph->seq), (u_long) ntohl(tcph->ack_seq),
ntohs(tcph->window), tcph->doff << 2);
break;
case IPPROTO_UDP:
// lay the UDP header struct over the packet data
udph = (struct udphdr *)nextlayer;
// skip UDP header
nextlayer = (unsigned char *) udph + UDP_HEADER_LEN;
printf("%s:%d > ", inet_ntoa(*(struct in_addr *)&(iph->saddr)), ntohs(udph->source));
printf("%s:%d", inet_ntoa(*(struct in_addr *)&(iph->daddr)), ntohs(udph->dest));
printf(" UDP TTL:%d TOS:0x%X ID:%d IpLen:%d DgmLen:%d\n",
iph->ttl, iph->tos, ntohs(iph->id),
iph->ihl << 2, ntohs(iph->tot_len));
printf("Len: %d\n", ntohs(udph->len) - UDP_HEADER_LEN);
break;
case IPPROTO_ICMP:
// lay the ICMP header struct over the packet data
icmph = (struct icmp *)nextlayer;
nextlayer = (unsigned char *) icmph + 8;
printf("%s > ", inet_ntoa(*(struct in_addr *)&(iph->saddr)));
printf("%s", inet_ntoa(*(struct in_addr *)&(iph->daddr)));
printf(" ICMP TTL:%d TOS:0x%X ID:%d IpLen:%d DgmLen:%d\n",
iph->ttl, iph->tos, ntohs(iph->id),
iph->ihl << 2, ntohs(iph->tot_len));
printf("Type: %d Code: %d ", icmph->icmp_type, icmph->icmp_code);
switch(icmph->icmp_type){
case ICMP_ECHOREPLY:
printf("ID: %d Seq: %d ECHO REPLY",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_DEST_UNREACH:
printf("DESTINATION UNREACHABLE: ");
switch(icmph->icmp_code){
case ICMP_NET_UNREACH:
printf("NET UNREACHABLE");
break;
case ICMP_HOST_UNREACH:
printf("HOST UNREACHABLE");
break;
case ICMP_PROT_UNREACH:
printf("PROTOCOL UNREACHABLE");
break;
case ICMP_PORT_UNREACH:
printf("PORT UNREACHABLE");
break;
case ICMP_FRAG_NEEDED:
printf("FRAGMENTATION NEEDED, DF SET\n"
"NEXT LINK MTU: %u",
ntohs(icmph->icmp_nextmtu));
break;
case ICMP_SR_FAILED:
printf("SOURCE ROUTE FAILED");
break;
case ICMP_NET_UNKNOWN:
printf("NET UNKNOWN");
break;
case ICMP_HOST_UNKNOWN:
printf("HOST UNKNOWN");
break;
case ICMP_HOST_ISOLATED:
printf("HOST ISOLATED");
break;
case ICMP_PKT_FILTERED_NET:
printf("ADMINISTRATIVELY PROHIBITED NETWORK FILTERED");
break;
case ICMP_PKT_FILTERED_HOST:
printf("ADMINISTRATIVELY PROHIBITED HOST FILTERED");
break;
case ICMP_NET_UNR_TOS:
printf("NET UNREACHABLE FOR TOS");
break;
case ICMP_HOST_UNR_TOS:
printf("HOST UNREACHABLE FOR TOS");
break;
case ICMP_PKT_FILTERED:
printf("ADMINISTRATIVELY PROHIBITED,\nPACKET FILTERED");
break;
case ICMP_PREC_VIOLATION:
printf("PREC VIOLATION");
break;
case ICMP_PREC_CUTOFF:
printf("PREC CUTOFF");
break;
default:
printf("UNKNOWN");
break;
}
break;
case ICMP_SOURCE_QUENCH:
printf("SOURCE QUENCH");
break;
case ICMP_REDIRECT:
printf("REDIRECT");
switch(icmph->icmp_code)
{
case ICMP_REDIR_NET:
printf(" NET");
break;
case ICMP_REDIR_HOST:
printf(" HOST");
break;
case ICMP_REDIR_TOS_NET:
printf(" TOS NET");
break;
case ICMP_REDIR_TOS_HOST:
printf(" TOS HOST");
break;
}
break;
case ICMP_ECHO:
printf("ID: %d Seq: %d ECHO",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_ROUTER_ADVERTISE:
printf("ROUTER ADVERTISMENT: "
"Num addrs: %d Addr entry size: %d Lifetime: %u",
icmph->icmp_num_addrs, icmph->icmp_wpa,
icmph->icmp_lifetime);
break;
case ICMP_ROUTER_SOLICIT:
printf("ROUTER SOLICITATION");
break;
case ICMP_TIME_EXCEEDED:
printf("TTL EXCEEDED");
switch(icmph->icmp_code)
{
case ICMP_TIMEOUT_TRANSIT:
printf(" IN TRANSIT");
break;
case ICMP_TIMEOUT_REASSY:
printf(" TIME EXCEEDED IN FRAG REASSEMBLY");
break;
}
break;
case ICMP_PARAMETERPROB:
printf("PARAMETER PROBLEM");
switch(icmph->icmp_code)
{
case ICMP_PARAM_BADIPHDR:
printf(": BAD IP HEADER BYTE %u", icmph->icmp_pptr);
break;
case ICMP_PARAM_OPTMISSING:
printf(": OPTION MISSING");
break;
case ICMP_PARAM_BAD_LENGTH:
printf(": BAD LENGTH");
break;
}
break;
case ICMP_TIMESTAMP:
printf("ID: %u Seq: %u TIMESTAMP REQUEST",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_TIMESTAMPREPLY:
printf("ID: %u Seq: %u TIMESTAMP REPLY:\n"
"Orig: %u Rtime: %u Ttime: %u",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq),
icmph->icmp_otime, icmph->icmp_rtime,
icmph->icmp_ttime);
break;
case ICMP_INFO_REQUEST:
printf("ID: %u Seq: %u INFO REQUEST",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_INFO_REPLY:
printf("ID: %u Seq: %u INFO REPLY",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_ADDRESS:
printf("ID: %u Seq: %u ADDRESS REQUEST",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq));
break;
case ICMP_ADDRESSREPLY:
printf("ID: %u Seq: %u ADDRESS REPLY: 0x%08X",
ntohs(icmph->icmp_id), ntohs(icmph->icmp_seq),
(u_int) icmph->icmp_mask);
break;
default:
printf("UNKNOWN");
break;
}
printf("\n");
break;
default:
printf("%s > ", inet_ntoa(*(struct in_addr *)&(iph->saddr)));
printf("%s", inet_ntoa(*(struct in_addr *)&(iph->daddr)));
pt = getprotobynumber(iph->protocol); // get protocol name
printf(" %s TTL:%d TOS:0x%X ID:%d IpLen:%d DgmLen:%d\n",
pt->p_name, iph->ttl, iph->tos, ntohs(iph->id),
iph->ihl << 2, ntohs(iph->tot_len));
break;
}
}
// Payload
if((nextlayer != NULL) && print_payload){
payload = nextlayer;
memset(abuf, 0, 17);
for( i=0; (unsigned int)payload < (unsigned int)(&rec->pkt)+(rec->caplen); payload++, i++) {
abuf[i%16] = isprint(*payload&0xff) ? (*payload&0xff) : '.';
printf("%02x ", *payload&0xff);
if ((i%16)==15) {
printf(" %s\n", abuf);
memset(abuf, 0, 17);
}
}
if((i > 0) && (i%16 != 16)){
while(i%16) {
printf(" ");
i++;
}
printf(" %s\n", abuf);
}
}
printf("\n");
}
void create_pkt(Packet* pkt, struct mapipkt *rec)
{
unsigned char *p;
unsigned char *nextlayer;
/* unsigned char *payload;
int i=0, j=0;
char abuf[17]; // for payload print
char tcpFlags[9];*/
//printf("caplen: %u, wlen: %u\n", rec->caplen, rec->wlen);
pkt->caplen = rec->caplen;
p = pkt->pkt = &(rec->pkt);
// lay the Ethernet header struct over the packet data
pkt->eth = (struct ether_header *)p;
// Datalink layer
pkt->ethertype = ntohs(pkt->eth->ether_type);
// skip ethernet header (14 bytes)
nextlayer = (unsigned char *) (p + ETH_HLEN);
// IP
if (pkt->ethertype == ETHERTYPE_IP)
{
switch(opt)
// lay the IP header struct over the packet data
pkt->iph = (struct iphdr *)nextlayer;
// skip IP header
nextlayer += pkt->iph->ihl * 4;
switch (pkt->iph->protocol)
{
case 'i':
offline = 0;
name = (char *)strdup(optarg);
case IPPROTO_TCP:
// lay the TCP header struct over the packet data
pkt->tcph = (struct tcphdr *)nextlayer;
// skip TCP header
nextlayer += pkt->tcph->doff * 4;
break;
case IPPROTO_UDP:
// lay the UDP header struct over the packet data
pkt->udph = (struct udphdr *)nextlayer;
// skip UDP header
nextlayer = (unsigned char *) pkt->udph + UDP_HEADER_LEN;
break;
case 'r':
offline = 1;
name = (char *)strdup(optarg);
case IPPROTO_ICMP:
// lay the ICMP header struct over the packet data
pkt->icmph = (struct icmp *)nextlayer;
nextlayer = (unsigned char *) pkt->icmph + 8;
break;
default:
pkt->pt = getprotobynumber(pkt->iph->protocol); // get protocol name
break;
}
}
if(offline) {
fd=mapi_create_offline_flow(name,MFF_PCAP);
fd2=mapi_create_offline_flow(name,MFF_PCAP);
}
else {
fd=mapi_create_flow(name);
fd2=mapi_create_flow(name);
}*/
// Payload
if (nextlayer != NULL)
pkt->payload = nextlayer;
//pkt->payload_size = ntohs(pkt->iph->tot_len) - (pkt->iph->ihl * 4) - (pkt->tcph->doff * 4);
pkt->payload_size = (unsigned int)(&rec->pkt)+(rec->caplen) - (unsigned int)pkt->payload;
}
void CreateTCPFlagString(struct tcphdr *tcph, char *flagBuffer){
// parse TCP flags
*flagBuffer++ = (char) ((tcph->res1) ? '1' : '*');
*flagBuffer++ = (char) ((tcph->res2) ? '2' : '*');
*flagBuffer++ = (char) ((tcph->urg) ? 'U' : '*');
*flagBuffer++ = (char) ((tcph->ack) ? 'A' : '*');
*flagBuffer++ = (char) ((tcph->psh) ? 'P' : '*');
*flagBuffer++ = (char) ((tcph->rst) ? 'R' : '*');
*flagBuffer++ = (char) ((tcph->syn) ? 'S' : '*');
*flagBuffer++ = (char) ((tcph->fin) ? 'F' : '*');
*flagBuffer = '\0';
}
if ((fd = mapi_create_flow(argv[1]))<0){
fprintf(stderr, "Could not create flow using '%s'\n", argv[1]);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if((fid=mapi_apply_function(fd, "PKT_COUNTER"))<0){
fprintf(stderr, "Could not apply PKT_COUNTER to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
int main(int argc, char *argv[])
{
int fd,fid;
int fid1,fid2;
int err_no=0;
char error[512];
struct mapipkt *pkt;
mapi_results_t* res1, * res2;
if(argc!=2){
fprintf(stderr, "Wrong Arguments\n");
return -1;
}
DOT;
if(mapi_apply_function(fd,"COOKING",100000,10)<0){
fprintf(stderr, "Could not apply COOKING to flow %d\n", fd);
if ((fd = mapi_create_flow(argv[1]))<0){
fprintf(stderr, "Could not create flow using '%s'\n", argv[1]);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if(mapi_connect(fd)<0){
fprintf(stderr, "Connecting to flow failed %d\n", fd);
if((fid=mapi_apply_function(fd, "BPF_FILTER","port 80"))<0){
fprintf(stderr, "Could not apply BPF_FILTER to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
/*
* sanity checks
*/
usleep(200000); /* 0.2 sec */
DOT;
res = mapi_read_results(fd, fid);
printf("\nBytes till now : %llu\n", *((unsigned long long*)res->res));
/* assuming 40 Gbit/s... :-) */
if (*((unsigned long long*)res->res) > 1000000000) { /* ~1 GB (40*0.2*10^9/8 bytes) */
fprintf(stderr, "\nWARNING: suspiciously high byte count (%llu)\n",
*((unsigned long long *)res->res));
}
if(mapi_close_flow(fd)<0){
fprintf(stderr,"Close flow failed\n");
if((fid1=mapi_apply_function(fd, "PKT_COUNTER"))<0){
fprintf(stderr, "Could not apply PKT_COUNTER 1 to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if ((fd = mapi_create_offline_flow("./tracefile" , MFF_PCAP))<0){
fprintf(stderr, "Could not create flow using './tracefile'\n");
if(mapi_apply_function(fd,"COOKING",10000,10,0,BOTH_SIDE)<0){
fprintf(stderr, "Could not apply COOKING to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if((fid=mapi_apply_function(fd, "PKT_COUNTER"))<0){
fprintf(stderr, "Could not apply PKT_COUNTER to flow %d\n", fd);
if((fid=mapi_apply_function(fd, "TO_BUFFER"))<0){
fprintf(stderr, "Could not apply TO_BUFFER to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if(mapi_apply_function(fd,"COOKING",100000,10)<0){
fprintf(stderr, "Could not apply COOKING to flow %d\n", fd);
if((fid2=mapi_apply_function(fd, "PKT_COUNTER"))<0){
fprintf(stderr, "Could not apply PKT_COUNTER 2 to flow %d\n", fd);
mapi_read_error(&err_no, error);
fprintf(stderr,"Erorcode :%d description: %s \n" ,err_no, error);
return -1;
}
DOT;
if(mapi_connect(fd)<0){
fprintf(stderr, "Connecting to flow failed %d\n", fd);
mapi_read_error(&err_no, error);
......@@ -137,23 +512,25 @@ DOT;
return -1;
}
DOT;
/*
* sanity checks
*/
usleep(200000);
cnt = mapi_read_results(fd,fid);
DOT;
cnt2 =mapi_read_results(fd,fid);
DOT;
while (1)
{
res1=mapi_read_results(fd, fid1);
printf("pkts before cooking %d\n",*((int*)res1->res));
if (*((unsigned long long*)cnt->res)!=*((unsigned long long*)cnt2->res) ) { /* ~1 GB (40*0.2*10^9/8 bytes) */
fprintf(stderr, "\nWARNING: Difference at packet count before and after cooking %llu and %llu respectively\n",
*((unsigned long long*)cnt->res),
*((unsigned long long*)cnt2->res));
res2=mapi_read_results(fd, fid2);
printf("pkts after cooking %d\n",*((int*)res2->res));
sleep(1);
}
if((pkt=mapi_get_next_pkt(fd, fid)) != NULL){
printf("Got packet\n");
print_mapi_pkt(pkt, 1);
}
else{
printf("\nError in mapi_get_next_packet\n");
}
DOT;