From 00096a3433b96dfd8ef7cc1d5feadaf190b65616 Mon Sep 17 00:00:00 2001 From: xueyunfei Date: Mon, 17 Apr 2023 19:55:50 +0800 Subject: [PATCH] lwip: Add security fixes and other features and bufixes to v4.2 * Update submodule: git log --oneline 2195f7416fb3136831babf3e96c027a73075bd4f..6bb132e3797d5449a923804c75c57d458920f8ac Detailed description of the changes: - tcp_in/ooseq: Fix incorrect segment trim when FIN moved (espressif/esp-lwip@6bb132e3) - api_msg: fix tcp_abort thread safety (2.1.2-esp) (espressif/esp-lwip@53a6e019) - lwip:optimization dhcp coarse timer (espressif/esp-lwip@a7abf28e) - napt: Fix ip_portmap_add() to keep only one port mapping (espressif/esp-lwip@abab9fef) - reduce the DHCP Request timeout (espressif/esp-lwip@6fa02bd3) - lwip timer:optimization dhcp fine timer (espressif/esp-lwip@79182163) - optimization lwip ip4 reassembly timer (espressif/esp-lwip@17f41c9f) - optimization lwip ip6 reassembly timer (espressif/esp-lwip@c943fc5a) - optimization lwip dns timer (espressif/esp-lwip@7f5ab42c) - napt: Fix clean compilation (espressif/esp-lwip@6132c975) - Lwip:add TCP Fin2 timeout configuration (espressif/esp-lwip@15b4400e) - napt: Fix IP forwarding when forward netif enable NAPT (espressif/esp-lwip@c950063f) - napt/stats: Move some napt counters to stats module (espressif/esp-lwip@475d658a) - ip_napt_maint: Fix timestamp overflow handling (espressif/esp-lwip@2e904508) - napt: Fixes and improvements (espressif/esp-lwip@fb1f3552) - test/napt: Add unit test for IP forward with PBUF_REF (espressif/esp-lwip@76303df2) - napt: Fix PBUF_REF type to clone the pbuf before forwarding (espressif/esp-lwip@39068263) - version: Update version numbers to match 2.1.2-esp (espressif/esp-lwip@2b922919) - pppos: fix in_tail null (espressif/esp-lwip@537c69d5) - PPP: Add test exhibiting empty packet null-deref (espressif/esp-lwip@202a07da) - pbuf: Add pbuf_copy_partial_pbuf library function (espressif/esp-lwip@1c9cd9c1) - Add #define for minimum IPv6 MTU length (espressif/esp-lwip@d2dc577b) - zepif: Copy possibly chained output pbuf properly (espressif/esp-lwip@64ab7f2a) - icmp6: Don't copy too much data (espressif/esp-lwip@4a64731b) - icmp6: Fix copying of chained pbuf in reply (espressif/esp-lwip@7c822ff4) - icmp6: keep to the RFC and send as much as possible with icmp6 error messages (espressif/esp-lwip@29100ab6) - dns: Add API to clear dns cache (espressif/esp-lwip@ee59f77d) - CI: Fixed adding gitlab key (espressif/esp-lwip@5a2bdba7) - test case: modify test case test_tcp_new_max_num_remove_FIN_WAIT_1 (espressif/esp-lwip@6b090f7d) - add function for deinit lwip timers (espressif/esp-lwip@2749568f) - dhcp: Fix build issue that set ESP_DHCP_DISABLE_VENDOR_CLASS_IDENTIFIER to true will build fail (espressif/esp-lwip@d827dbf7) - Document that sntp_setservername doesn't copy the string (espressif/esp-lwip@54acdb59) - Closes https://github.com/espressif/esp-idf/issues/6786 - lwip/dhcp: add 60 option for vendor class identify (espressif/esp-lwip@ae7edc2a) - Closes https://github.com/espressif/esp-lwip/issues/32 - dhcp: Restore dhcp_cb on restart after dhcp_release_and_stop() (espressif/esp-lwip@55ea9d9c) - Closes https://github.com/espressif/esp-idf/issues/7217 - napt: Fix disbale IPv6 and enable NAPT will build error (espressif/esp-lwip@74cf7f9f) - napt: fix checksum of UDP (espressif/esp-lwip@bb63eed1) - sntp: Fix client receive KOD packet that make pool MEMP_SYS_TIMEOUT not be freed (espressif/esp-lwip@1c1642fe) - test case: add tcp state and reset test cases. (espressif/esp-lwip@67deb805) --- components/lwip/Kconfig | 16 ++++- components/lwip/lwip | 2 +- components/lwip/port/esp32/include/lwipopts.h | 58 +++++++++++++++++++ .../lwip/test_afl_host/sdkconfig.defaults | 1 + docs/en/api-guides/lwip.rst | 1 + 5 files changed, 76 insertions(+), 2 deletions(-) create mode 100644 components/lwip/test_afl_host/sdkconfig.defaults diff --git a/components/lwip/Kconfig b/components/lwip/Kconfig index 8b9ac25e47..b824964d11 100644 --- a/components/lwip/Kconfig +++ b/components/lwip/Kconfig @@ -245,6 +245,14 @@ menu "LWIP" server. Last valid DHCP configuration is stored in nvs and restored after reset/power-up. If IP is still available, there is no need for sending discovery message to DHCP server and save some time. + config LWIP_DHCP_COARSE_TIMER_SECS + int "DHCP coarse timer interval(s)" + default 1 + range 1 10 + help + Set DHCP coarse interval in seconds. + A higher value will be less precise but cost less power consumption. + menu "DHCP server" config LWIP_DHCPS_LEASE_UNIT @@ -420,7 +428,13 @@ menu "LWIP" int "Maximum segment lifetime (MSL)" default 60000 help - Set maximum segment lifetime in in milliseconds. + Set maximum segment lifetime in milliseconds. + + config LWIP_TCP_FIN_WAIT_TIMEOUT + int "Maximum FIN segment lifetime" + default 20000 + help + Set maximum segment lifetime in milliseconds. config LWIP_TCP_SND_BUF_DEFAULT int "Default send buffer size" diff --git a/components/lwip/lwip b/components/lwip/lwip index 2195f7416f..6bb132e379 160000 --- a/components/lwip/lwip +++ b/components/lwip/lwip @@ -1 +1 @@ -Subproject commit 2195f7416fb3136831babf3e96c027a73075bd4f +Subproject commit 6bb132e3797d5449a923804c75c57d458920f8ac diff --git a/components/lwip/port/esp32/include/lwipopts.h b/components/lwip/port/esp32/include/lwipopts.h index 5ab47c4165..103b731bed 100644 --- a/components/lwip/port/esp32/include/lwipopts.h +++ b/components/lwip/port/esp32/include/lwipopts.h @@ -46,6 +46,12 @@ #include "sntp.h" #include "netif/dhcp_state.h" +#ifdef __cplusplus +extern "C" +{ +#endif + + /* Enable all Espressif-only options */ /* @@ -255,6 +261,33 @@ */ #define ESP_DHCP_DISABLE_CLIENT_ID CONFIG_LWIP_DHCP_DISABLE_CLIENT_ID +#define DHCP_DEFINE_CUSTOM_TIMEOUTS 1 +/* Since for embedded devices it's not that hard to miss a discover packet, so lower + * the discover retry backoff time from (2,4,8,16,32,60,60)s to (500m,1,2,4,8,15,15)s. + */ + #define DHCP_REQUEST_TIMEOUT_SEQUENCE(state, tries) (state == DHCP_STATE_REQUESTING ? \ + (uint16_t)(1 * 1000) : \ + (uint16_t)(((tries) < 6 ? 1 << (tries) : 60) * 250)) + +#define DHCP_COARSE_TIMER_SECS CONFIG_LWIP_DHCP_COARSE_TIMER_SECS + +static inline uint32_t timeout_from_offered(uint32_t lease, uint32_t min) +{ + uint32_t timeout = lease; + if (timeout == 0) { + timeout = min; + } + timeout = (timeout + DHCP_COARSE_TIMER_SECS - 1) / DHCP_COARSE_TIMER_SECS; + return timeout; +} + +#define DHCP_CALC_TIMEOUT_FROM_OFFERED_T0_LEASE(dhcp) \ + timeout_from_offered((dhcp)->offered_t0_lease, 120) +#define DHCP_CALC_TIMEOUT_FROM_OFFERED_T1_RENEW(dhcp) \ + timeout_from_offered((dhcp)->offered_t1_renew, (dhcp)->t0_timeout >> 1 /* 50% */) +#define DHCP_CALC_TIMEOUT_FROM_OFFERED_T2_REBIND(dhcp) \ + timeout_from_offered((dhcp)->offered_t2_rebind, ((dhcp)->t0_timeout / 8) * 7 /* 87.5% */) + /** * CONFIG_LWIP_DHCP_RESTORE_LAST_IP==1: Last valid IP address obtained from DHCP server * is restored after reset/power-up. @@ -367,6 +400,11 @@ */ #define TCP_MSS CONFIG_LWIP_TCP_MSS +/** + * TCP_FIN_WAIT_TIMEOUT: The maximum FIN segment lifetime in milliseconds + */ +#define TCP_FIN_WAIT_TIMEOUT CONFIG_LWIP_TCP_FIN_WAIT_TIMEOUT + /** * TCP_TMR_INTERVAL: TCP timer interval */ @@ -899,9 +937,25 @@ u32_t lwip_hook_tcp_isn(const struct ip_addr *local_ip, u16_t local_port, #ifdef CONFIG_LWIP_TIMERS_ONDEMAND #define ESP_LWIP_IGMP_TIMERS_ONDEMAND 1 #define ESP_LWIP_MLD6_TIMERS_ONDEMAND 1 +#define ESP_LWIP_DHCP_FINE_TIMERS_ONDEMAND 1 +#define ESP_LWIP_DNS_TIMERS_ONDEMAND 1 +#if IP_REASSEMBLY +#define ESP_LWIP_IP4_REASSEMBLY_TIMERS_ONDEMAND 1 +#endif /* IP_REASSEMBLY */ +#if LWIP_IPV6_REASS +#define ESP_LWIP_IP6_REASSEMBLY_TIMERS_ONDEMAND 1 +#endif /* LWIP_IPV6_REASS */ #else #define ESP_LWIP_IGMP_TIMERS_ONDEMAND 0 #define ESP_LWIP_MLD6_TIMERS_ONDEMAND 0 +#define ESP_LWIP_DHCP_FINE_TIMERS_ONDEMAND 0 +#define ESP_LWIP_DNS_TIMERS_ONDEMAND 0 +#if IP_REASSEMBLY +#define ESP_LWIP_IP4_REASSEMBLY_TIMERS_ONDEMAND 0 +#endif /* IP_REASSEMBLY */ +#if LWIP_IPV6_REASS +#define ESP_LWIP_IP6_REASSEMBLY_TIMERS_ONDEMAND 0 +#endif /* LWIP_IPV6_REASS */ #endif #define TCP_SND_BUF CONFIG_LWIP_TCP_SND_BUF_DEFAULT @@ -960,4 +1014,8 @@ u32_t lwip_hook_tcp_isn(const struct ip_addr *local_ip, u16_t local_port, #define SOC_SEND_LOG //printf +#ifdef __cplusplus +} +#endif + #endif /* __LWIPOPTS_H__ */ diff --git a/components/lwip/test_afl_host/sdkconfig.defaults b/components/lwip/test_afl_host/sdkconfig.defaults new file mode 100644 index 0000000000..4f0658f2b8 --- /dev/null +++ b/components/lwip/test_afl_host/sdkconfig.defaults @@ -0,0 +1 @@ +CONFIG_LWIP_TIMERS_ONDEMAND=n diff --git a/docs/en/api-guides/lwip.rst b/docs/en/api-guides/lwip.rst index 641376010c..a26e137df5 100644 --- a/docs/en/api-guides/lwip.rst +++ b/docs/en/api-guides/lwip.rst @@ -374,6 +374,7 @@ Most lwIP RAM usage is on-demand, as RAM is allocated from the heap as needed. T - Reducing :ref:`CONFIG_LWIP_MAX_SOCKETS` reduces the maximum number of sockets in the system. This will also cause TCP sockets in the ``WAIT_CLOSE`` state to be closed and recycled more rapidly (if needed to open a new socket), further reducing peak RAM usage. - Reducing :ref:`CONFIG_LWIP_TCPIP_RECVMBOX_SIZE`, :ref:`CONFIG_LWIP_TCP_RECVMBOX_SIZE` and :ref:`CONFIG_LWIP_UDP_RECVMBOX_SIZE` reduce memory usage at the expense of throughput, depending on usage. +- Reducing :ref:`CONFIG_LWIP_TCP_MSL`, :ref:`CONFIG_LWIP_TCP_FIN_WAIT_TIMEOUT` reduces the maximum segment lifetime in the system. This will also cause TCP sockets in the ``TIME_WAIT``, ``FIN_WAIT_2`` state to be closed and recycled more rapidly If using Wi-Fi, please also refer to :ref:`wifi-buffer-usage`.