#!/usr/bin/perl # # Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006 # Yokogawa Electric Corporation. # All rights reserved. # # Redistribution and use of this software in source and binary # forms, with or without modification, are permitted provided that # the following conditions and disclaimer are agreed and accepted # by the user: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with # the distribution. # # 3. Neither the names of the copyrighters, the name of the project # which is related to this software (hereinafter referred to as # "project") nor the names of the contributors may be used to # endorse or promote products derived from this software without # specific prior written permission. # # 4. No merchantable use may be permitted without prior written # notification to the copyrighters. # # 5. The copyrighters, the project and the contributors may prohibit # the use of this software at any time. # # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHTERS, THE PROJECT AND # CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING # BUT NOT LIMITED THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS # FOR A PARTICULAR PURPOSE, ARE DISCLAIMED. IN NO EVENT SHALL THE # COPYRIGHTERS, THE PROJECT OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, # INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR # SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, # STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING # IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE # POSSIBILITY OF SUCH DAMAGE. # # $TAHI: ct/icmp.p2/Pkt_Too_Big.seq,v 1.12 2006/03/09 07:29:59 akisada Exp $ ######################################################################## BEGIN { $V6evalTool::TestVersion = '$Name: V6LC_P2_1_4_6 $'; } use V6evalTool; use icmp; use Pkt_Too_Big; use lib '../'; use AdvancedFunctionality; sub create_nce_link0(); sub create_nce_link1($); sub cleanup_local($); sub cleanup_tunnel(); # Interface $IF = 'Link0'; $IF1 = 'Link1'; checkNUT(router); if(!$AdvancedFunctionality::MTU_CONFIGURATION) { exit($V6evalTool::exitSkip); } %pktdesc = ( echo_request_1500_link0 => 'Send Echo Request w/ 1500 bytes (Link0)', pkt_too_big_link0 => 'Receive Packet Too Big Message (MTU = 1280)', ); vLogHTML("Initialization
"); vCapture($IF); if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { vCapture($IF1); } #----------------------------------------------------------------------# # Test Setup # #----------------------------------------------------------------------# $ret = setup_v6LC_5_1_4_A(); if($ret == $icmp::subFail) { goto error; } unless($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { my $srcaddr = vMAC2LLAddr($V6evalTool::NutDef{'Link0_addr'}); $srcaddr =~ s/fe80::/3ffe:501:ffff:100:/; my $dstaddr = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); $dstaddr =~ s/fe80::/3ffe:501:ffff:110:/; my $insrcaddr = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); $insrcaddr =~ s/fe80::/3ffe:501:ffff:100:/; my $indstaddr = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); $indstaddr =~ s/fe80::/3ffe:501:ffff:101:/; my $gateway = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); my $Link0_device = $V6evalTool::NutDef{'Link0_device'}; if(vRemote('tunnel.rmt', 'if=0 '. 'prefixlen=64 '. 'routeprefixlen=64 '. 'addrfamily=inet6 '. "prefix=3ffe:501:ffff:101:: ". "srcaddr=$srcaddr ". "dstaddr=$dstaddr ". "insrcaddr=$insrcaddr ". "indstaddr=$indstaddr ")) { vLogHTML('tunnel.rmt: '. 'Can\'t configure the tunnel.
'); exit($V6evalTool::exitFatal); } } $ret = create_nce_link0(); if($ret == $icmp::subFail) { goto error; } $ret = create_nce_link1( $AdvancedFunctionality::HAS_MULTIPLE_INTERFACES? $IF1: $IF); if($ret == $icmp::subFail) { goto error; } #---------------------------------------------------------------------- # reduce Link MTU of LINK1 Interface from 1500 to 1280 #---------------------------------------------------------------------- if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES && (set_mtu($IF1, 1280) != $icmp::subPass)) { vLogHTML('set mtu failed.
'); goto error; }; #----------------------------------------------------------------------# # Procedure # #----------------------------------------------------------------------# vLogHTML("Procedure:
"); vClear($IF); %ret1 = vSend($IF, echo_request_1500_link0); %ret = icmp_vRecv($IF, $icmp::wait_reply, 0, 0, pkt_too_big_link1); if($ret{status} != 0) { vLogHTML(''. 'TN can not receive Packet Too Big Message.
'); goto error; } elsif($ret{recvFrame} eq 'pkt_too_big_link1' ) { vLog("TN received Packet Too Big Message."); } else { vLogHTML(''. 'TN receive unexpected packets from NUT
'); goto error; }; #---------------------------------------------------------------------- # remove configurations #---------------------------------------------------------------------- vLog("clear configurations"); if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { set_mtu($IF1, 1500); } vLog("OK"); cleanup_local($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES? $IF1: $IF); cleanup(); unless($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { cleanup_tunnel(); } vStop($IF); if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { vStop($IF1); } exit($V6evalTool::exitPass); error: vLogHTML('FAIL
'); vLog("clear configurations"); if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { set_mtu($IF1, 1500); } cleanup_local( $AdvancedFunctionality::HAS_MULTIPLE_INTERFACES? $IF1: $IF); cleanup(); unless($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { cleanup_tunnel(); } vStop($IF); if($AdvancedFunctionality::HAS_MULTIPLE_INTERFACES) { vStop($IF1); } exit($V6evalTool::exitFail); #----------------------------------------------------------------------# sub create_nce_link0() { my $false = 0; my $true = 1; my $got_erep = $false; my $delay_first_probe_time = 5; # NUT: NONE/INCOMPLETE/REACHABLE/STALE/DELAY/PROBE vClear($IF); vSend($IF, 'echo_request_global'); for(my $timeout = $icmp::wait_reply; ; ) { my %ret = vRecv($IF, $timeout, 0, 0, 'echo_reply_global', 'ns_global', 'ns_global_sll'); if($ret{'recvFrame'} eq 'echo_reply_global') { # NUT: REACHABLE/DELAY $got_erep = $true; $timeout = $delay_first_probe_time + $icmp::wait_reply; next; } if(($ret{'recvFrame'} eq 'ns_global') || ($ret{'recvFrame'} eq 'ns_global_sll')) { # NUT: INCOMPLETE/PROBE vSend($IF, 'na_global'); # NUT: REACHABLE $timeout = $icmp::wait_reply; next; } if($got_erep) { last; } vLogHTML(''. 'Could\'t observe Echo Reply
'); return($icmp::subFail); } return($icmp::subPass); } #----------------------------------------------------------------------# sub create_nce_link1($) { my ($interface) = @_; my $false = 0; my $true = 1; my $got_erep = $false; my $delay_first_probe_time = 5; # NUT: NONE/INCOMPLETE/REACHABLE/STALE/DELAY/PROBE vClear($interface); vSend($interface, 'echo_request_global_link1'); for(my $timeout = $icmp::wait_reply; ; ) { my %ret = vRecv($interface, $timeout, 0, 0, 'echo_reply_global_link1', 'ns_global_link1', 'ns_global_sll_link1'); if($ret{'recvFrame'} eq 'echo_reply_global_link1') { # NUT: REACHABLE/DELAY $got_erep = $true; $timeout = $delay_first_probe_time + $icmp::wait_reply; next; } if(($ret{'recvFrame'} eq 'ns_global_link1') || ($ret{'recvFrame'} eq 'ns_global_sll_link1')) { # NUT: INCOMPLETE/PROBE vSend($interface, 'na_global_link1'); # NUT: REACHABLE $timeout = $icmp::wait_reply; next; } if($got_erep) { last; } vLogHTML(''. 'Could\'t observe Echo Reply
'); return($icmp::subFail); } return($icmp::subPass); } #----------------------------------------------------------------------# sub cleanup_local($) { my ($interface) = @_; vClear($interface); vSend($interface, 'clean_na_global_link1'); vSend($interface, 'echo_request_global_link1'); vRecv($interface, $icmp::wait_time_for_ns, 0, 0); return; } #----------------------------------------------------------------------# sub cleanup_tunnel() { my $srcaddr = vMAC2LLAddr($V6evalTool::NutDef{'Link0_addr'}); $srcaddr =~ s/fe80::/3ffe:501:ffff:100:/; my $dstaddr = vMAC2LLAddr($V6evalTool::NutDef{'Link0_addr'}); $dstaddr =~ s/fe80::/3ffe:501:ffff:110:/; my $insrcaddr = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); $insrcaddr =~ s/fe80::/3ffe:501:ffff:100:/; my $indstaddr = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); $indstaddr =~ s/fe80::/3ffe:501:ffff:101:/; my $gateway = vMAC2LLAddr($V6evalTool::TnDef{'Link0_addr'}); my $Link0_device = $V6evalTool::NutDef{'Link0_device'}; if(vRemote('tunnel.rmt', 'if=0 '. 'deletetunnel '. 'prefixlen=64 '. 'routeprefixlen=64 '. 'addrfamily=inet6 '. "prefix=3ffe:501:ffff:101:: ". "srcaddr=$srcaddr ". "dstaddr=$dstaddr ". "insrcaddr=$insrcaddr ". "indstaddr=$indstaddr ")) { vLogHTML('tunnel.rmt: '. 'Can\'t configure the tunnel.
'); exit($V6evalTool::exitFatal); } return; } ######################################################################## __END__ =head1 NAME Pkt_Too_Big - Verify that the NUT sends Packet Too Big Message =head1 TARGET Router =head1 SYNOPSIS Pkt_Too_Big.seq [-tooloption ...] -p Pkt_Too_Big.def =head1 NETWORK CONFIGURATION This test is OFFLINK Network Configuration test. In this test, TN play a Roll of the Router. Physical Network configuration Link0 --------+---------------+-------------- | | NUT TN | | --------+---------------+-------------- Link1 Logical Network Configuration Host A (TN-Link0) | Link0 --------+-------+----------------- | NUT (globaladdress:B) | --------+-------+----------------- | Link1 Router(TN-Link1) | ----------------+-------+--------- | HOST B (OFFLINK_LINK1_GLOBAL_ADDRESS) In this configuration, Packets are send and received. for example, In Logical HOST B -- Echo Reply --> NUT Actually, in physical TN (as Router) -- Echo Reply --> NUT =head1 INITIALIZATION TN attempt to execute remote command 'vRemote(route.rmt)'. 'route add -inet6 OFFLINK_LINK1_GLOBAL_ADDRESS TN-LINK1-address' And status of Neighbor Cache Entry for TN's addresses are reachable. =head1 TEST PROCEDURE This test verifies that the node sends a Packet Too Big Message in response to a packet that it can not forward because the packet is larger than the MTU of the outgoing link. TN NUT --------------------------- 1. After NUT is initialized (set static route) , NUT sets the Link MTU of LINK1 Interface to 1280 . 2. TN send Echo Request to Host B. === echo request ===> 3. NUT send Packet Too Big Message <=== Packet Too Big Message === =head1 JUDGEMENT << PASS >> NUT send a Packet Too Big Message. << FAIL >> NUT do not send a Packet Too Big Message. =cut # =head1 REFERENCE # # RFC2463 # 3.2 Packet Too Big Message # # 0 1 2 3 # 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 # +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ # | Type | Code | Checksum | # +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ # | MTU | # +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ # | As much of invoking packet | # + as will fit without the ICMPv6 packet + # | exceeding the minimum IPv6 MTU [IPv6] | # # IPv6 Fields: # # =begin html #
#    Destination Address
# Copied from the Source Address field of the invoking # packet. #
# # =end html # # ICMPv6 Fields: # # =begin html #
#    Type           2
# 
# # =end html # # =begin html #
#    Code           Set to 0 (zero) by the sender and ignored by the
#                   receiver
# 
# # =end html # # MTU The Maximum Transmission Unit of the next-hop link. # # Description # # =begin html #
#    A Packet Too Big MUST be sent by a router in response to a packet
#    that it cannot forward because the packet is larger than the MTU of
#    the outgoing link.  The information in this message is used as part
#    of the Path MTU Discovery process [PMTU].
# 
# # =end html # # Sending a Packet Too Big Message makes an exception to one of the # rules of when to send an ICMPv6 error message, in that unlike other # messages, it is sent in response to a packet received with an IPv6 # multicast destination address, or a link-layer multicast or link- # layer broadcast address. # =pod =head1 REFERENCE =begin html
RFC 2463 - ICMPv6 (ICMP for IPv6)
=end html =head1 SEE ALSO perldoc V6evalTool perldoc V6evalRemote =cut