|
|
| 444 |
} |
444 |
} |
| 445 |
|
445 |
|
| 446 |
ofpbuf * |
446 |
ofpbuf * |
| 447 |
OpenFlowSwitchNetDevice::BufferFromPacket (Ptr<Packet> packet, Address src, Address dst, int mtu, uint16_t protocol) |
447 |
OpenFlowSwitchNetDevice::BufferFromPacket (Ptr<const Packet> constPacket, Address src, Address dst, int mtu, uint16_t protocol) |
| 448 |
{ |
448 |
{ |
| 449 |
NS_LOG_INFO ("Creating Openflow buffer from packet."); |
449 |
NS_LOG_INFO ("Creating Openflow buffer from packet."); |
| 450 |
|
450 |
|
|
|
451 |
Ptr<Packet> packet = constPacket->Copy (); |
| 451 |
/* |
452 |
/* |
| 452 |
* Allocate buffer with some headroom to add headers in forwarding |
453 |
* Allocate buffer with some headroom to add headers in forwarding |
| 453 |
* to the controller or adding a vlan tag, plus an extra 2 bytes to |
454 |
* to the controller or adding a vlan tag, plus an extra 2 bytes to |
|
|
| 458 |
ofpbuf *buffer = ofpbuf_new (headroom + hard_header + mtu); |
459 |
ofpbuf *buffer = ofpbuf_new (headroom + hard_header + mtu); |
| 459 |
buffer->data = (char*)buffer->data + headroom + hard_header; |
460 |
buffer->data = (char*)buffer->data + headroom + hard_header; |
| 460 |
|
461 |
|
| 461 |
int l2_length = 0, l3_length = 0, l4_length = 0; |
462 |
int l3_length = 0, l4_length = 0; |
| 462 |
|
|
|
| 463 |
// Load headers |
| 464 |
EthernetHeader eth_hd; |
| 465 |
if (packet->PeekHeader (eth_hd)) |
| 466 |
{ |
| 467 |
buffer->l2 = new eth_header; |
| 468 |
eth_header* eth_h = (eth_header*)buffer->l2; |
| 469 |
dst.CopyTo (eth_h->eth_dst); // Destination Mac Address |
| 470 |
src.CopyTo (eth_h->eth_src); // Source Mac Address |
| 471 |
eth_h->eth_type = htons (ETH_TYPE_IP); // Ether Type |
| 472 |
NS_LOG_INFO ("Parsed EthernetHeader"); |
| 473 |
|
| 474 |
l2_length = ETH_HEADER_LEN; |
| 475 |
} |
| 476 |
|
463 |
|
| 477 |
// We have to wrap this because PeekHeader has an assert fail if we check for an Ipv4Header that isn't there. |
464 |
// We have to wrap this because PeekHeader has an assert fail if we check for an Ipv4Header that isn't there. |
| 478 |
if (protocol == Ipv4L3Protocol::PROT_NUMBER) |
465 |
if (protocol == Ipv4L3Protocol::PROT_NUMBER) |
|
|
| 493 |
ip_h->ip_dst = htonl (ip_hd.GetDestination ().Get ()); // Destination Address |
480 |
ip_h->ip_dst = htonl (ip_hd.GetDestination ().Get ()); // Destination Address |
| 494 |
ip_h->ip_csum = csum (&ip_h, sizeof ip_h); // Header Checksum |
481 |
ip_h->ip_csum = csum (&ip_h, sizeof ip_h); // Header Checksum |
| 495 |
NS_LOG_INFO ("Parsed Ipv4Header"); |
482 |
NS_LOG_INFO ("Parsed Ipv4Header"); |
|
|
483 |
packet->RemoveHeader (ip_hd); |
| 496 |
|
484 |
|
| 497 |
l3_length = IP_HEADER_LEN; |
485 |
l3_length = IP_HEADER_LEN; |
| 498 |
} |
486 |
} |
|
|
| 515 |
arp_h->ar_hln = sizeof arp_h->ar_tha; // Hardware address length. |
503 |
arp_h->ar_hln = sizeof arp_h->ar_tha; // Hardware address length. |
| 516 |
arp_h->ar_pln = sizeof arp_h->ar_tpa; // Protocol address length. |
504 |
arp_h->ar_pln = sizeof arp_h->ar_tpa; // Protocol address length. |
| 517 |
NS_LOG_INFO ("Parsed ArpHeader"); |
505 |
NS_LOG_INFO ("Parsed ArpHeader"); |
|
|
506 |
packet->RemoveHeader (arp_hd); |
| 518 |
|
507 |
|
| 519 |
l3_length = ARP_ETH_HEADER_LEN; |
508 |
l3_length = ARP_ETH_HEADER_LEN; |
| 520 |
} |
509 |
} |
|
|
| 539 |
tcp_h->tcp_urg = tcp_hd.GetUrgentPointer (); // Urgent Pointer |
528 |
tcp_h->tcp_urg = tcp_hd.GetUrgentPointer (); // Urgent Pointer |
| 540 |
tcp_h->tcp_csum = csum (&tcp_h, sizeof tcp_h); // Header Checksum |
529 |
tcp_h->tcp_csum = csum (&tcp_h, sizeof tcp_h); // Header Checksum |
| 541 |
NS_LOG_INFO ("Parsed TcpHeader"); |
530 |
NS_LOG_INFO ("Parsed TcpHeader"); |
|
|
531 |
packet->RemoveHeader (tcp_hd); |
| 542 |
|
532 |
|
| 543 |
l4_length = TCP_HEADER_LEN; |
533 |
l4_length = TCP_HEADER_LEN; |
| 544 |
} |
534 |
} |
|
|
| 562 |
udp_csum = csum_continue (udp_csum, udp_h, sizeof udp_h); |
552 |
udp_csum = csum_continue (udp_csum, udp_h, sizeof udp_h); |
| 563 |
udp_h->udp_csum = csum_finish (csum_continue (udp_csum, buffer->data, buffer->size)); // Header Checksum |
553 |
udp_h->udp_csum = csum_finish (csum_continue (udp_csum, buffer->data, buffer->size)); // Header Checksum |
| 564 |
NS_LOG_INFO ("Parsed UdpHeader"); |
554 |
NS_LOG_INFO ("Parsed UdpHeader"); |
|
|
555 |
packet->RemoveHeader (udp_hd); |
| 565 |
|
556 |
|
| 566 |
l4_length = UDP_HEADER_LEN; |
557 |
l4_length = UDP_HEADER_LEN; |
| 567 |
} |
558 |
} |
| 568 |
} |
559 |
} |
| 569 |
} |
560 |
} |
| 570 |
|
561 |
|
| 571 |
// Load Packet data into buffer data |
562 |
// Load any remaining packet data into buffer data |
| 572 |
packet->CopyData ((uint8_t*)buffer->data, packet->GetSize ()); |
563 |
packet->CopyData ((uint8_t*)buffer->data, packet->GetSize ()); |
| 573 |
|
564 |
|
| 574 |
if (buffer->l4) |
565 |
if (buffer->l4) |
|
|
| 581 |
ofpbuf_push (buffer, buffer->l3, l3_length); |
572 |
ofpbuf_push (buffer, buffer->l3, l3_length); |
| 582 |
delete (ip_header*)buffer->l3; |
573 |
delete (ip_header*)buffer->l3; |
| 583 |
} |
574 |
} |
| 584 |
if (buffer->l2) |
|
|
| 585 |
{ |
| 586 |
ofpbuf_push (buffer, buffer->l2, l2_length); |
| 587 |
delete (eth_header*)buffer->l2; |
| 588 |
} |
| 589 |
|
575 |
|
| 590 |
return buffer; |
576 |
return buffer; |
| 591 |
} |
577 |
} |