Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/http/httpd.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ struct http_request {
char path[HTTP_PATH_LEN]; // URL path
char query[HTTP_QUERY_LEN]; // URL query string, if present in the target
char headers[HTTP_HEADERS_LEN]; // HTTP headers
char body[HTTP_BODY_LEN]; // HTTP body (for POST requests)
char body[HTTP_BODY_LEN]; // HTTP body, if present in the request
size_t body_len;
};

Expand Down
2 changes: 1 addition & 1 deletion src/port/rp2350_cyw43439/cyw43439_wifi.c
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ static int op_connect(struct wolfIP_ll_dev *ll,
const uint8_t bssid[6])
{
(void)ll;
/* For WPA2/WPA3 the supplicant owns the keying material; the radio
/* For WPA2-PSK the supplicant owns the keying material; the radio
* does 802.11 open auth + assoc carrying the RSN IE (open_auth = 0
* selects the WPA2-PSK/CCMP path), then EAPOL flows through the
* 0x888E TX/RX path for the host-run 4-way. */
Expand Down
17 changes: 15 additions & 2 deletions src/test/unit/unit.c
Original file line number Diff line number Diff line change
Expand Up @@ -210,6 +210,7 @@ Suite *wolf_suite(void)
tcase_add_test(tc_utils, test_sock_bind_tcp_state_not_closed);
tcase_add_test(tc_utils, test_sock_bind_tcp_filter_blocks);
tcase_add_test(tc_utils, test_sock_bind_tcp_port_collision_rejected);
tcase_add_test(tc_utils, test_sock_connect_tcp_keeps_bound_low_port);
tcase_add_test(tc_utils, test_sock_bind_udp_src_port_nonzero);
tcase_add_test(tc_utils, test_udp_auto_port_skips_in_use);
tcase_add_test(tc_utils, test_port_alloc_walks_past_long_collision_run);
Expand Down Expand Up @@ -262,6 +263,7 @@ Suite *wolf_suite(void)
tcase_add_test(tc_utils, test_sock_accept_invalid_tcp_fd);
tcase_add_test(tc_utils, test_sock_accept_success_sets_addr);
tcase_add_test(tc_utils, test_sock_accept_listener_resets_paws_state);
tcase_add_test(tc_utils, test_syn_rcvd_rst_listener_resets_paws_state);
tcase_add_test(tc_utils, test_sock_accept_no_available_socket);
tcase_add_test(tc_utils, test_sock_accept_no_free_socket_syn_rcvd);
tcase_add_test(tc_utils, test_sock_accept_listen_no_connection);
Expand Down Expand Up @@ -292,11 +294,14 @@ Suite *wolf_suite(void)
#ifdef IP_MULTICAST
tcase_add_test(tc_utils, test_multicast_join_and_drop_reports);
tcase_add_test(tc_utils, test_multicast_join_report_repeated);
tcase_add_test(tc_utils, test_multicast_join_report_repeat_heap_full_rearmed_on_poll);
tcase_add_test(tc_utils, test_multicast_join_validation_and_shared_refs);
tcase_add_test(tc_utils, test_multicast_udp_receive_requires_join);
tcase_add_test(tc_utils, test_multicast_udp_send_mac_ttl_loop_and_options);
tcase_add_test(tc_utils, test_multicast_igmp_query_refreshes_report);
tcase_add_test(tc_utils, test_multicast_igmp_query_flood_coalesced);
tcase_add_test(tc_utils, test_multicast_igmp_query_report_heap_full_rearmed_on_poll);
tcase_add_test(tc_utils, test_multicast_igmp_query_report_rearmed_after_tick_rollback);
tcase_add_test(tc_utils, test_multicast_igmp_query_bad_checksum_dropped);
tcase_add_test(tc_utils, test_multicast_igmp_query_spoofed_dropped);
tcase_add_test(tc_utils, test_multicast_join_requires_configured_ip);
Expand Down Expand Up @@ -1305,7 +1310,7 @@ Suite *wolf_suite(void)
tcase_add_test(tc_core, test_notify_loopback_null_stack_no_crash);

/* === Branch-coverage tests from fleet ===*/
/* --- unit_tests_tcp_state.c (65 tests) --- */
/* --- unit_tests_tcp_state.c (72 tests) --- */
tcase_add_test(tc_core, test_tcp_send_reset_reply_ignores_rst_input);
tcase_add_test(tc_core, test_tcp_send_reset_reply_ack_in_uses_ack_seq);
tcase_add_test(tc_core, test_tcp_send_reset_reply_syn_no_ack_sets_rst_ack);
Expand All @@ -1322,6 +1327,7 @@ Suite *wolf_suite(void)
tcase_add_test(tc_core, test_tcp_input_syn_rcvd_rst_good_seq_reverts_to_listen);
tcase_add_test(tc_core, test_tcp_input_syn_rcvd_rst_good_seq_nonlistener_closes);
tcase_add_test(tc_core, test_tcp_input_syn_rcvd_rst_nullcb_recv_reports_eof);
tcase_add_test(tc_core, test_tcp_input_closed_bound_rst_ignored);
tcase_add_test(tc_core, test_tcp_input_time_wait_sends_ack_on_any_segment);
tcase_add_test(tc_core, test_tcp_input_last_ack_unacceptable_sends_ack);
tcase_add_test(tc_core, test_tcp_input_last_ack_syn_sends_challenge_ack);
Expand All @@ -1344,6 +1350,12 @@ Suite *wolf_suite(void)
tcase_add_test(tc_core, test_tcp_rto_cb_fin_wait_2_wrong_state_stops_timer);
tcase_add_test(tc_core, test_tcp_rto_cb_ctrl_not_needed_stops);
tcase_add_test(tc_core, test_tcp_rto_cb_ctrl_maxretries_nonlistener_closes);
tcase_add_test(tc_core, test_tcp_rto_cb_ctrl_rearm_heap_full_closes);
tcase_add_test(tc_core, test_tcp_fin_wait_2_timeout_start_heap_full_leaves_flag_clear);
tcase_add_test(tc_core, test_tcp_preaccept_timeout_start_heap_full_leaves_flag_clear);
tcase_add_test(tc_core, test_sock_connect_tcp_heap_full_does_not_pin_syn_sent);
tcase_add_test(tc_core, test_sock_connect_tcp_heap_full_drops_queued_syn);
tcase_add_test(tc_core, test_sock_accept_heap_full_keeps_listener_readable);
tcase_add_test(tc_core, test_tcp_ack_duplicate_zero_inflight_early_return);
tcase_add_test(tc_core, test_tcp_ack_duplicate_ack_ne_snd_una_returns);
tcase_add_test(tc_core, test_tcp_ack_fourth_dupack_inflates_cwnd);
Expand Down Expand Up @@ -1449,7 +1461,7 @@ Suite *wolf_suite(void)
#ifdef IP_MULTICAST
tcase_add_test(tc_core, test_poll_tx_udp_multicast_arp_skipped_uses_mcast_mac);
#endif /* IP_MULTICAST */
/* --- unit_tests_dhcp_edges.c (52 tests) --- */
/* --- unit_tests_dhcp_edges.c (53 tests) --- */
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_zero_lease_noop);
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_null_noop);
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_renew_gt_lease_clamped);
Expand All @@ -1458,6 +1470,7 @@ Suite *wolf_suite(void)
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_rebind_gt_lease_clamped);
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_explicit_t1_t2);
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_t1_t2_equal_lease_resets_defaults);
tcase_add_test(tc_core, test_dhcp_schedule_lease_timer_heap_full_rearmed_on_poll);
tcase_add_test(tc_core, test_dhcp_msg_type_returns_offer);
tcase_add_test(tc_core, test_dhcp_msg_type_returns_nak);
tcase_add_test(tc_core, test_dhcp_msg_type_returns_ack);
Expand Down
86 changes: 86 additions & 0 deletions src/test/unit/unit_tests_api.c
Original file line number Diff line number Diff line change
Expand Up @@ -1533,6 +1533,39 @@ START_TEST(test_sock_bind_tcp_port_collision_rejected)
}
END_TEST

