⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ipsumdump_ip.cc

📁 COPE the first practical network coding scheme which is developped on click
💻 CC
📖 第 1 页 / 共 2 页
字号:
// -*- mode: c++; c-basic-offset: 4 -*-/* * ipsumdump_general.{cc,hh} -- general IP summary dump unparsers * Eddie Kohler * * Copyright (c) 2002 International Computer Science Institute * Copyright (c) 2004 Regents of the University of California * * Permission is hereby granted, free of charge, to any person obtaining a * copy of this software and associated documentation files (the "Software"), * to deal in the Software without restriction, subject to the conditions * listed in the Click LICENSE file. These conditions include: you must * preserve this copyright notice, and you cannot mention the copyright * holders in advertising related to the Software without their permission. * The Software is provided WITHOUT ANY WARRANTY, EXPRESS OR IMPLIED. This * notice is a summary of the Click LICENSE file; the license in that file is * legally binding. */#include <click/config.h>#include "ipsumdumpinfo.hh"#include <click/packet.hh>#include <click/packet_anno.hh>#include <clicknet/ip.h>#include <clicknet/tcp.h>#include <clicknet/udp.h>#include <click/confparse.hh>CLICK_DECLSenum { T_IP_SRC, T_IP_DST, T_IP_TOS, T_IP_TTL, T_IP_FRAG, T_IP_FRAGOFF,       T_IP_ID, T_IP_SUM, T_IP_PROTO, T_IP_OPT, T_IP_LEN, T_IP_CAPTURE_LEN,       T_SPORT, T_DPORT, T_PAYLOAD_LEN, T_PAYLOAD };namespace IPSummaryDump {void ip_prepare(PacketDesc& d){    Packet* p = d.p;    d.iph = p->ip_header();    d.tcph = p->tcp_header();    d.udph = p->udp_header();    #define BAD(msg, hdr) do { if (d.bad_sa && !*d.bad_sa) *d.bad_sa << "!bad " << msg << '\n'; hdr = 0; } while (0)#define BAD2(msg, val, hdr) do { if (d.bad_sa && !*d.bad_sa) *d.bad_sa << "!bad " << msg << val << '\n'; hdr = 0; } while (0)    // check IP header    if (!d.iph)	/* nada */;    else if (p->network_length() < (int) offsetof(click_ip, ip_id))	BAD("truncated IP header", d.iph);    else if (d.iph->ip_v != 4)	BAD2("IP version ", d.iph->ip_v, d.iph);    else if (d.iph->ip_hl < (sizeof(click_ip) >> 2))	BAD2("IP header length ", d.iph->ip_hl, d.iph);    else if (ntohs(d.iph->ip_len) < (d.iph->ip_hl << 2))	BAD2("IP length ", ntohs(d.iph->ip_len), d.iph);    else {	// truncate packet length to IP length if necessary	int ip_len = ntohs(d.iph->ip_len);	if (p->network_length() > ip_len) {	    SET_EXTRA_LENGTH_ANNO(p, EXTRA_LENGTH_ANNO(p) + p->network_length() - ip_len);	    p->take(p->network_length() - ip_len);	} else if (d.careful_trunc && p->network_length() + EXTRA_LENGTH_ANNO(p) < (uint32_t) ip_len) {	    /* This doesn't actually kill the IP header. */ 	    int scratch;	    BAD2("truncated IP missing ", (ntohs(d.iph->ip_len) - p->network_length() - EXTRA_LENGTH_ANNO(p)), scratch);	}    }    // check TCP header    if (!d.iph || !d.tcph	|| p->network_length() <= (int)(d.iph->ip_hl << 2)	|| d.iph->ip_p != IP_PROTO_TCP	|| !IP_FIRSTFRAG(d.iph))	d.tcph = 0;    else if (p->transport_length() > 12	     && d.tcph->th_off < (sizeof(click_tcp) >> 2))	BAD2("TCP header length ", d.tcph->th_off, d.tcph);    // check UDP header    if (!d.iph || !d.udph	|| p->network_length() <= (int)(d.iph->ip_hl << 2)	|| d.iph->ip_p != IP_PROTO_UDP	|| !IP_FIRSTFRAG(d.iph))	d.udph = 0;#undef BAD#undef BAD2    // Adjust extra length, since we calculate lengths here based on ip_len.    if (d.iph && EXTRA_LENGTH_ANNO(p) > 0) {	int32_t full_len = p->length() + EXTRA_LENGTH_ANNO(p);	if (ntohs(d.iph->ip_len) + 8 >= full_len - p->network_header_offset())	    SET_EXTRA_LENGTH_ANNO(p, 0);	else {	    full_len = full_len - ntohs(d.iph->ip_len);	    SET_EXTRA_LENGTH_ANNO(p, full_len);	}    }}static bool ip_extract(PacketDesc& d, int thunk){    int network_length = d.p->network_length();    switch (thunk & ~B_TYPEMASK) {	// IP header properties#define CHECK(l) do { if (!d.iph || network_length < (l)) return field_missing(d, MISSING_IP, "IP", (l)); } while (0)	      case T_IP_SRC:	CHECK(16);	d.v = d.iph->ip_src.s_addr;	return true;      case T_IP_DST:	CHECK(20);	d.v = d.iph->ip_dst.s_addr;	return true;      case T_IP_TOS:	CHECK(2);	d.v = d.iph->ip_tos;	return true;      case T_IP_TTL:	CHECK(9);	d.v = d.iph->ip_ttl;	return true;      case T_IP_FRAG:	CHECK(8);	d.v = (IP_ISFRAG(d.iph) ? (IP_FIRSTFRAG(d.iph) ? 'F' : 'f') : '.');	return true;      case T_IP_FRAGOFF:	CHECK(8);	d.v = ntohs(d.iph->ip_off);	return true;      case T_IP_ID:	CHECK(6);	d.v = ntohs(d.iph->ip_id);	return true;      case T_IP_SUM:	CHECK(12);	d.v = ntohs(d.iph->ip_sum);	return true;      case T_IP_PROTO:	CHECK(10);	d.v = d.iph->ip_p;	return true;      case T_IP_OPT:	if (!d.iph || (d.iph->ip_hl > 5 && network_length < (int)(d.iph->ip_hl << 2)))	    return field_missing(d, MISSING_IP, "IP", (d.iph ? d.iph->ip_hl << 2 : 20));	if (d.iph->ip_hl <= 5)	    d.vptr = 0, d.v2 = 0;	else {	    d.vptr = (const uint8_t *) (d.iph + 1);	    d.v2 = (d.iph->ip_hl << 2) - sizeof(click_ip);	}	return true;      case T_IP_LEN:	if (d.iph)	    d.v = ntohs(d.iph->ip_len) + (d.force_extra_length ? EXTRA_LENGTH_ANNO(d.p) : 0);	else	    d.v = d.p->length() + EXTRA_LENGTH_ANNO(d.p);	return true;      case T_IP_CAPTURE_LEN: {	  uint32_t allow_len = (d.iph ? network_length : d.p->length());	  uint32_t len = (d.iph ? ntohs(d.iph->ip_len) : allow_len);	  d.v = (len < allow_len ? len : allow_len);	  return true;      }#undef CHECK      default:	return false;    }}static void ip_outa(const PacketDesc& d, int thunk){    switch (thunk & ~B_TYPEMASK) {      case T_IP_SRC:      case T_IP_DST:	*d.sa << IPAddress(d.v);	break;      case T_IP_FRAG:	*d.sa << (char) d.v;	break;      case T_IP_FRAGOFF:	*d.sa << ((d.v & IP_OFFMASK) << 3);	if (d.v & IP_MF)	    *d.sa << '+';	break;      case T_IP_PROTO:	switch (d.v) {	  case IP_PROTO_TCP:	*d.sa << 'T'; break;	  case IP_PROTO_UDP:	*d.sa << 'U'; break;	  case IP_PROTO_ICMP:	*d.sa << 'I'; break;	  default:		*d.sa << d.v; break;	}	break;      case T_IP_OPT:	if (!d.vptr)	    *d.sa << '.';	else	    unparse_ip_opt(*d.sa, d.vptr, d.v2, DO_IPOPT_ALL_NOPAD);	break;    }}static void ip_outb(const PacketDesc& d, bool ok, int thunk){    if ((thunk & ~B_TYPEMASK) == T_IP_OPT) {	if (!ok || !d.vptr)	    *d.sa << '\0';	else	    unparse_ip_opt_binary(*d.sa, d.vptr, d.v2, DO_IPOPT_ALL);    }}static const uint8_t* ip_inb(PacketDesc& d, const uint8_t *s, const uint8_t *ends, int thunk){    if ((thunk & ~B_TYPEMASK) == T_IP_OPT && s + s[0] + 1 <= ends) {	d.vptr = s + 1;	d.v2 = s[0];	return s + s[0] + 1;    } else	return ends;}static bool transport_extract(PacketDesc& d, int thunk){    Packet* p = d.p;    switch (thunk & ~B_TYPEMASK) {		// TCP/UDP header properties#define CHECK(l) do { if ((!d.tcph && !d.udph) || p->transport_length() < (l)) return field_missing(d, MISSING_IP_TRANSPORT, "transport", (l)); } while (0)      case T_SPORT:	CHECK(2);	d.v = ntohs(p->udp_header()->uh_sport);	return true;      case T_DPORT:	CHECK(4);	d.v = ntohs(p->udp_header()->uh_dport);	return true;#undef CHECK      case T_PAYLOAD_LEN:	if (d.iph) {	    int32_t off = p->network_header_length();	    if (d.tcph && p->transport_length() >= 13)		off += (d.tcph->th_off << 2);	    else if (d.udph)		off += sizeof(click_udp);	    else if (IP_FIRSTFRAG(d.iph) && (d.iph->ip_p == IP_PROTO_TCP || d.iph->ip_p == IP_PROTO_UDP))		off = ntohs(d.iph->ip_len);	    d.v = ntohs(d.iph->ip_len) - off + (d.force_extra_length ? EXTRA_LENGTH_ANNO(p) : 0);	} else	    d.v = p->length() + EXTRA_LENGTH_ANNO(p);	return true;      case T_PAYLOAD:	return true;      default:	return false;    }}static void transport_outa(const PacketDesc& d, int thunk){    switch (thunk & ~B_TYPEMASK) {      case T_PAYLOAD: {	  int32_t off;	  uint32_t len;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -