00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037 #ifndef ns_packet_h
00038 #define ns_packet_h
00039
00040 #include <string.h>
00041 #include <assert.h>
00042
00043 #include "config.h"
00044 #include "scheduler.h"
00045 #include "object.h"
00046 #include "lib/bsd-list.h"
00047 #include "packet-stamp.h"
00048 #include "ns-process.h"
00049
00050
00051 #define RT_PORT 255
00052
00053 #define HDR_CMN(p) (hdr_cmn::access(p))
00054 #define HDR_ARP(p) (hdr_arp::access(p))
00055 #define HDR_MAC(p) (hdr_mac::access(p))
00056 #define HDR_MAC802_11(p) ((hdr_mac802_11 *)hdr_mac::access(p))
00057 #define HDR_MAC_TDMA(p) ((hdr_mac_tdma *)hdr_mac::access(p))
00058 #define HDR_SMAC(p) ((hdr_smac *)hdr_mac::access(p))
00059 #define HDR_LL(p) (hdr_ll::access(p))
00060 #define HDR_HDLC(p) ((hdr_hdlc *)hdr_ll::access(p))
00061 #define HDR_IP(p) (hdr_ip::access(p))
00062 #define HDR_RTP(p) (hdr_rtp::access(p))
00063 #define HDR_TCP(p) (hdr_tcp::access(p))
00064 #define HDR_SCTP(p) (hdr_sctp::access(p))
00065 #define HDR_SR(p) (hdr_sr::access(p))
00066 #define HDR_TFRC(p) (hdr_tfrc::access(p))
00067 #define HDR_TORA(p) (hdr_tora::access(p))
00068 #define HDR_IMEP(p) (hdr_imep::access(p))
00069 #define HDR_CDIFF(p) (hdr_cdiff::access(p))
00070
00071 #define HDR_LMS(p) (hdr_lms::access(p))
00072
00073
00074
00075 enum packet_t {
00076 PT_TCP,
00077 PT_UDP,
00078 PT_CBR,
00079 PT_AUDIO,
00080 PT_VIDEO,
00081 PT_ACK,
00082 PT_START,
00083 PT_STOP,
00084 PT_PRUNE,
00085 PT_GRAFT,
00086 PT_GRAFTACK,
00087 PT_JOIN,
00088 PT_ASSERT,
00089 PT_MESSAGE,
00090 PT_RTCP,
00091 PT_RTP,
00092 PT_RTPROTO_DV,
00093 PT_CtrMcast_Encap,
00094 PT_CtrMcast_Decap,
00095 PT_SRM,
00096
00097 PT_REQUEST,
00098 PT_ACCEPT,
00099 PT_CONFIRM,
00100 PT_TEARDOWN,
00101 PT_LIVE,
00102 PT_REJECT,
00103
00104 PT_TELNET,
00105 PT_FTP,
00106 PT_PARETO,
00107 PT_EXP,
00108 PT_INVAL,
00109 PT_HTTP,
00110
00111
00112 PT_ENCAPSULATED,
00113 PT_MFTP,
00114
00115
00116 PT_ARP,
00117 PT_MAC,
00118 PT_TORA,
00119 PT_DSR,
00120 PT_AODV,
00121 PT_IMEP,
00122
00123
00124 PT_RAP_DATA,
00125 PT_RAP_ACK,
00126
00127 PT_TFRC,
00128 PT_TFRC_ACK,
00129 PT_PING,
00130
00131
00132 PT_DIFF,
00133
00134
00135 PT_RTPROTO_LS,
00136
00137
00138 PT_LDP,
00139
00140
00141 PT_GAF,
00142
00143
00144 PT_REALAUDIO,
00145
00146
00147 PT_PUSHBACK,
00148
00149 #ifdef HAVE_STL
00150
00151 PT_PGM,
00152 #endif //STL
00153
00154
00155 PT_LMS,
00156 PT_LMS_SETUP,
00157
00158 PT_SCTP,
00159 PT_SCTP_APP1,
00160
00161
00162 PT_SMAC,
00163
00164
00165 PT_XCP,
00166
00167
00168 PT_HDLC,
00169
00170
00171 PT_NTYPE
00172 };
00173
00174 class p_info {
00175 public:
00176 p_info() {
00177 name_[PT_TCP]= "tcp";
00178 name_[PT_UDP]= "udp";
00179 name_[PT_CBR]= "cbr";
00180 name_[PT_AUDIO]= "audio";
00181 name_[PT_VIDEO]= "video";
00182 name_[PT_ACK]= "ack";
00183 name_[PT_START]= "start";
00184 name_[PT_STOP]= "stop";
00185 name_[PT_PRUNE]= "prune";
00186 name_[PT_GRAFT]= "graft";
00187 name_[PT_GRAFTACK]= "graftAck";
00188 name_[PT_JOIN]= "join";
00189 name_[PT_ASSERT]= "assert";
00190 name_[PT_MESSAGE]= "message";
00191 name_[PT_RTCP]= "rtcp";
00192 name_[PT_RTP]= "rtp";
00193 name_[PT_RTPROTO_DV]= "rtProtoDV";
00194 name_[PT_CtrMcast_Encap]= "CtrMcast_Encap";
00195 name_[PT_CtrMcast_Decap]= "CtrMcast_Decap";
00196 name_[PT_SRM]= "SRM";
00197
00198 name_[PT_REQUEST]= "sa_req";
00199 name_[PT_ACCEPT]= "sa_accept";
00200 name_[PT_CONFIRM]= "sa_conf";
00201 name_[PT_TEARDOWN]= "sa_teardown";
00202 name_[PT_LIVE]= "live";
00203 name_[PT_REJECT]= "sa_reject";
00204
00205 name_[PT_TELNET]= "telnet";
00206 name_[PT_FTP]= "ftp";
00207 name_[PT_PARETO]= "pareto";
00208 name_[PT_EXP]= "exp";
00209 name_[PT_INVAL]= "httpInval";
00210 name_[PT_HTTP]= "http";
00211 name_[PT_ENCAPSULATED]= "encap";
00212 name_[PT_MFTP]= "mftp";
00213 name_[PT_ARP]= "ARP";
00214 name_[PT_MAC]= "MAC";
00215 name_[PT_TORA]= "TORA";
00216 name_[PT_DSR]= "DSR";
00217 name_[PT_AODV]= "AODV";
00218 name_[PT_IMEP]= "IMEP";
00219
00220 name_[PT_RAP_DATA] = "rap_data";
00221 name_[PT_RAP_ACK] = "rap_ack";
00222
00223 name_[PT_TFRC]= "tcpFriend";
00224 name_[PT_TFRC_ACK]= "tcpFriendCtl";
00225 name_[PT_PING]="ping";
00226
00227
00228 name_[PT_DIFF] = "diffusion";
00229
00230
00231 name_[PT_RTPROTO_LS] = "rtProtoLS";
00232
00233
00234 name_[PT_LDP] = "LDP";
00235
00236
00237 name_[PT_GAF] = "gaf";
00238
00239
00240 name_[PT_REALAUDIO] = "ra";
00241
00242
00243 name_[PT_PUSHBACK] = "pushback";
00244
00245 #ifdef HAVE_STL
00246
00247 name_[PT_PGM] = "PGM";
00248 #endif //STL
00249
00250
00251 name_[PT_LMS]="LMS";
00252 name_[PT_LMS_SETUP]="LMS_SETUP";
00253
00254 name_[PT_SCTP]= "sctp";
00255 name_[PT_SCTP_APP1] = "sctp_app1";
00256
00257
00258 name_[PT_SMAC]="smac";
00259
00260
00261 name_[PT_HDLC]="HDLC";
00262
00263
00264 name_[PT_XCP]="xcp";
00265
00266 name_[PT_NTYPE]= "undefined";
00267 }
00268 const char* name(packet_t p) const {
00269 if ( p <= PT_NTYPE ) return name_[p];
00270 return 0;
00271 }
00272 static bool data_packet(packet_t type) {
00273 return ( (type) == PT_TCP || \
00274 (type) == PT_TELNET || \
00275 (type) == PT_CBR || \
00276 (type) == PT_AUDIO || \
00277 (type) == PT_VIDEO || \
00278 (type) == PT_ACK || \
00279 (type) == PT_SCTP || \
00280 (type) == PT_SCTP_APP1 || \
00281 (type) == PT_HDLC \
00282 );
00283 }
00284 private:
00285 static char* name_[PT_NTYPE+1];
00286 };
00287 extern p_info packet_info;
00288
00289
00290
00291 #define DATA_PACKET(type) ( (type) == PT_TCP || \
00292 (type) == PT_TELNET || \
00293 (type) == PT_CBR || \
00294 (type) == PT_AUDIO || \
00295 (type) == PT_VIDEO || \
00296 (type) == PT_ACK || \
00297 (type) == PT_SCTP || \
00298 (type) == PT_SCTP_APP1 \
00299 )
00300
00301
00302 #define OFFSET(type, field) ((long) &((type *)0)->field)
00303
00304 class PacketData : public AppData {
00305 public:
00306 PacketData(int sz) : AppData(PACKET_DATA) {
00307 datalen_ = sz;
00308 if (datalen_ > 0)
00309 data_ = new unsigned char[datalen_];
00310 else
00311 data_ = NULL;
00312 }
00313 PacketData(PacketData& d) : AppData(d) {
00314 datalen_ = d.datalen_;
00315 if (datalen_ > 0) {
00316 data_ = new unsigned char[datalen_];
00317 memcpy(data_, d.data_, datalen_);
00318 } else
00319 data_ = NULL;
00320 }
00321 virtual ~PacketData() {
00322 if (data_ != NULL)
00323 delete []data_;
00324 }
00325 unsigned char* data() { return data_; }
00326
00327 virtual int size() const { return datalen_; }
00328 virtual AppData* copy() { return new PacketData(*this); }
00329 private:
00330 unsigned char* data_;
00331 int datalen_;
00332 };
00333
00334
00335 typedef void (*FailureCallback)(Packet *,void *);
00336
00337 class Packet : public Event {
00338 private:
00339 unsigned char* bits_;
00340
00341
00342 AppData* data_;
00343 static void init(Packet*);
00344 bool fflag_;
00345 protected:
00346 static Packet* free_;
00347 int ref_count_;
00348 public:
00349 Packet* next_;
00350 static int hdrlen_;
00351
00352 Packet() : bits_(0), data_(0), ref_count_(0), next_(0) { }
00353 inline unsigned char* const bits() { return (bits_); }
00354 inline Packet* copy() const;
00355 inline Packet* refcopy() { ++ref_count_; return this; }
00356 inline int& ref_count() { return (ref_count_); }
00357 static inline Packet* alloc();
00358 static inline Packet* alloc(int);
00359 inline void allocdata(int);
00360
00361 inline void initdata() { data_ = 0;}
00362 static inline void free(Packet*);
00363 inline unsigned char* access(int off) const {
00364 if (off < 0)
00365 abort();
00366 return (&bits_[off]);
00367 }
00368
00369
00370 inline unsigned char* accessdata() const {
00371 if (data_ == 0)
00372 return 0;
00373 assert(data_->type() == PACKET_DATA);
00374 return (((PacketData*)data_)->data());
00375 }
00376
00377
00378 inline AppData* userdata() const {
00379 return data_;
00380 }
00381 inline void setdata(AppData* d) {
00382 if (data_ != NULL)
00383 delete data_;
00384 data_ = d;
00385 }
00386 inline int datalen() const { return data_ ? data_->size() : 0; }
00387
00388
00389
00390 static void dump_header(Packet *p, int offset, int length);
00391
00392
00393
00394
00395 PacketStamp txinfo_;
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405 u_int8_t incoming;
00406
00407
00408 };
00409
00410
00411
00412
00413
00414 class iface_literal {
00415 public:
00416 enum iface_constant {
00417 UNKN_IFACE= -1,
00418
00419
00420 ANY_IFACE= -2
00421
00422
00423
00424
00425
00426 };
00427 iface_literal(const iface_constant i, const char * const n) :
00428 value_(i), name_(n) {}
00429 inline int value() const { return value_; }
00430 inline const char * const name() const { return name_; }
00431 private:
00432 const iface_constant value_;
00433
00434 const char * const name_;
00435 };
00436
00437 static const iface_literal UNKN_IFACE(iface_literal::UNKN_IFACE, "?");
00438 static const iface_literal ANY_IFACE(iface_literal::ANY_IFACE, "*");
00439
00440
00441
00442
00443
00444
00445 enum ns_af_enum { NS_AF_NONE, NS_AF_ILINK, NS_AF_INET };
00446
00447 struct hdr_cmn {
00448 enum dir_t { DOWN= -1, NONE= 0, UP= 1 };
00449 packet_t ptype_;
00450 int size_;
00451 int uid_;
00452 int error_;
00453 int errbitcnt_;
00454 int fecsize_;
00455 double ts_;
00456 int iface_;
00457 dir_t direction_;
00458
00459 char src_rt_valid;
00460 double ts_arr_;
00461
00462
00463 nsaddr_t prev_hop_;
00464 nsaddr_t next_hop_;
00465 int addr_type_;
00466 nsaddr_t last_hop_;
00467
00468
00469
00470 FailureCallback xmit_failure_;
00471 void *xmit_failure_data_;
00472
00473
00474
00475
00476
00477
00478 int xmit_reason_;
00479 #define XMIT_REASON_RTS 0x01
00480 #define XMIT_REASON_ACK 0x02
00481
00482
00483 int num_forwards_;
00484 int opt_num_forwards_;
00485
00486
00487
00488 double txtime_;
00489 inline double& txtime() { return(txtime_); }
00490
00491 static int offset_;
00492 inline static int& offset() { return offset_; }
00493 inline static hdr_cmn* access(const Packet* p) {
00494 return (hdr_cmn*) p->access(offset_);
00495 }
00496
00497
00498 inline packet_t& ptype() { return (ptype_); }
00499 inline int& size() { return (size_); }
00500 inline int& uid() { return (uid_); }
00501 inline int& error() { return error_; }
00502 inline int& errbitcnt() {return errbitcnt_; }
00503 inline int& fecsize() {return fecsize_; }
00504 inline double& timestamp() { return (ts_); }
00505 inline int& iface() { return (iface_); }
00506 inline dir_t& direction() { return (direction_); }
00507
00508 inline nsaddr_t& next_hop() { return (next_hop_); }
00509 inline int& addr_type() { return (addr_type_); }
00510 inline int& num_forwards() { return (num_forwards_); }
00511 inline int& opt_num_forwards() { return (opt_num_forwards_); }
00512
00513 };
00514
00515
00516 class PacketHeaderClass : public TclClass {
00517 protected:
00518 PacketHeaderClass(const char* classname, int hdrsize);
00519 virtual int method(int argc, const char*const* argv);
00520 void field_offset(const char* fieldname, int offset);
00521 inline void bind_offset(int* off) { offset_ = off; }
00522 inline void offset(int* off) {offset_= off;}
00523 int hdrlen_;
00524 int* offset_;
00525 public:
00526 virtual void bind();
00527 virtual void export_offsets();
00528 TclObject* create(int argc, const char*const* argv);
00529 };
00530
00531
00532 inline void Packet::init(Packet* p)
00533 {
00534 bzero(p->bits_, hdrlen_);
00535 }
00536
00537 inline Packet* Packet::alloc()
00538 {
00539 Packet* p = free_;
00540 if (p != 0) {
00541 assert(p->fflag_ == FALSE);
00542 free_ = p->next_;
00543 assert(p->data_ == 0);
00544 p->uid_ = 0;
00545 p->time_ = 0;
00546 } else {
00547 p = new Packet;
00548 p->bits_ = new unsigned char[hdrlen_];
00549 if (p == 0 || p->bits_ == 0)
00550 abort();
00551 }
00552 init(p);
00553 (HDR_CMN(p))->next_hop_ = -2;
00554 (HDR_CMN(p))->last_hop_ = -2;
00555 p->fflag_ = TRUE;
00556 (HDR_CMN(p))->direction() = hdr_cmn::DOWN;
00557
00558
00559 p->next_ = 0;
00560 return (p);
00561 }
00562
00563
00564
00565
00566
00567
00568 inline void Packet::allocdata(int n)
00569 {
00570 assert(data_ == 0);
00571 data_ = new PacketData(n);
00572 if (data_ == 0)
00573 abort();
00574 }
00575
00576
00577 inline Packet* Packet::alloc(int n)
00578 {
00579 Packet* p = alloc();
00580 if (n > 0)
00581 p->allocdata(n);
00582 return (p);
00583 }
00584
00585
00586 inline void Packet::free(Packet* p)
00587 {
00588 if (p->fflag_) {
00589 if (p->ref_count_ == 0) {
00590
00591
00592
00593
00594 assert(p->uid_ <= 0);
00595
00596 if (p->data_ != 0) {
00597 delete p->data_;
00598 p->data_ = 0;
00599 }
00600 init(p);
00601 p->next_ = free_;
00602 free_ = p;
00603 p->fflag_ = FALSE;
00604 } else {
00605 --p->ref_count_;
00606 }
00607 }
00608 }
00609
00610 inline Packet* Packet::copy() const
00611 {
00612
00613 Packet* p = alloc();
00614 memcpy(p->bits(), bits_, hdrlen_);
00615 if (data_)
00616 p->data_ = data_->copy();
00617 p->txinfo_.init(&txinfo_);
00618
00619 return (p);
00620 }
00621
00622 inline void
00623 Packet::dump_header(Packet *p, int offset, int length)
00624 {
00625 assert(offset + length <= p->hdrlen_);
00626 struct hdr_cmn *ch = HDR_CMN(p);
00627
00628 fprintf(stderr, "\nPacket ID: %d\n", ch->uid());
00629
00630 for(int i = 0; i < length ; i+=16) {
00631 fprintf(stderr, "%02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x\n",
00632 p->bits_[offset + i], p->bits_[offset + i + 1],
00633 p->bits_[offset + i + 2], p->bits_[offset + i + 3],
00634 p->bits_[offset + i + 4], p->bits_[offset + i + 5],
00635 p->bits_[offset + i + 6], p->bits_[offset + i + 7],
00636 p->bits_[offset + i + 8], p->bits_[offset + i + 9],
00637 p->bits_[offset + i + 10], p->bits_[offset + i + 11],
00638 p->bits_[offset + i + 12], p->bits_[offset + i + 13],
00639 p->bits_[offset + i + 14], p->bits_[offset + i + 15]);
00640 }
00641 }
00642
00643 #endif