/* A TCP socket explicitly bound to a port below 1024 keeps that source port
* across connect. */
START_TEST(test_sock_connect_tcp_keeps_bound_low_port)
{
struct wolfIP s;
int tcp_sd;
struct tsocket *ts;
struct wolfIP_sockaddr_in sin;

wolfIP_init(&s);
mock_link_init(&s);
wolfIP_ipconfig_set(&s, 0x0A000001U, 0xFFFFFF00U, 0);

tcp_sd = wolfIP_sock_socket(&s, AF_INET, IPSTACK_SOCK_STREAM, WI_IPPROTO_TCP);
ck_assert_int_gt(tcp_sd, 0);
ts = &s.tcpsockets[SOCKET_UNMARK(tcp_sd)];

memset(&sin, 0, sizeof(sin));
sin.sin_family = AF_INET;
sin.sin_port = ee16(20);
sin.sin_addr.s_addr = ee32(0x0A000001U);
ck_assert_int_eq(wolfIP_sock_bind(&s, tcp_sd,
(struct wolfIP_sockaddr *)&sin, sizeof(sin)), 0);

sin.sin_port = ee16(5001);
sin.sin_addr.s_addr = ee32(0x0A000002U);
ck_assert_int_eq(wolfIP_sock_connect(&s, tcp_sd,
(struct wolfIP_sockaddr *)&sin, sizeof(sin)), -WOLFIP_EAGAIN);

ck_assert_uint_eq(ts->src_port, 20);
}
END_TEST

