Skip to content

Commit 9d0af75

Browse files
committed
add test for net_lwip_webserver with iperf throughput validation
1 parent ce81b01 commit 9d0af75

2 files changed

Lines changed: 63 additions & 2 deletions

File tree

examples/device/net_lwip_webserver/src/tusb_config.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,10 +96,13 @@ extern "C" {
9696
#define USE_ECM 1
9797
#else
9898
#define USE_ECM 0
99-
#define INCLUDE_IPERF
10099
#endif
101100
#endif
102101

102+
#ifndef INCLUDE_IPERF
103+
#define INCLUDE_IPERF
104+
#endif
105+
103106
//--------------------------------------------------------------------
104107
// NCM CLASS CONFIGURATION, SEE "ncm.h" FOR PERFORMANCE TUNING
105108
//--------------------------------------------------------------------

test/hil/hil_test.py

Lines changed: 59 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1028,6 +1028,63 @@ def test_device_mtp(board):
10281028
mtp.disconnect()
10291029

10301030

1031+
def test_device_net_lwip_webserver(board):
1032+
# MAC hard-coded in examples/device/net_lwip_webserver/src/main.c; Linux names the
1033+
# USB network interface enx<MAC_lowercase_no_colons>. Device IP is 192.168.7.1 and
1034+
# the example runs an iperf2 TCP server on port 5001 (INCLUDE_IPERF).
1035+
import socket
1036+
mac_no_colons = '0202846a9600'
1037+
iface = 'enx' + mac_no_colons
1038+
device_ip = '192.168.7.1'
1039+
iperf_port = 5001
1040+
1041+
# Wait for the host to get an IPv4 address in the device's subnet (DHCP served by the device).
1042+
deadline = time.time() + ENUM_TIMEOUT
1043+
host_ip = None
1044+
while time.time() < deadline:
1045+
ret = subprocess.run(['ip', '-o', '-4', 'addr', 'show', iface],
1046+
capture_output=True, text=True, timeout=2)
1047+
m = re.search(r'inet (192\.168\.7\.\d+)/', ret.stdout) if ret.returncode == 0 else None
1048+
if m:
1049+
host_ip = m.group(1)
1050+
break
1051+
time.sleep(0.5)
1052+
assert host_ip, f'USB net iface {iface} did not come up with 192.168.7.x within {ENUM_TIMEOUT}s'
1053+
1054+
# Poll the iperf TCP port until the device is accepting. The net stack comes up a bit
1055+
# after DHCP completes; iperf server binding isn't instantaneous after reflash.
1056+
deadline = time.time() + ENUM_TIMEOUT
1057+
last_err = None
1058+
while time.time() < deadline:
1059+
try:
1060+
with socket.create_connection((device_ip, iperf_port), timeout=1):
1061+
last_err = None
1062+
break
1063+
except OSError as e:
1064+
last_err = e
1065+
time.sleep(0.3)
1066+
assert last_err is None, f'iperf TCP {device_ip}:{iperf_port} not accepting within {ENUM_TIMEOUT}s: {last_err}'
1067+
1068+
# Throughput: 5-second iperf2 TCP test, CSV output for stable parsing.
1069+
# iperf2 CSV final summary line: timestamp,src_ip,src_port,dst_ip,dst_port,id,interval,bytes,bps
1070+
ret = subprocess.run(['iperf', '-c', device_ip, '-t', '5', '-y', 'C'],
1071+
capture_output=True, text=True, timeout=30)
1072+
stderr = ret.stderr.strip()
1073+
stdout = ret.stdout.strip()
1074+
assert ret.returncode == 0, f'iperf rc={ret.returncode}: stderr={stderr!r} stdout={stdout!r}'
1075+
lines = [l for l in stdout.splitlines() if l]
1076+
assert lines, f'iperf produced no output (rc={ret.returncode}, stderr={stderr!r})'
1077+
try:
1078+
bps = int(lines[-1].split(',')[-1])
1079+
except (ValueError, IndexError) as e:
1080+
raise AssertionError(f'could not parse iperf output: {lines[-1]!r} ({e})')
1081+
mbps = bps / 1e6
1082+
print(f' iperf {mbps:5.1f} Mbps', end='')
1083+
1084+
# Reject implausibly low throughput - a working USB-net link should clear this easily.
1085+
assert mbps >= 1.0, f'iperf throughput too low: {mbps:.2f} Mbps'
1086+
1087+
10311088
def test_device_msc_dual_lun(board):
10321089
uid = board['uid']
10331090

@@ -1150,7 +1207,8 @@ def test_device_hid_generic_inout(board):
11501207
'device/hid_generic_inout',
11511208
'device/printer_to_cdc',
11521209
'device/midi_test',
1153-
'device/mtp'
1210+
'device/mtp',
1211+
'device/net_lwip_webserver'
11541212
]
11551213

11561214
dual_tests = [

0 commit comments

Comments
 (0)