Skip to content

Commit 0f37b30

Browse files
committed
integration-test: SNP: improve clarity
Interestingly, the interrupt status never shows that we can receive a packet. Buggy OVMF firmware?
1 parent fb5c097 commit 0f37b30

File tree

1 file changed

+51
-13
lines changed
  • uefi-test-runner/src/proto/network

1 file changed

+51
-13
lines changed

uefi-test-runner/src/proto/network/snp.rs

Lines changed: 51 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,55 @@
11
// SPDX-License-Identifier: MIT OR Apache-2.0
22

3+
use core::ops::DerefMut;
34
use uefi::proto::network::snp::{InterruptStatus, NetworkState, ReceiveFlags, SimpleNetwork};
45
use uefi::proto::network::MacAddress;
56
use uefi::{boot, Status};
67

8+
const ETHERNET_PROTOCOL_IPV4: u16 = 0x0800;
9+
10+
/// Receives the next IPv4 packet and prints corresponding metadata.
11+
fn receive(simple_network: &mut SimpleNetwork, buffer: &mut [u8]) -> uefi::Result<usize> {
12+
let mut recv_src_mac = MacAddress([0; 32]);
13+
let mut recv_dst_mac = MacAddress([0; 32]);
14+
let mut recv_ethernet_protocol = 0;
15+
16+
debug!(
17+
"InterruptStatus (before receive): {:?}",
18+
simple_network.get_interrupt_status()?
19+
);
20+
let res = simple_network.receive(
21+
buffer,
22+
None,
23+
Some(&mut recv_src_mac),
24+
Some(&mut recv_dst_mac),
25+
Some(&mut recv_ethernet_protocol),
26+
);
27+
debug!(
28+
"InterruptStatus (after receive) : {:?}",
29+
simple_network.get_interrupt_status()?
30+
);
31+
32+
res.inspect(|_| {
33+
debug!("Received:");
34+
debug!(" src_mac = {:x?}", recv_src_mac);
35+
debug!(" dst_mac = {:x?}", recv_dst_mac);
36+
debug!(" ethernet_proto=0x{:x?}", recv_ethernet_protocol);
37+
38+
// Ensure that we do not accidentally get an ARP packet, which we
39+
// do not expect in this test.
40+
assert_eq!(recv_ethernet_protocol, ETHERNET_PROTOCOL_IPV4);
41+
})
42+
}
43+
44+
/// This test sends a simple UDP/IP packet to the `EchoService` (created by
45+
/// `cargo xtask run`) and receives its message.
746
pub fn test() {
847
info!("Testing the simple network protocol");
948

1049
let handles = boot::find_handles::<SimpleNetwork>().unwrap_or_default();
1150

1251
for handle in handles {
13-
let Ok(simple_network) = boot::open_protocol_exclusive::<SimpleNetwork>(handle) else {
52+
let Ok(mut simple_network) = boot::open_protocol_exclusive::<SimpleNetwork>(handle) else {
1453
continue;
1554
};
1655

@@ -51,6 +90,12 @@ pub fn test() {
5190
)
5291
.expect("Failed to set receive filters");
5392

93+
// EthernetFrame(IPv4Packet(UDPPacket(Payload))).
94+
// The ethernet frame header will be filled by `transmit()`.
95+
// The UDP packet contains the byte sequence `4, 4, 3, 2, 1`.
96+
//
97+
// The packet is sent to the `EchoService` created by
98+
// `cargo xtask run`. It runs on UDP port 21572.
5499
let payload = b"\0\0\0\0\0\0\0\0\0\0\0\0\0\0\
55100
\x45\x00\
56101
\x00\x21\
@@ -67,7 +112,6 @@ pub fn test() {
67112
\xa9\xe4\
68113
\x04\x01\x02\x03\x04";
69114

70-
let dest_addr = MacAddress([0xffu8; 32]);
71115
assert!(!simple_network
72116
.get_interrupt_status()
73117
.unwrap()
@@ -79,8 +123,8 @@ pub fn test() {
79123
simple_network.mode().media_header_size as usize,
80124
payload,
81125
None,
82-
Some(dest_addr),
83-
Some(0x0800),
126+
Some(simple_network.mode().broadcast_address),
127+
Some(ETHERNET_PROTOCOL_IPV4),
84128
)
85129
.expect("Failed to transmit frame");
86130

@@ -95,16 +139,10 @@ pub fn test() {
95139
let mut buffer = [0u8; 1500];
96140

97141
info!("Waiting for the reception");
98-
if simple_network.receive(&mut buffer, None, None, None, None)
99-
== Err(Status::NOT_READY.into())
100-
{
101-
boot::stall(1_000_000);
102-
103-
simple_network
104-
.receive(&mut buffer, None, None, None, None)
105-
.unwrap();
106-
}
142+
let n = receive(simple_network.deref_mut(), &mut buffer).unwrap();
143+
debug!("Reply has {n} bytes");
107144

145+
// Check payload in UDP packet that was reversed by our EchoService.
108146
assert_eq!(buffer[42..47], [4, 4, 3, 2, 1]);
109147

110148
// Get stats

0 commit comments

Comments
 (0)