START_TEST(test_sock_bind_udp_src_port_nonzero)
{
struct wolfIP s;
Expand Down Expand Up @@ -2844,6 +2877,59 @@ START_TEST(test_sock_accept_listener_resets_paws_state)
}
END_TEST

/* A RST that reverts a half-open listener to LISTEN clears the aborted peer's
* PAWS state, so the next connection seeds a fresh TS.Recent. */
START_TEST(test_syn_rcvd_rst_listener_resets_paws_state)
{
struct wolfIP s;
int listen_sd;
struct tsocket *listener;
struct wolfIP_sockaddr_in sin;

wolfIP_init(&s);
mock_link_init(&s);
wolfIP_ipconfig_set(&s, 0x0A000001U, 0xFFFFFF00U, 0);

listen_sd = wolfIP_sock_socket(&s, AF_INET, IPSTACK_SOCK_STREAM, WI_IPPROTO_TCP);
ck_assert_int_gt(listen_sd, 0);
memset(&sin, 0, sizeof(sin));
sin.sin_family = AF_INET;
sin.sin_port = ee16(1234);
sin.sin_addr.s_addr = ee32(0x0A000001U);
ck_assert_int_eq(wolfIP_sock_bind(&s, listen_sd, (struct wolfIP_sockaddr *)&sin, sizeof(sin)), 0);
ck_assert_int_eq(wolfIP_sock_listen(&s, listen_sd, 1), 0);

listener = &s.tcpsockets[SOCKET_UNMARK(listen_sd)];

/* Connection 1: the timestamped SYN seeds the half-open listener's
* TS.Recent (last_ts/ts_recent_valid) and enables PAWS. */
inject_tcp_syn_ts(&s, TEST_PRIMARY_IF, 0x0A0000A1U, 0x0A000001U, 1234,
0x10000000U);
ck_assert_int_eq(listener->sock.tcp.state, TCP_SYN_RCVD);
ck_assert_uint_eq(listener->sock.tcp.ts_enabled, 1);
ck_assert_uint_eq(listener->sock.tcp.last_ts, ee32(0x10000000U));
ck_assert_uint_eq(listener->sock.tcp.ts_recent_valid, 1);

/* Connection 1 is aborted in-sequence: the listener goes back to LISTEN
* and must be at the same fresh baseline the accept() revert leaves. */
inject_tcp_segment(&s, TEST_PRIMARY_IF, 0x0A0000A1U, 0x0A000001U,
40000, 1234, listener->sock.tcp.ack, 0, TCP_FLAG_RST);
ck_assert_int_eq(listener->sock.tcp.state, TCP_LISTEN);
ck_assert_uint_eq(listener->sock.tcp.ts_enabled, 0);
ck_assert_uint_eq(listener->sock.tcp.ts_recent_valid, 0);
ck_assert_uint_eq(listener->sock.tcp.last_ts, 0U);

/* Connection 2, from a client with a lower timestamp epoch, must seed
* a fresh TS.Recent instead of inheriting connection 1's. */
inject_tcp_syn_ts(&s, TEST_PRIMARY_IF, 0x0A0000A2U, 0x0A000001U, 1234,
100U);
ck_assert_int_eq(listener->sock.tcp.state, TCP_SYN_RCVD);
ck_assert_uint_eq(listener->sock.tcp.ts_enabled, 1);
ck_assert_uint_eq(listener->sock.tcp.last_ts, ee32(100U));
ck_assert_uint_eq(listener->sock.tcp.ts_recent_valid, 1);
}
END_TEST

