UdpOutDevice.cc
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00024 #define WANT_WINSOCK2
00025 #include <platdep/sockets.h>
00026
00027 #include "IPDatagram_m.h"
00028 #include "UDPPacket.h"
00029 #include "IPAddressResolver.h"
00030
00031 #include "UdpOutDevice.h"
00032
00033
00034 Define_Module(UdpOutDevice);
00035
00036 char* UdpOutDevice::encapsulate(cPacket *msg,
00037 unsigned int* length,
00038 sockaddr** addr,
00039 socklen_t* addrlen)
00040 {
00041 cPacket* payloadMsg = NULL;
00042 char* payload = NULL;
00043 sockaddr_in* addrbuf = NULL;
00044
00045 unsigned int payloadLen;
00046
00047 IPDatagram* IP = check_and_cast<IPDatagram*>(msg);
00048
00049 UDPPacket* UDP = dynamic_cast<UDPPacket*>(IP->decapsulate());
00050
00051 if (!UDP) {
00052 EV << "[UdpOutDevice::encapsulate()]\n"
00053 << " Can't parse non-UDP packets (e.g. ICMP) (yet)"
00054 << endl;
00055
00056 goto parse_error;
00057 }
00058
00059
00060 if( IP->getMoreFragments() ) {
00061 EV << "[UdpOutDevice::encapsulate()]\n"
00062 << " Can't parse fragmented packets"
00063 << endl;
00064 goto parse_error;
00065 }
00066
00067 payloadMsg = UDP->decapsulate();
00068
00069
00070 payload = parser->encapsulatePayload(payloadMsg, &payloadLen);
00071 if (!payload) {
00072 EV << "[UdpOutDevice::encapsulate()]\n"
00073 << " Can't parse packet payload, dropping packet"
00074 << endl;
00075 goto parse_error;
00076 }
00077
00078 if (payloadLen > mtu) {
00079 EV << "[UdpOutDevice::encapsulate()]\n"
00080 << " Encapsulating packet failed: packet too long"
00081 << endl;
00082 goto parse_error;
00083 }
00084
00085 *length = payloadLen;
00086
00087
00088 addrbuf = new sockaddr_in;
00089 addrbuf->sin_family = AF_INET;
00090 addrbuf->sin_port = htons(UDP->getDestinationPort());
00091 addrbuf->sin_addr.s_addr = htonl(IP->getDestAddress().getInt());
00092 *addrlen = sizeof(sockaddr_in);
00093 *addr = (sockaddr*) addrbuf;
00094
00095 delete IP;
00096 delete UDP;
00097 delete payloadMsg;
00098 return payload;
00099
00100 parse_error:
00101 delete IP;
00102 delete UDP;
00103 delete payloadMsg;
00104 delete payload;
00105 return NULL;
00106
00107 }
00108
00109 cPacket* UdpOutDevice::decapsulate(char* buf,
00110 uint32_t length,
00111 sockaddr* addr,
00112 socklen_t addrlen)
00113 {
00114 if (!addr) {
00115 opp_error("UdpOutDevice::decapsulate called without providing "
00116 "sockaddr (addr = NULL)");
00117 }
00118
00119 if (addrlen != sizeof(sockaddr_in) ) {
00120 opp_error("UdpOutDevice::decapsulate called with wrong sockaddr length. "
00121 "Only IPv4 is supported at the moment!");
00122 }
00123 sockaddr_in* addrbuf = (sockaddr_in*) addr;
00124
00125 IPDatagram* IP = new IPDatagram;
00126 UDPPacket* UDP = new UDPPacket;
00127 cPacket* payload = 0;
00128
00129
00130 payload = parser->decapsulatePayload(buf, length);
00131
00132 if (!payload) {
00133 EV << "[UdpOutDevice::decapsulate()]\n"
00134 << " Parsing of payload failed, dropping packet"
00135 << endl;
00136 goto parse_error;
00137 }
00138
00139
00140 IP->setSrcAddress(IPAddress(ntohl(addrbuf->sin_addr.s_addr)));
00141 IP->setDestAddress(IPAddressResolver().addressOf(getParentModule()).get4());
00142 IP->setTransportProtocol(IPPROTO_UDP);
00143 IP->setTimeToLive(42);
00144 IP->setIdentification(42);
00145 IP->setMoreFragments(false);
00146 IP->setDontFragment(false);
00147 IP->setFragmentOffset(0);
00148 IP->setDiffServCodePoint(0);
00149 IP->setBitLength(160);
00150
00151 UDP->setSourcePort(ntohs(addrbuf->sin_port));
00152 UDP->setDestinationPort(getParentModule()->getSubmodule("overlay", 0)->
00153 gate("appIn")->getNextGate()->getOwnerModule()->
00154 par("localPort").longValue());
00155
00156 UDP->setByteLength(8);
00157
00158
00159 UDP->encapsulate(payload);
00160 IP->encapsulate(UDP);
00161 delete[] buf;
00162 delete addr;
00163 return IP;
00164
00165 parse_error:
00166 delete IP;
00167 delete UDP;
00168 delete[] buf;
00169 delete addr;
00170 delete payload;
00171 return NULL;
00172 }
00173