inet.hh revision 1762
12391SN/A/* 22391SN/A * Copyright (c) 2002-2005 The Regents of The University of Michigan 32391SN/A * All rights reserved. 42391SN/A * 52391SN/A * Redistribution and use in source and binary forms, with or without 62391SN/A * modification, are permitted provided that the following conditions are 72391SN/A * met: redistributions of source code must retain the above copyright 82391SN/A * notice, this list of conditions and the following disclaimer; 92391SN/A * redistributions in binary form must reproduce the above copyright 102391SN/A * notice, this list of conditions and the following disclaimer in the 112391SN/A * documentation and/or other materials provided with the distribution; 122391SN/A * neither the name of the copyright holders nor the names of its 132391SN/A * contributors may be used to endorse or promote products derived from 142391SN/A * this software without specific prior written permission. 152391SN/A * 162391SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 172391SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 182391SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 192391SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 202391SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 212391SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 222391SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 232391SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 242391SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 252391SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 262391SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272665Ssaidi@eecs.umich.edu */ 282665Ssaidi@eecs.umich.edu 292914Ssaidi@eecs.umich.edu#ifndef __BASE_INET_HH__ 302391SN/A#define __BASE_INET_HH__ 312391SN/A 322391SN/A#include <iosfwd> 332391SN/A#include <string> 342391SN/A#include <utility> 352391SN/A#include <vector> 362391SN/A 372391SN/A#include "base/range.hh" 382391SN/A#include "dev/etherpkt.hh" 392391SN/A#include "sim/host.hh" 402391SN/A 412391SN/A#include "dnet/os.h" 423348Sbinkertn@umich.edu#include "dnet/eth.h" 432391SN/A#include "dnet/ip.h" 442391SN/A#include "dnet/ip6.h" 453879Ssaidi@eecs.umich.edu#include "dnet/addr.h" 462394SN/A#include "dnet/arp.h" 472391SN/A#include "dnet/icmp.h" 482415SN/A#include "dnet/tcp.h" 493348Sbinkertn@umich.edu#include "dnet/udp.h" 502394SN/A#include "dnet/intf.h" 512391SN/A#include "dnet/route.h" 522423SN/A#include "dnet/fw.h" 532391SN/A#include "dnet/blob.h" 543012Ssaidi@eecs.umich.edu#include "dnet/rand.h" 554467Sstever@eecs.umich.edu 562391SN/Anamespace Net { 573012Ssaidi@eecs.umich.edu 582391SN/A/* 592391SN/A * Ethernet Stuff 602391SN/A */ 614626Sstever@eecs.umich.edustruct EthAddr : protected eth_addr 624626Sstever@eecs.umich.edu{ 634626Sstever@eecs.umich.edu protected: 642391SN/A void parse(const std::string &addr); 653012Ssaidi@eecs.umich.edu 662391SN/A public: 672391SN/A EthAddr(); 682391SN/A EthAddr(const uint8_t ea[ETH_ADDR_LEN]); 692391SN/A EthAddr(const eth_addr &ea); 703751Sgblack@eecs.umich.edu EthAddr(const std::string &addr); 713751Sgblack@eecs.umich.edu const EthAddr &operator=(const eth_addr &ea); 723751Sgblack@eecs.umich.edu const EthAddr &operator=(const std::string &addr); 733751Sgblack@eecs.umich.edu 743012Ssaidi@eecs.umich.edu int size() const { return sizeof(eth_addr); } 752391SN/A 762391SN/A const uint8_t *bytes() const { return &data[0]; } 772541SN/A uint8_t *bytes() { return &data[0]; } 782541SN/A 792541SN/A const uint8_t *addr() const { return &data[0]; } 804470Sstever@eecs.umich.edu bool unicast() const { return data[0] == 0x00; } 814470Sstever@eecs.umich.edu bool multicast() const { return data[0] == 0x01; } 824470Sstever@eecs.umich.edu bool broadcast() const { return data[0] == 0xff; } 834470Sstever@eecs.umich.edu std::string string() const; 844467Sstever@eecs.umich.edu 854467Sstever@eecs.umich.edu operator uint64_t() const 864467Sstever@eecs.umich.edu { 874467Sstever@eecs.umich.edu uint64_t reg = 0; 882541SN/A reg |= ((uint64_t)data[0]) << 40; 892541SN/A reg |= ((uint64_t)data[1]) << 32; 902391SN/A reg |= ((uint64_t)data[2]) << 24; 912391SN/A reg |= ((uint64_t)data[3]) << 16; 923012Ssaidi@eecs.umich.edu reg |= ((uint64_t)data[4]) << 8; 933918Ssaidi@eecs.umich.edu reg |= ((uint64_t)data[5]) << 0; 942416SN/A return reg; 952391SN/A } 962391SN/A 972391SN/A}; 982391SN/A 992391SN/Astd::ostream &operator<<(std::ostream &stream, const EthAddr &ea); 1003012Ssaidi@eecs.umich.edubool operator==(const EthAddr &left, const EthAddr &right); 1014040Ssaidi@eecs.umich.edu 1022391SN/Astruct EthHdr : public eth_hdr 1033012Ssaidi@eecs.umich.edu{ 1042391SN/A uint16_t type() const { return ntohs(eth_type); } 1052391SN/A const EthAddr &src() const { return *(EthAddr *)ð_src; } 1062391SN/A const EthAddr &dst() const { return *(EthAddr *)ð_dst; } 1072408SN/A 1082408SN/A int size() const { return sizeof(eth_hdr); } 1092408SN/A 1102409SN/A const uint8_t *bytes() const { return (const uint8_t *)this; } 1112409SN/A const uint8_t *payload() const { return bytes() + size(); } 1122408SN/A uint8_t *bytes() { return (uint8_t *)this; } 1132408SN/A uint8_t *payload() { return bytes() + size(); } 1143012Ssaidi@eecs.umich.edu}; 1153349Sbinkertn@umich.edu 1163012Ssaidi@eecs.umich.educlass EthPtr 1173012Ssaidi@eecs.umich.edu{ 1183012Ssaidi@eecs.umich.edu protected: 1192413SN/A friend class IpPtr; 1203170Sstever@eecs.umich.edu PacketPtr p; 1213170Sstever@eecs.umich.edu 1223170Sstever@eecs.umich.edu public: 1233170Sstever@eecs.umich.edu EthPtr() {} 1243170Sstever@eecs.umich.edu EthPtr(const PacketPtr &ptr) : p(ptr) { } 1254626Sstever@eecs.umich.edu 1263170Sstever@eecs.umich.edu EthHdr *operator->() { return (EthHdr *)p->data; } 1274626Sstever@eecs.umich.edu EthHdr &operator*() { return *(EthHdr *)p->data; } 1283170Sstever@eecs.umich.edu operator EthHdr *() { return (EthHdr *)p->data; } 1293170Sstever@eecs.umich.edu 1303170Sstever@eecs.umich.edu const EthHdr *operator->() const { return (const EthHdr *)p->data; } 1313170Sstever@eecs.umich.edu const EthHdr &operator*() const { return *(const EthHdr *)p->data; } 1323170Sstever@eecs.umich.edu operator const EthHdr *() const { return (const EthHdr *)p->data; } 1333170Sstever@eecs.umich.edu 1343170Sstever@eecs.umich.edu const EthPtr &operator=(const PacketPtr &ptr) { p = ptr; return *this; } 1353170Sstever@eecs.umich.edu 1363170Sstever@eecs.umich.edu const PacketPtr packet() const { return p; } 1373170Sstever@eecs.umich.edu PacketPtr packet() { return p; } 1383170Sstever@eecs.umich.edu bool operator!() const { return !p; } 1393170Sstever@eecs.umich.edu operator bool() const { return p; } 1403170Sstever@eecs.umich.edu}; 1413170Sstever@eecs.umich.edu 1423170Sstever@eecs.umich.edu/* 1433170Sstever@eecs.umich.edu * IP Stuff 1443170Sstever@eecs.umich.edu */ 1453170Sstever@eecs.umich.edustruct IpOpt; 1463170Sstever@eecs.umich.edustruct IpHdr : public ip_hdr 1473170Sstever@eecs.umich.edu{ 1483170Sstever@eecs.umich.edu uint8_t version() const { return ip_v; } 1493170Sstever@eecs.umich.edu uint8_t hlen() const { return ip_hl * 4; } 1503170Sstever@eecs.umich.edu uint8_t tos() const { return ip_tos; } 1513170Sstever@eecs.umich.edu uint16_t len() const { return ntohs(ip_len); } 1523170Sstever@eecs.umich.edu uint16_t id() const { return ntohs(ip_id); } 1533170Sstever@eecs.umich.edu uint16_t frag_flags() const { return ntohs(ip_off) >> 13; } 1543170Sstever@eecs.umich.edu uint16_t frag_off() const { return ntohs(ip_off) & 0x1fff; } 1553170Sstever@eecs.umich.edu uint8_t ttl() const { return ip_ttl; } 1564626Sstever@eecs.umich.edu uint8_t proto() const { return ip_p; } 1573170Sstever@eecs.umich.edu uint16_t sum() const { return ip_sum; } 1584626Sstever@eecs.umich.edu uint32_t src() const { return ntohl(ip_src); } 1593170Sstever@eecs.umich.edu uint32_t dst() const { return ntohl(ip_dst); } 1604626Sstever@eecs.umich.edu 1613170Sstever@eecs.umich.edu void sum(uint16_t sum) { ip_sum = sum; } 1623170Sstever@eecs.umich.edu 1633170Sstever@eecs.umich.edu bool options(std::vector<const IpOpt *> &vec) const; 1643170Sstever@eecs.umich.edu 1653170Sstever@eecs.umich.edu int size() const { return hlen(); } 1663170Sstever@eecs.umich.edu const uint8_t *bytes() const { return (const uint8_t *)this; } 1673170Sstever@eecs.umich.edu const uint8_t *payload() const { return bytes() + size(); } 1683170Sstever@eecs.umich.edu uint8_t *bytes() { return (uint8_t *)this; } 1693170Sstever@eecs.umich.edu uint8_t *payload() { return bytes() + size(); } 1703170Sstever@eecs.umich.edu}; 1713170Sstever@eecs.umich.edu 1723170Sstever@eecs.umich.educlass IpPtr 1733170Sstever@eecs.umich.edu{ 1743170Sstever@eecs.umich.edu protected: 1753170Sstever@eecs.umich.edu friend class TcpPtr; 1763170Sstever@eecs.umich.edu friend class UdpPtr; 1773170Sstever@eecs.umich.edu PacketPtr p; 1783170Sstever@eecs.umich.edu 1793170Sstever@eecs.umich.edu const IpHdr *h() const 1803170Sstever@eecs.umich.edu { return (const IpHdr *)(p->data + sizeof(eth_hdr)); } 1813170Sstever@eecs.umich.edu IpHdr *h() { return (IpHdr *)(p->data + sizeof(eth_hdr)); } 1823170Sstever@eecs.umich.edu 1833170Sstever@eecs.umich.edu void set(const PacketPtr &ptr) 1843170Sstever@eecs.umich.edu { 1853170Sstever@eecs.umich.edu EthHdr *eth = (EthHdr *)ptr->data; 1863170Sstever@eecs.umich.edu if (eth->type() == ETH_TYPE_IP) 1873170Sstever@eecs.umich.edu p = ptr; 1883170Sstever@eecs.umich.edu else 1893170Sstever@eecs.umich.edu p = 0; 1903170Sstever@eecs.umich.edu } 1913170Sstever@eecs.umich.edu 1923170Sstever@eecs.umich.edu public: 1933170Sstever@eecs.umich.edu IpPtr() {} 1943170Sstever@eecs.umich.edu IpPtr(const PacketPtr &ptr) { set(ptr); } 1953170Sstever@eecs.umich.edu IpPtr(const EthPtr &ptr) { set(ptr.p); } 1963170Sstever@eecs.umich.edu IpPtr(const IpPtr &ptr) : p(ptr.p) { } 1973170Sstever@eecs.umich.edu 1984040Ssaidi@eecs.umich.edu IpHdr *operator->() { return h(); } 1993170Sstever@eecs.umich.edu IpHdr &operator*() { return *h(); } 2003170Sstever@eecs.umich.edu operator IpHdr *() { return h(); } 2013170Sstever@eecs.umich.edu 2023170Sstever@eecs.umich.edu const IpHdr *operator->() const { return h(); } 2033170Sstever@eecs.umich.edu const IpHdr &operator*() const { return *h(); } 2044626Sstever@eecs.umich.edu operator const IpHdr *() const { return h(); } 2054626Sstever@eecs.umich.edu 2064626Sstever@eecs.umich.edu const IpPtr &operator=(const PacketPtr &ptr) { set(ptr); return *this; } 2074626Sstever@eecs.umich.edu const IpPtr &operator=(const EthPtr &ptr) { set(ptr.p); return *this; } 2084626Sstever@eecs.umich.edu const IpPtr &operator=(const IpPtr &ptr) { p = ptr.p; return *this; } 2094626Sstever@eecs.umich.edu 2104626Sstever@eecs.umich.edu const PacketPtr packet() const { return p; } 2114626Sstever@eecs.umich.edu PacketPtr packet() { return p; } 2124626Sstever@eecs.umich.edu bool operator!() const { return !p; } 2134626Sstever@eecs.umich.edu operator bool() const { return p; } 2144626Sstever@eecs.umich.edu operator bool() { return p; } 2154626Sstever@eecs.umich.edu}; 2164626Sstever@eecs.umich.edu 2174626Sstever@eecs.umich.eduuint16_t cksum(const IpPtr &ptr); 2184626Sstever@eecs.umich.edu 2194626Sstever@eecs.umich.edustruct IpOpt : public ip_opt 2204626Sstever@eecs.umich.edu{ 2214626Sstever@eecs.umich.edu uint8_t type() const { return opt_type; } 2224626Sstever@eecs.umich.edu uint8_t typeNumber() const { return IP_OPT_NUMBER(opt_type); } 2234626Sstever@eecs.umich.edu uint8_t typeClass() const { return IP_OPT_CLASS(opt_type); } 2244626Sstever@eecs.umich.edu uint8_t typeCopied() const { return IP_OPT_COPIED(opt_type); } 2254626Sstever@eecs.umich.edu uint8_t len() const { return IP_OPT_TYPEONLY(type()) ? 1 : opt_len; } 2264626Sstever@eecs.umich.edu 2274626Sstever@eecs.umich.edu bool isNumber(int num) const { return typeNumber() == IP_OPT_NUMBER(num); } 2284626Sstever@eecs.umich.edu bool isClass(int cls) const { return typeClass() == IP_OPT_CLASS(cls); } 2294626Sstever@eecs.umich.edu bool isCopied(int cpy) const { return typeCopied() == IP_OPT_COPIED(cpy); } 2304626Sstever@eecs.umich.edu 2314626Sstever@eecs.umich.edu const uint8_t *data() const { return opt_data.data8; } 2324626Sstever@eecs.umich.edu void sec(ip_opt_data_sec &sec) const; 2334626Sstever@eecs.umich.edu void lsrr(ip_opt_data_rr &rr) const; 2344626Sstever@eecs.umich.edu void ssrr(ip_opt_data_rr &rr) const; 2352413SN/A void ts(ip_opt_data_ts &ts) const; 2364040Ssaidi@eecs.umich.edu uint16_t satid() const { return ntohs(opt_data.satid); } 2374040Ssaidi@eecs.umich.edu uint16_t mtup() const { return ntohs(opt_data.mtu); } 2382414SN/A uint16_t mtur() const { return ntohs(opt_data.mtu); } 2394626Sstever@eecs.umich.edu void tr(ip_opt_data_tr &tr) const; 2404626Sstever@eecs.umich.edu const uint32_t *addext() const { return &opt_data.addext[0]; } 2414626Sstever@eecs.umich.edu uint16_t rtralt() const { return ntohs(opt_data.rtralt); } 2424626Sstever@eecs.umich.edu void sdb(std::vector<uint32_t> &vec) const; 2433175Srdreslin@umich.edu}; 2444626Sstever@eecs.umich.edu 2454626Sstever@eecs.umich.edu/* 2464626Sstever@eecs.umich.edu * TCP Stuff 2474626Sstever@eecs.umich.edu */ 2484040Ssaidi@eecs.umich.edustruct TcpOpt; 2494040Ssaidi@eecs.umich.edustruct TcpHdr : public tcp_hdr 2504040Ssaidi@eecs.umich.edu{ 2514040Ssaidi@eecs.umich.edu uint16_t sport() const { return ntohs(th_sport); } 2524040Ssaidi@eecs.umich.edu uint16_t dport() const { return ntohs(th_dport); } 2534040Ssaidi@eecs.umich.edu uint32_t seq() const { return ntohl(th_seq); } 2544040Ssaidi@eecs.umich.edu uint32_t ack() const { return ntohl(th_ack); } 2554040Ssaidi@eecs.umich.edu uint8_t off() const { return th_off; } 2564040Ssaidi@eecs.umich.edu uint8_t flags() const { return th_flags & 0x3f; } 2574040Ssaidi@eecs.umich.edu uint16_t win() const { return ntohs(th_win); } 2584052Ssaidi@eecs.umich.edu uint16_t sum() const { return th_sum; } 2594626Sstever@eecs.umich.edu uint16_t urp() const { return ntohs(th_urp); } 2604040Ssaidi@eecs.umich.edu 2614040Ssaidi@eecs.umich.edu void sum(uint16_t sum) { th_sum = sum; } 2624040Ssaidi@eecs.umich.edu 2634052Ssaidi@eecs.umich.edu bool options(std::vector<const TcpOpt *> &vec) const; 2644626Sstever@eecs.umich.edu 2654626Sstever@eecs.umich.edu int size() const { return off(); } 2664040Ssaidi@eecs.umich.edu const uint8_t *bytes() const { return (const uint8_t *)this; } 2674052Ssaidi@eecs.umich.edu const uint8_t *payload() const { return bytes() + size(); } 2684626Sstever@eecs.umich.edu uint8_t *bytes() { return (uint8_t *)this; } 2694626Sstever@eecs.umich.edu uint8_t *payload() { return bytes() + size(); } 2704040Ssaidi@eecs.umich.edu}; 2714040Ssaidi@eecs.umich.edu 2724040Ssaidi@eecs.umich.educlass TcpPtr 2734040Ssaidi@eecs.umich.edu{ 2744040Ssaidi@eecs.umich.edu protected: 2754626Sstever@eecs.umich.edu PacketPtr p; 2764040Ssaidi@eecs.umich.edu int off; 2774626Sstever@eecs.umich.edu 2784626Sstever@eecs.umich.edu const TcpHdr *h() const { return (const TcpHdr *)(p->data + off); } 2794626Sstever@eecs.umich.edu TcpHdr *h() { return (TcpHdr *)(p->data + off); } 2804626Sstever@eecs.umich.edu 2814626Sstever@eecs.umich.edu void set(const PacketPtr &ptr, int offset) { p = ptr; off = offset; } 2824040Ssaidi@eecs.umich.edu void set(const IpPtr &ptr) 2834626Sstever@eecs.umich.edu { 2844626Sstever@eecs.umich.edu if (ptr->proto() == IP_PROTO_TCP) 2854626Sstever@eecs.umich.edu set(ptr.p, sizeof(eth_hdr) + ptr->hlen()); 2864626Sstever@eecs.umich.edu else 2874626Sstever@eecs.umich.edu set(0, 0); 2884626Sstever@eecs.umich.edu } 2894626Sstever@eecs.umich.edu 2904626Sstever@eecs.umich.edu public: 2914626Sstever@eecs.umich.edu TcpPtr() {} 2924626Sstever@eecs.umich.edu TcpPtr(const IpPtr &ptr) { set(ptr); } 2934626Sstever@eecs.umich.edu TcpPtr(const TcpPtr &ptr) : p(ptr.p), off(ptr.off) {} 2944626Sstever@eecs.umich.edu 2954040Ssaidi@eecs.umich.edu TcpHdr *operator->() { return h(); } 2962413SN/A TcpHdr &operator*() { return *h(); } 2972413SN/A operator TcpHdr *() { return h(); } 2982420SN/A 2994626Sstever@eecs.umich.edu const TcpHdr *operator->() const { return h(); } 3004626Sstever@eecs.umich.edu const TcpHdr &operator*() const { return *h(); } 3014626Sstever@eecs.umich.edu operator const TcpHdr *() const { return h(); } 3024626Sstever@eecs.umich.edu 3034626Sstever@eecs.umich.edu const TcpPtr &operator=(const IpPtr &i) { set(i); return *this; } 3044626Sstever@eecs.umich.edu const TcpPtr &operator=(const TcpPtr &t) { set(t.p, t.off); return *this; } 3054626Sstever@eecs.umich.edu 3064626Sstever@eecs.umich.edu const PacketPtr packet() const { return p; } 3074626Sstever@eecs.umich.edu PacketPtr packet() { return p; } 3084626Sstever@eecs.umich.edu bool operator!() const { return !p; } 3094626Sstever@eecs.umich.edu operator bool() const { return p; } 3104626Sstever@eecs.umich.edu operator bool() { return p; } 3114626Sstever@eecs.umich.edu}; 3124626Sstever@eecs.umich.edu 3134626Sstever@eecs.umich.eduuint16_t cksum(const TcpPtr &ptr); 3144626Sstever@eecs.umich.edu 3154626Sstever@eecs.umich.edutypedef Range<uint16_t> SackRange; 3164626Sstever@eecs.umich.edu 3174626Sstever@eecs.umich.edustruct TcpOpt : public tcp_opt 3184626Sstever@eecs.umich.edu{ 3194626Sstever@eecs.umich.edu uint8_t type() const { return opt_type; } 3204626Sstever@eecs.umich.edu uint8_t len() const { return TCP_OPT_TYPEONLY(type()) ? 1 : opt_len; } 3214626Sstever@eecs.umich.edu 3224626Sstever@eecs.umich.edu bool isopt(int opt) const { return type() == opt; } 3234626Sstever@eecs.umich.edu 3244626Sstever@eecs.umich.edu const uint8_t *data() const { return opt_data.data8; } 3252641Sstever@eecs.umich.edu 3262413SN/A uint16_t mss() const { return ntohs(opt_data.mss); } 3272413SN/A uint8_t wscale() const { return opt_data.wscale; } 3284626Sstever@eecs.umich.edu bool sack(std::vector<SackRange> &vec) const; 3292413SN/A uint32_t echo() const { return ntohl(opt_data.echo); } 3302738Sstever@eecs.umich.edu uint32_t tsval() const { return ntohl(opt_data.timestamp[0]); } 3312413SN/A uint32_t tsecr() const { return ntohl(opt_data.timestamp[1]); } 3324468Sstever@eecs.umich.edu uint32_t cc() const { return ntohl(opt_data.cc); } 3334468Sstever@eecs.umich.edu uint8_t cksum() const{ return opt_data.cksum; } 3344468Sstever@eecs.umich.edu const uint8_t *md5() const { return opt_data.md5; } 3354468Sstever@eecs.umich.edu 3364468Sstever@eecs.umich.edu int size() const { return len(); } 3374468Sstever@eecs.umich.edu const uint8_t *bytes() const { return (const uint8_t *)this; } 3384468Sstever@eecs.umich.edu const uint8_t *payload() const { return bytes() + size(); } 3394467Sstever@eecs.umich.edu uint8_t *bytes() { return (uint8_t *)this; } 3402462SN/A uint8_t *payload() { return bytes() + size(); } 3412462SN/A}; 3424467Sstever@eecs.umich.edu 3434467Sstever@eecs.umich.edu/* 3444467Sstever@eecs.umich.edu * UDP Stuff 3454467Sstever@eecs.umich.edu */ 3464467Sstever@eecs.umich.edustruct UdpHdr : public udp_hdr 3474467Sstever@eecs.umich.edu{ 3484467Sstever@eecs.umich.edu uint16_t sport() const { return ntohs(uh_sport); } 3494467Sstever@eecs.umich.edu uint16_t dport() const { return ntohs(uh_dport); } 3504467Sstever@eecs.umich.edu uint16_t len() const { return ntohs(uh_ulen); } 3514467Sstever@eecs.umich.edu uint16_t sum() const { return uh_sum; } 3524467Sstever@eecs.umich.edu 3534467Sstever@eecs.umich.edu void sum(uint16_t sum) { uh_sum = sum; } 3544467Sstever@eecs.umich.edu 3554467Sstever@eecs.umich.edu int size() const { return sizeof(udp_hdr); } 3562413SN/A const uint8_t *bytes() const { return (const uint8_t *)this; } 3572413SN/A const uint8_t *payload() const { return bytes() + size(); } 3584467Sstever@eecs.umich.edu uint8_t *bytes() { return (uint8_t *)this; } 3592413SN/A uint8_t *payload() { return bytes() + size(); } 3602413SN/A}; 3612413SN/A 3622413SN/Aclass UdpPtr 3632413SN/A{ 3642640Sstever@eecs.umich.edu protected: 3652640Sstever@eecs.umich.edu PacketPtr p; 3662914Ssaidi@eecs.umich.edu int off; 3672413SN/A 3682413SN/A const UdpHdr *h() const { return (const UdpHdr *)(p->data + off); } 3692413SN/A UdpHdr *h() { return (UdpHdr *)(p->data + off); } 3702413SN/A 3712413SN/A void set(const PacketPtr &ptr, int offset) { p = ptr; off = offset; } 3722413SN/A void set(const IpPtr &ptr) 3732413SN/A { 3742413SN/A if (ptr->proto() == IP_PROTO_UDP) 3752413SN/A set(ptr.p, sizeof(eth_hdr) + ptr->hlen()); 3762522SN/A else 3774475Sstever@eecs.umich.edu set(0, 0); 3782413SN/A } 3792522SN/A 3802497SN/A public: 3812497SN/A UdpPtr() {} 3822497SN/A UdpPtr(const IpPtr &ptr) { set(ptr); } 3834475Sstever@eecs.umich.edu UdpPtr(const UdpPtr &ptr) : p(ptr.p), off(ptr.off) {} 3842497SN/A 3854475Sstever@eecs.umich.edu UdpHdr *operator->() { return h(); } 3862522SN/A UdpHdr &operator*() { return *h(); } 3874475Sstever@eecs.umich.edu operator UdpHdr *() { return h(); } 3882413SN/A 3892413SN/A const UdpHdr *operator->() const { return h(); } 3902415SN/A const UdpHdr &operator*() const { return *h(); } 3912415SN/A operator const UdpHdr *() const { return h(); } 3922415SN/A 3932415SN/A const UdpPtr &operator=(const IpPtr &i) { set(i); return *this; } 3942415SN/A const UdpPtr &operator=(const UdpPtr &t) { set(t.p, t.off); return *this; } 3952413SN/A 3962413SN/A const PacketPtr packet() const { return p; } 3973349Sbinkertn@umich.edu PacketPtr packet() { return p; } 3982413SN/A bool operator!() const { return !p; } 3994626Sstever@eecs.umich.edu operator bool() const { return p; } 4002413SN/A operator bool() { return p; } 4012413SN/A}; 4022413SN/A 4033349Sbinkertn@umich.eduuint16_t cksum(const UdpPtr &ptr); 4042413SN/A 4054490Sstever@eecs.umich.edu/* namespace Net */ } 4063612Srdreslin@umich.edu 4073091Sstever@eecs.umich.edu#endif // __BASE_INET_HH__ 4083091Sstever@eecs.umich.edu