START_TEST(test_sock_accept_no_available_socket)
{
struct wolfIP s;
Expand Down
32 changes: 32 additions & 0 deletions src/test/unit/unit_tests_dhcp_edges.c
Original file line number Diff line number Diff line change
Expand Up @@ -219,6 +219,38 @@ START_TEST(test_dhcp_schedule_lease_timer_explicit_t1_t2)
}
END_TEST

/* A lease whose renewal timer could not be armed is re-armed by the poll loop once a slot frees. */
START_TEST(test_dhcp_schedule_lease_timer_heap_full_rearmed_on_poll)
{
struct wolfIP s;
struct wolfIP_timer t = {0};
uint32_t filler[MAX_TIMERS];
int i;

wolfIP_init(&s);
mock_link_init(&s);
s.last_tick = 1000U;
s.dhcp_state = DHCP_BOUND;

/* Fill the timer heap so the renewal insert fails. */
for (i = 0; i < MAX_TIMERS; i++) {
t.expires = s.last_tick + 1000U + (uint64_t)i;
t.arg = NULL;
t.cb = NULL;
filler[i] = (uint32_t)timers_binheap_insert(&s.timers, t);
}

dhcp_schedule_lease_timer(&s, 3600U, 1800U, 3150U);
ck_assert_int_eq(s.dhcp_timer, NO_TIMER);

timer_binheap_cancel(&s.timers, filler[0]);
(void)wolfIP_poll(&s, s.last_tick);

ck_assert_int_ne(s.dhcp_timer, NO_TIMER);
ck_assert_uint_eq(find_timer_expiry(&s, s.dhcp_timer), s.dhcp_renew_at);
}
END_TEST

/* -------------------------------------------------------------------------
* dhcp_msg_type — return each message type and validate
* ---------------------------------------------------------------------- */
Expand Down
2 changes: 1 addition & 1 deletion src/test/unit/unit_tests_dns_dhcp.c
Original file line number Diff line number Diff line change
Expand Up @@ -1373,7 +1373,7 @@ START_TEST(test_sock_connect_tcp_src_port_low)
sin.sin_addr.s_addr = ee32(0x0A000002U);

ck_assert_int_eq(wolfIP_sock_connect(&s, tcp_sd, (struct wolfIP_sockaddr *)&sin, sizeof(sin)), -WOLFIP_EAGAIN);
ck_assert_uint_eq(ts->src_port, 1025);
ck_assert_uint_eq(ts->src_port, 1);
}
END_TEST

Expand Down
Loading
Loading