Public Member Functions

ICMPSerializer Class Reference

#include <ICMPSerializer.h>

List of all members.

Public Member Functions

 ICMPSerializer ()
int serialize (const ICMPMessage *pkt, unsigned char *buf, unsigned int bufsize)
void parse (const unsigned char *buf, unsigned int bufsize, ICMPMessage *pkt)

Detailed Description

Converts between ICMPMessage and binary (network byte order) ICMP header.

Definition at line 28 of file ICMPSerializer.h.


Constructor & Destructor Documentation

ICMPSerializer::ICMPSerializer (  )  [inline]

Definition at line 31 of file ICMPSerializer.h.

{}


Member Function Documentation

void ICMPSerializer::parse ( const unsigned char *  buf,
unsigned int  bufsize,
ICMPMessage *  pkt 
)

Puts a packet sniffed from the wire into an ICMPMessage.

Definition at line 107 of file ICMPSerializer.cc.

{
    struct icmp *icmp = (struct icmp*) buf;

    switch(icmp->icmp_type)
    {
        case ICMP_ECHO:
        {
            PingPayload *pp;
            char name[32];

            pkt->setType(ICMP_ECHO_REQUEST);
            pkt->setCode(0);
            pkt->setByteLength(4);
            sprintf(name,"ping%d", ntohs(icmp->icmp_seq));
            pp = new PingPayload(name);
            pp->setOriginatorId(ntohs(icmp->icmp_id));
            pp->setSeqNo(ntohs(icmp->icmp_seq));
            pp->setByteLength(bufsize - 4);
            pp->setDataArraySize(bufsize - ICMP_MINLEN);
            for(unsigned int i=0; i<bufsize - ICMP_MINLEN; i++)
                pp->setData(i, icmp->icmp_data[i]);
            pkt->encapsulate(pp);
            pkt->setName(pp->getName());
            break;
        }
        case ICMP_ECHOREPLY:
        {
            PingPayload *pp;
            char name[32];

            pkt->setType(ICMP_ECHO_REPLY);
            pkt->setCode(0);
            pkt->setByteLength(4);
            sprintf(name,"ping%d-reply", ntohs(icmp->icmp_seq));
            pp = new PingPayload(name);
            pp->setOriginatorId(ntohs(icmp->icmp_id));
            pp->setSeqNo(ntohs(icmp->icmp_seq));
            pp->setByteLength(bufsize - 4);
            pp->setDataArraySize(bufsize - ICMP_MINLEN);
            for (unsigned int i=0; i<bufsize - ICMP_MINLEN; i++)
                pp->setData(i, icmp->icmp_data[i]);
            pkt->encapsulate(pp);
            pkt->setName(pp->getName());
            break;
        }
        default:
        {
            EV << "Can not create ICMP packet: type " << icmp->icmp_type << " not supported.";
            break;
        }
    }
}

int ICMPSerializer::serialize ( const ICMPMessage *  pkt,
unsigned char *  buf,
unsigned int  bufsize 
)

Serializes an ICMPMessage for transmission on the wire. Returns the length of data written into buffer.

Definition at line 41 of file ICMPSerializer.cc.

{
    struct icmp *icmp = (struct icmp *) (buf);
    int packetLength;

    packetLength = ICMP_MINLEN;

    switch(pkt->getType())
    {
        case ICMP_ECHO_REQUEST:
        {
            PingPayload *pp = check_and_cast<PingPayload* >(pkt->getEncapsulatedMsg());
            icmp->icmp_type = ICMP_ECHO;
            icmp->icmp_code = 0;
            icmp->icmp_id   = htons(pp->getOriginatorId());
            icmp->icmp_seq  = htons(pp->getSeqNo());
            unsigned int datalen = (pp->getByteLength() - 4);
            for (unsigned int i=0; i < datalen; i++)
                if (i < pp->getDataArraySize()) {
                    icmp->icmp_data[i] = pp->getData(i);
                } else {
                    icmp->icmp_data[i] = 'a';
                }
            packetLength += datalen;
            break;
        }
        case ICMP_ECHO_REPLY:
        {
            PingPayload *pp = check_and_cast<PingPayload* >(pkt->getEncapsulatedMsg());
            icmp->icmp_type = ICMP_ECHOREPLY;
            icmp->icmp_code = 0;
            icmp->icmp_id   = htons(pp->getOriginatorId());
            icmp->icmp_seq  = htons(pp->getSeqNo());
            unsigned int datalen = pp->getDataArraySize();
            for(unsigned int i=0; i < datalen; i++)
                icmp->icmp_data[i] = pp->getData(i);
            packetLength += datalen;
            break;
        }
        case ICMP_DESTINATION_UNREACHABLE:
        {
            IPDatagram *ip = check_and_cast<IPDatagram* >(pkt->getEncapsulatedMsg());
            icmp->icmp_type = ICMP_UNREACH;
            icmp->icmp_code = pkt->getCode();
            packetLength += IPSerializer().serialize(ip, (unsigned char *)icmp->icmp_data, bufsize - ICMP_MINLEN);
            break;
        }
        case ICMP_TIME_EXCEEDED:
        {
            IPDatagram *ip = check_and_cast<IPDatagram* >(pkt->getEncapsulatedMsg());
            icmp->icmp_type = ICMP_TIMXCEED;
            icmp->icmp_code = ICMP_TIMXCEED_INTRANS;
            packetLength += IPSerializer().serialize(ip, (unsigned char *)icmp->icmp_data, bufsize - ICMP_MINLEN);
            break;
        }
        default:
        {
            packetLength = 0;
            EV << "Can not serialize ICMP packet: type " << pkt->getType() << " not supported.";
            break;
        }
    }
    icmp->icmp_cksum = TCPIPchecksum::checksum(buf, packetLength);
    return packetLength;
}


The documentation for this class was generated from the following files: