Skip to content

Commit a067442

Browse files
committed
IPsec: add IPv6 drop/deliver module test (ESP/AH/BYPASS/no-rule)
tests/module/IPsec_Ipv6.test runs four UDP streams between two IPv6 hosts, each matched by a different Security Policy, and asserts all four IPsec outcomes over IPv6: the ESP-protected, AH-protected and BYPASS streams are delivered, while the stream with no matching rule is dropped at egress. This is stronger than the ipv6.ini fingerprint (which only pins byte output) -- it asserts actual end-to-end delivery and non-delivery, and the AH stream exercises the AH path fixed in the previous commit.
1 parent 09ef81f commit a067442

1 file changed

Lines changed: 217 additions & 0 deletions

File tree

tests/module/IPsec_Ipv6.test

Lines changed: 217 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,217 @@
1+
%description:
2+
IPsec over IPv6 -- end-to-end drop/deliver assertions (stronger than the ipv6.ini
3+
fingerprint example, which only pins byte output). Four UDP streams run between two
4+
IPv6 hosts, each matched by a different Security Policy, proving that all four IPsec
5+
egress/ingress outcomes behave correctly over IPv6:
6+
7+
app[0] 1000->2000 ESP-protected -> delivered (egress ESP PROTECT, ingress ACCEPT ESP)
8+
app[1] 1001->2001 BYPASS rule -> delivered (no protection)
9+
app[2] 1002->2002 no matching rule -> dropped at egress (default DROP)
10+
app[3] 1003->2003 AH-protected -> delivered (egress AH PROTECT, ingress ACCEPT AH)
11+
12+
The AH stream is the point of this test: the AH ingress path had a latent
13+
double-remove bug (it removed the IPsecAuthenticationHeader twice, so the second
14+
removeAtFront<> hit the following EncryptedChunk and crashed). No prior example used
15+
AH, so neither a fingerprint nor the existing examples could have caught it. Here we
16+
require an AH datagram to be de-protected and delivered end to end.
17+
18+
%#--------------------------------------------------------------------------------------------------------------
19+
%file: test.ned
20+
import inet.networklayer.configurator.ipv6.Ipv6NetworkConfigurator;
21+
import inet.node.ipv6.StandardHost6;
22+
import ned.DatarateChannel;
23+
24+
network IPsecIpv6Test
25+
{
26+
submodules:
27+
client1: StandardHost6 { @display("p=80,100;i=device/pc3"); }
28+
server: StandardHost6 { @display("p=280,100;i=device/pc2"); }
29+
configurator: Ipv6NetworkConfigurator { @display("p=80,180"); }
30+
connections:
31+
client1.pppg++ <--> { datarate = 10Mbps; delay = 0.1us; } <--> server.pppg++;
32+
}
33+
34+
%#--------------------------------------------------------------------------------------------------------------
35+
%file: ipsecConfig.xml
36+
<ipsecConfig>
37+
<Devices>
38+
<Device id="client1">
39+
<!-- app[0] 1000->2000 UDP: ESP -->
40+
<SecurityPolicy>
41+
<Selector>
42+
<LocalAddress>client1</LocalAddress>
43+
<RemoteAddress>server</RemoteAddress>
44+
<Protocol>UDP</Protocol>
45+
<LocalPort>1000</LocalPort>
46+
<RemotePort>2000</RemotePort>
47+
</Selector>
48+
<Direction>OUT</Direction>
49+
<Action>PROTECT</Action>
50+
<Protection>ESP</Protection>
51+
<EspMode>CONFIDENTIALITY</EspMode>
52+
<EncryptionAlg>AES_CBC_128</EncryptionAlg>
53+
<SecurityAssociation><SPI>101</SPI></SecurityAssociation>
54+
</SecurityPolicy>
55+
56+
<!-- app[1] 1001->2001 UDP: BYPASS -->
57+
<SecurityPolicy>
58+
<Selector>
59+
<LocalAddress>client1</LocalAddress>
60+
<RemoteAddress>server</RemoteAddress>
61+
<Protocol>UDP</Protocol>
62+
<LocalPort>1001</LocalPort>
63+
<RemotePort>2001</RemotePort>
64+
</Selector>
65+
<Direction>OUT</Direction>
66+
<Action>BYPASS</Action>
67+
</SecurityPolicy>
68+
69+
<!-- app[3] 1003->2003 UDP: AH -->
70+
<SecurityPolicy>
71+
<Selector>
72+
<LocalAddress>client1</LocalAddress>
73+
<RemoteAddress>server</RemoteAddress>
74+
<Protocol>UDP</Protocol>
75+
<LocalPort>1003</LocalPort>
76+
<RemotePort>2003</RemotePort>
77+
</Selector>
78+
<Direction>OUT</Direction>
79+
<Action>PROTECT</Action>
80+
<Protection>AH</Protection>
81+
<AuthenticationAlg>HMAC_SHA1</AuthenticationAlg>
82+
<SecurityAssociation><SPI>103</SPI></SecurityAssociation>
83+
</SecurityPolicy>
84+
85+
<!-- app[2] 1002->2002 has NO policy => default DROP at egress -->
86+
</Device>
87+
88+
<Device id="server">
89+
<!-- app[0] 2000<-1000 UDP: ESP, same SPI as client1's OUT rule -->
90+
<SecurityPolicy>
91+
<Selector>
92+
<LocalAddress>server</LocalAddress>
93+
<RemoteAddress>client1</RemoteAddress>
94+
<Protocol>UDP</Protocol>
95+
<LocalPort>2000</LocalPort>
96+
<RemotePort>1000</RemotePort>
97+
</Selector>
98+
<Direction>IN</Direction>
99+
<Action>PROTECT</Action>
100+
<Protection>ESP</Protection>
101+
<EspMode>CONFIDENTIALITY</EspMode>
102+
<EncryptionAlg>AES_CBC_128</EncryptionAlg>
103+
<SecurityAssociation><SPI>101</SPI></SecurityAssociation>
104+
</SecurityPolicy>
105+
106+
<!-- app[1] 2001<-1001 UDP: BYPASS -->
107+
<SecurityPolicy>
108+
<Selector>
109+
<LocalAddress>server</LocalAddress>
110+
<RemoteAddress>client1</RemoteAddress>
111+
<Protocol>UDP</Protocol>
112+
<LocalPort>2001</LocalPort>
113+
<RemotePort>1001</RemotePort>
114+
</Selector>
115+
<Direction>IN</Direction>
116+
<Action>BYPASS</Action>
117+
</SecurityPolicy>
118+
119+
<!-- app[3] 2003<-1003 UDP: AH, same SPI as client1's OUT rule -->
120+
<SecurityPolicy>
121+
<Selector>
122+
<LocalAddress>server</LocalAddress>
123+
<RemoteAddress>client1</RemoteAddress>
124+
<Protocol>UDP</Protocol>
125+
<LocalPort>2003</LocalPort>
126+
<RemotePort>1003</RemotePort>
127+
</Selector>
128+
<Direction>IN</Direction>
129+
<Action>PROTECT</Action>
130+
<Protection>AH</Protection>
131+
<AuthenticationAlg>HMAC_SHA1</AuthenticationAlg>
132+
<SecurityAssociation><SPI>103</SPI></SecurityAssociation>
133+
</SecurityPolicy>
134+
</Device>
135+
</Devices>
136+
</ipsecConfig>
137+
138+
%#--------------------------------------------------------------------------------------------------------------
139+
%inifile: omnetpp.ini
140+
[General]
141+
ned-path = .;../../../../src;../../lib
142+
network = IPsecIpv6Test
143+
sim-time-limit = 10s
144+
cmdenv-express-mode = false
145+
cmdenv-log-prefix = "%C: "
146+
147+
# static global IPv6 addresses so "client1"/"server" in the SPD selectors resolve to
148+
# routable addresses (wire each node's Ipv6NodeConfigurator to the global configurator)
149+
**.ipv6.configurator.networkConfiguratorModule = "configurator"
150+
151+
**.client*.**.hasIpsec = true
152+
**.server.**.hasIpsec = true
153+
**.client1.**spdConfig = xmldoc("ipsecConfig.xml", "ipsecConfig/Devices/Device[@id='client1']/")
154+
**.server.**spdConfig = xmldoc("ipsecConfig.xml", "ipsecConfig/Devices/Device[@id='server']/")
155+
156+
# zero delays -> deterministic ACCEPT path (the QUEUE/reinject path is covered by the
157+
# ipv6.ini example and NetfilterHooks_Ipv6 test)
158+
**.ipsec.ahProtectOutDelay = 0s
159+
**.ipsec.ahProtectInDelay = 0s
160+
**.ipsec.espProtectOutDelay = 0s
161+
**.ipsec.espProtectInDelay = 0s
162+
163+
**.numApps = 4
164+
**.client1.app[*].typename = "UdpBasicApp"
165+
**.client1.app[0].localPort = 1000
166+
**.client1.app[1].localPort = 1001
167+
**.client1.app[2].localPort = 1002
168+
**.client1.app[3].localPort = 1003
169+
**.client1.app[*].destAddresses = "server"
170+
**.client1.app[0].destPort = 2000
171+
**.client1.app[1].destPort = 2001
172+
**.client1.app[2].destPort = 2002
173+
**.client1.app[3].destPort = 2003
174+
**.client1.app[*].startTime = 1s
175+
**.client1.app[*].stopTime = 4s
176+
**.client1.app[*].sendInterval = 1s
177+
**.client1.app[*].messageLength = 100B
178+
179+
**.server.app[*].typename = "UdpSink"
180+
**.server.app[0].localPort = 2000
181+
**.server.app[1].localPort = 2001
182+
**.server.app[2].localPort = 2002
183+
**.server.app[3].localPort = 2003
184+
185+
%#--------------------------------------------------------------------------------------------------------------
186+
%# ===== egress decisions on client1 =====
187+
%contains: stdout
188+
IPsec OUT ESP PROTECT
189+
%contains: stdout
190+
IPsec OUT AH PROTECT
191+
%contains: stdout
192+
IPsec OUT BYPASS rule
193+
%# app[2] has no policy -> default DROP at egress
194+
%contains: stdout
195+
IPsec OUT BYPASS, no matching rule
196+
%# ===== ingress decisions on server =====
197+
%contains: stdout
198+
IPsec IN ACCEPT ESP
199+
%# the AH de-protection that the double-remove fix unlocks:
200+
%contains: stdout
201+
IPsec IN ACCEPT AH
202+
%contains: stdout
203+
IPsec BYPASS rule
204+
%# ===== end-to-end delivery: ESP, BYPASS and AH streams arrive; the no-rule stream does not =====
205+
%contains: stdout
206+
server.app[0]: Received packet
207+
%contains: stdout
208+
server.app[1]: Received packet
209+
%contains: stdout
210+
server.app[3]: Received packet
211+
%not-contains: stdout
212+
server.app[2]: Received packet
213+
%#--------------------------------------------------------------------------------------------------------------
214+
%postrun-command: grep "undisposed object:" test.out > test_undisposed.out || true
215+
%not-contains: test_undisposed.out
216+
undisposed object: (
217+
%#--------------------------------------------------------------------------------------------------------------

0 commit comments

Comments
 (0)