1195972f6Sopenharmony_ci/** 2195972f6Sopenharmony_ci * @defgroup lwip lwIP 3195972f6Sopenharmony_ci * 4195972f6Sopenharmony_ci * @defgroup infrastructure Infrastructure 5195972f6Sopenharmony_ci * 6195972f6Sopenharmony_ci * @defgroup api APIs 7195972f6Sopenharmony_ci * lwIP provides three Application Program's Interfaces (APIs) for programs 8195972f6Sopenharmony_ci * to use for communication with the TCP/IP code: 9195972f6Sopenharmony_ci * - low-level "core" / "callback" or @ref callbackstyle_api. 10195972f6Sopenharmony_ci * - higher-level @ref sequential_api. 11195972f6Sopenharmony_ci * - BSD-style @ref socket. 12195972f6Sopenharmony_ci * 13195972f6Sopenharmony_ci * The raw TCP/IP interface allows the application program to integrate 14195972f6Sopenharmony_ci * better with the TCP/IP code. Program execution is event based by 15195972f6Sopenharmony_ci * having callback functions being called from within the TCP/IP 16195972f6Sopenharmony_ci * code. The TCP/IP code and the application program both run in the same 17195972f6Sopenharmony_ci * thread. The sequential API has a much higher overhead and is not very 18195972f6Sopenharmony_ci * well suited for small systems since it forces a multithreaded paradigm 19195972f6Sopenharmony_ci * on the application. 20195972f6Sopenharmony_ci * 21195972f6Sopenharmony_ci * The raw TCP/IP interface is not only faster in terms of code execution 22195972f6Sopenharmony_ci * time but is also less memory intensive. The drawback is that program 23195972f6Sopenharmony_ci * development is somewhat harder and application programs written for 24195972f6Sopenharmony_ci * the raw TCP/IP interface are more difficult to understand. Still, this 25195972f6Sopenharmony_ci * is the preferred way of writing applications that should be small in 26195972f6Sopenharmony_ci * code size and memory usage. 27195972f6Sopenharmony_ci * 28195972f6Sopenharmony_ci * All APIs can be used simultaneously by different application 29195972f6Sopenharmony_ci * programs. In fact, the sequential API is implemented as an application 30195972f6Sopenharmony_ci * program using the raw TCP/IP interface. 31195972f6Sopenharmony_ci * 32195972f6Sopenharmony_ci * Do not confuse the lwIP raw API with raw Ethernet or IP sockets. 33195972f6Sopenharmony_ci * The former is a way of interfacing the lwIP network stack (including 34195972f6Sopenharmony_ci * TCP and UDP), the latter refers to processing raw Ethernet or IP data 35195972f6Sopenharmony_ci * instead of TCP connections or UDP packets. 36195972f6Sopenharmony_ci * 37195972f6Sopenharmony_ci * Raw API applications may never block since all packet processing 38195972f6Sopenharmony_ci * (input and output) as well as timer processing (TCP mainly) is done 39195972f6Sopenharmony_ci * in a single execution context. 40195972f6Sopenharmony_ci * 41195972f6Sopenharmony_ci * @defgroup callbackstyle_api "raw" APIs 42195972f6Sopenharmony_ci * @ingroup api 43195972f6Sopenharmony_ci * Non thread-safe APIs, callback style for maximum performance and minimum 44195972f6Sopenharmony_ci * memory footprint. 45195972f6Sopenharmony_ci * Program execution is driven by callbacks functions, which are then 46195972f6Sopenharmony_ci * invoked by the lwIP core when activity related to that application 47195972f6Sopenharmony_ci * occurs. A particular application may register to be notified via a 48195972f6Sopenharmony_ci * callback function for events such as incoming data available, outgoing 49195972f6Sopenharmony_ci * data sent, error notifications, poll timer expiration, connection 50195972f6Sopenharmony_ci * closed, etc. An application can provide a callback function to perform 51195972f6Sopenharmony_ci * processing for any or all of these events. Each callback is an ordinary 52195972f6Sopenharmony_ci * C function that is called from within the TCP/IP code. Every callback 53195972f6Sopenharmony_ci * function is passed the current TCP or UDP connection state as an 54195972f6Sopenharmony_ci * argument. Also, in order to be able to keep program specific state, 55195972f6Sopenharmony_ci * the callback functions are called with a program specified argument 56195972f6Sopenharmony_ci * that is independent of the TCP/IP state. 57195972f6Sopenharmony_ci * The raw API (sometimes called native API) is an event-driven API designed 58195972f6Sopenharmony_ci * to be used without an operating system that implements zero-copy send and 59195972f6Sopenharmony_ci * receive. This API is also used by the core stack for interaction between 60195972f6Sopenharmony_ci * the various protocols. It is the only API available when running lwIP 61195972f6Sopenharmony_ci * without an operating system. 62195972f6Sopenharmony_ci * 63195972f6Sopenharmony_ci * @defgroup sequential_api Sequential-style APIs 64195972f6Sopenharmony_ci * @ingroup api 65195972f6Sopenharmony_ci * Sequential-style APIs, blocking functions. More overhead, but can be called 66195972f6Sopenharmony_ci * from any thread except TCPIP thread. 67195972f6Sopenharmony_ci * The sequential API provides a way for ordinary, sequential, programs 68195972f6Sopenharmony_ci * to use the lwIP stack. It is quite similar to the BSD socket API. The 69195972f6Sopenharmony_ci * model of execution is based on the blocking open-read-write-close 70195972f6Sopenharmony_ci * paradigm. Since the TCP/IP stack is event based by nature, the TCP/IP 71195972f6Sopenharmony_ci * code and the application program must reside in different execution 72195972f6Sopenharmony_ci * contexts (threads). 73195972f6Sopenharmony_ci * 74195972f6Sopenharmony_ci * @defgroup socket Socket API 75195972f6Sopenharmony_ci * @ingroup api 76195972f6Sopenharmony_ci * BSD-style socket API.\n 77195972f6Sopenharmony_ci * Thread-safe, to be called from non-TCPIP threads only.\n 78195972f6Sopenharmony_ci * Can be activated by defining @ref LWIP_SOCKET to 1.\n 79195972f6Sopenharmony_ci * Header is in posix/sys/socket.h\n 80195972f6Sopenharmony_ci * The socket API is a compatibility API for existing applications, 81195972f6Sopenharmony_ci * currently it is built on top of the sequential API. It is meant to 82195972f6Sopenharmony_ci * provide all functions needed to run socket API applications running 83195972f6Sopenharmony_ci * on other platforms (e.g. unix / windows etc.). However, due to limitations 84195972f6Sopenharmony_ci * in the specification of this API, there might be incompatibilities 85195972f6Sopenharmony_ci * that require small modifications of existing programs. 86195972f6Sopenharmony_ci * 87195972f6Sopenharmony_ci * @defgroup netifs NETIFs 88195972f6Sopenharmony_ci * 89195972f6Sopenharmony_ci * @defgroup apps Applications 90195972f6Sopenharmony_ci */ 91195972f6Sopenharmony_ci 92195972f6Sopenharmony_ci/** 93195972f6Sopenharmony_ci * @mainpage Overview 94195972f6Sopenharmony_ci * @verbinclude "README" 95195972f6Sopenharmony_ci */ 96195972f6Sopenharmony_ci 97195972f6Sopenharmony_ci/** 98195972f6Sopenharmony_ci * @page upgrading Upgrading 99195972f6Sopenharmony_ci * @verbinclude "UPGRADING" 100195972f6Sopenharmony_ci */ 101195972f6Sopenharmony_ci 102195972f6Sopenharmony_ci/** 103195972f6Sopenharmony_ci * @page changelog Changelog 104195972f6Sopenharmony_ci * 105195972f6Sopenharmony_ci * 2.1.0 106195972f6Sopenharmony_ci * ----- 107195972f6Sopenharmony_ci * * Support TLS via new @ref altcp_api connection API (https, smtps, mqtt over TLS) 108195972f6Sopenharmony_ci * * Switch to cmake as the main build system (Makefile file lists are still 109195972f6Sopenharmony_ci * maintained for now) 110195972f6Sopenharmony_ci * * Improve IPv6 support: support address scopes, support stateless DHCPv6, bugfixes 111195972f6Sopenharmony_ci * * Add debug helper asserts to ensure threading/locking requirements are met 112195972f6Sopenharmony_ci * * Add sys_mbox_trypost_fromisr() and tcpip_callbackmsg_trycallback_fromisr() 113195972f6Sopenharmony_ci * (for FreeRTOS, mainly) 114195972f6Sopenharmony_ci * * socket API: support poll(), sendmsg() and recvmsg(); fix problems on close 115195972f6Sopenharmony_ci * 116195972f6Sopenharmony_ci * Detailed Changelog 117195972f6Sopenharmony_ci * ------------------ 118195972f6Sopenharmony_ci * @verbinclude "CHANGELOG" 119195972f6Sopenharmony_ci */ 120195972f6Sopenharmony_ci 121195972f6Sopenharmony_ci/** 122195972f6Sopenharmony_ci * @page contrib How to contribute to lwIP 123195972f6Sopenharmony_ci * @verbinclude "contrib.txt" 124195972f6Sopenharmony_ci */ 125195972f6Sopenharmony_ci 126195972f6Sopenharmony_ci/** 127195972f6Sopenharmony_ci * @page pitfalls Common pitfalls 128195972f6Sopenharmony_ci * 129195972f6Sopenharmony_ci * Multiple Execution Contexts in lwIP code 130195972f6Sopenharmony_ci * ======================================== 131195972f6Sopenharmony_ci * 132195972f6Sopenharmony_ci * The most common source of lwIP problems is to have multiple execution contexts 133195972f6Sopenharmony_ci * inside the lwIP code. 134195972f6Sopenharmony_ci * 135195972f6Sopenharmony_ci * lwIP can be used in two basic modes: @ref lwip_nosys (no OS/RTOS 136195972f6Sopenharmony_ci * running on target system) or @ref lwip_os (there is an OS running 137195972f6Sopenharmony_ci * on the target system). 138195972f6Sopenharmony_ci * 139195972f6Sopenharmony_ci * See also: @ref multithreading (especially the part about @ref LWIP_ASSERT_CORE_LOCKED()!) 140195972f6Sopenharmony_ci * 141195972f6Sopenharmony_ci * Mainloop Mode 142195972f6Sopenharmony_ci * ------------- 143195972f6Sopenharmony_ci * In mainloop mode, only @ref callbackstyle_api can be used. 144195972f6Sopenharmony_ci * The user has two possibilities to ensure there is only one 145195972f6Sopenharmony_ci * exection context at a time in lwIP: 146195972f6Sopenharmony_ci * 147195972f6Sopenharmony_ci * 1) Deliver RX ethernet packets directly in interrupt context to lwIP 148195972f6Sopenharmony_ci * by calling netif->input directly in interrupt. This implies all lwIP 149195972f6Sopenharmony_ci * callback functions are called in IRQ context, which may cause further 150195972f6Sopenharmony_ci * problems in application code: IRQ is blocked for a long time, multiple 151195972f6Sopenharmony_ci * execution contexts in application code etc. When the application wants 152195972f6Sopenharmony_ci * to call lwIP, it only needs to disable interrupts during the call. 153195972f6Sopenharmony_ci * If timers are involved, even more locking code is needed to lock out 154195972f6Sopenharmony_ci * timer IRQ and ethernet IRQ from each other, assuming these may be nested. 155195972f6Sopenharmony_ci * 156195972f6Sopenharmony_ci * 2) Run lwIP in a mainloop. There is example code here: @ref lwip_nosys. 157195972f6Sopenharmony_ci * lwIP is _ONLY_ called from mainloop callstacks here. The ethernet IRQ 158195972f6Sopenharmony_ci * has to put received telegrams into a queue which is polled in the 159195972f6Sopenharmony_ci * mainloop. Ensure lwIP is _NEVER_ called from an interrupt, e.g. 160195972f6Sopenharmony_ci * some SPI IRQ wants to forward data to udp_send() or tcp_write()! 161195972f6Sopenharmony_ci * 162195972f6Sopenharmony_ci * OS Mode 163195972f6Sopenharmony_ci * ------- 164195972f6Sopenharmony_ci * In OS mode, @ref callbackstyle_api AND @ref sequential_api can be used. 165195972f6Sopenharmony_ci * @ref sequential_api are designed to be called from threads other than 166195972f6Sopenharmony_ci * the TCPIP thread, so there is nothing to consider here. 167195972f6Sopenharmony_ci * But @ref callbackstyle_api functions must _ONLY_ be called from 168195972f6Sopenharmony_ci * TCPIP thread. It is a common error to call these from other threads 169195972f6Sopenharmony_ci * or from IRQ contexts. Ethernet RX needs to deliver incoming packets 170195972f6Sopenharmony_ci * in the correct way by sending a message to TCPIP thread, this is 171195972f6Sopenharmony_ci * implemented in tcpip_input(). 172195972f6Sopenharmony_ci * Again, ensure lwIP is _NEVER_ called from an interrupt, e.g. 173195972f6Sopenharmony_ci * some SPI IRQ wants to forward data to udp_send() or tcp_write()! 174195972f6Sopenharmony_ci * 175195972f6Sopenharmony_ci * 1) tcpip_callback() can be used get called back from TCPIP thread, 176195972f6Sopenharmony_ci * it is safe to call any @ref callbackstyle_api from there. 177195972f6Sopenharmony_ci * 178195972f6Sopenharmony_ci * 2) Use @ref LWIP_TCPIP_CORE_LOCKING. All @ref callbackstyle_api 179195972f6Sopenharmony_ci * functions can be called when lwIP core lock is aquired, see 180195972f6Sopenharmony_ci * @ref LOCK_TCPIP_CORE() and @ref UNLOCK_TCPIP_CORE(). 181195972f6Sopenharmony_ci * These macros cannot be used in an interrupt context! 182195972f6Sopenharmony_ci * Note the OS must correctly handle priority inversion for this. 183195972f6Sopenharmony_ci * 184195972f6Sopenharmony_ci * Cache / DMA issues 185195972f6Sopenharmony_ci * ================== 186195972f6Sopenharmony_ci * 187195972f6Sopenharmony_ci * DMA-capable ethernet hardware and zero-copy RX 188195972f6Sopenharmony_ci * ---------------------------------------------- 189195972f6Sopenharmony_ci * 190195972f6Sopenharmony_ci * lwIP changes the content of RECEIVED pbufs in the TCP code path. 191195972f6Sopenharmony_ci * This implies one or more cacheline(s) of the RX pbuf become dirty 192195972f6Sopenharmony_ci * and need to be flushed before the memory is handed over to the 193195972f6Sopenharmony_ci * DMA ethernet hardware for the next telegram to be received. 194195972f6Sopenharmony_ci * See http://lists.nongnu.org/archive/html/lwip-devel/2017-12/msg00070.html 195195972f6Sopenharmony_ci * for a more detailed explanation. 196195972f6Sopenharmony_ci * Also keep in mind the user application may also write into pbufs, 197195972f6Sopenharmony_ci * so it is generally a bug not to flush the data cache before handing 198195972f6Sopenharmony_ci * a buffer to DMA hardware. 199195972f6Sopenharmony_ci * 200195972f6Sopenharmony_ci * DMA-capable ethernet hardware and cacheline alignment 201195972f6Sopenharmony_ci * ----------------------------------------------------- 202195972f6Sopenharmony_ci * Nice description about DMA capable hardware and buffer handling: 203195972f6Sopenharmony_ci * http://www.pebblebay.com/a-guide-to-using-direct-memory-access-in-embedded-systems-part-two/ 204195972f6Sopenharmony_ci * Read especially sections "Cache coherency" and "Buffer alignment". 205195972f6Sopenharmony_ci */ 206195972f6Sopenharmony_ci 207195972f6Sopenharmony_ci/** 208195972f6Sopenharmony_ci * @page mem_err Debugging memory pool sizes 209195972f6Sopenharmony_ci * If you have issues with lwIP and you are using memory pools, check that your pools 210195972f6Sopenharmony_ci * are correctly sized.\n 211195972f6Sopenharmony_ci * To debug pool sizes, \#define LWIP_STATS and MEMP_STATS to 1. Check the global variable 212195972f6Sopenharmony_ci * lwip_stats.memp[] using a debugger. If the "err" member of a pool is > 0, the pool 213195972f6Sopenharmony_ci * may be too small for your application and you need to increase its size. 214195972f6Sopenharmony_ci */ 215195972f6Sopenharmony_ci 216195972f6Sopenharmony_ci/** 217195972f6Sopenharmony_ci * @page bugs Reporting bugs 218195972f6Sopenharmony_ci * Please report bugs in the lwIP bug tracker at savannah.\n 219195972f6Sopenharmony_ci * BEFORE submitting, please check if the bug has already been reported!\n 220195972f6Sopenharmony_ci * https://savannah.nongnu.org/bugs/?group=lwip 221195972f6Sopenharmony_ci */ 222195972f6Sopenharmony_ci 223195972f6Sopenharmony_ci/** 224195972f6Sopenharmony_ci * @page zerocopyrx Zero-copy RX 225195972f6Sopenharmony_ci * The following code is an example for zero-copy RX ethernet driver: 226195972f6Sopenharmony_ci * @include ZeroCopyRx.c 227195972f6Sopenharmony_ci */ 228195972f6Sopenharmony_ci 229195972f6Sopenharmony_ci/** 230195972f6Sopenharmony_ci * @defgroup lwip_nosys Mainloop mode ("NO_SYS") 231195972f6Sopenharmony_ci * @ingroup lwip 232195972f6Sopenharmony_ci * Use this mode if you do not run an OS on your system. \#define NO_SYS to 1. 233195972f6Sopenharmony_ci * Feed incoming packets to netif->input(pbuf, netif) function from mainloop, 234195972f6Sopenharmony_ci * *not* *from* *interrupt* *context*. You can allocate a @ref pbuf in interrupt 235195972f6Sopenharmony_ci * context and put them into a queue which is processed from mainloop.\n 236195972f6Sopenharmony_ci * Call sys_check_timeouts() periodically in the mainloop.\n 237195972f6Sopenharmony_ci * Porting: implement all functions in @ref sys_time, @ref sys_prot and 238195972f6Sopenharmony_ci * @ref compiler_abstraction.\n 239195972f6Sopenharmony_ci * You can only use @ref callbackstyle_api in this mode.\n 240195972f6Sopenharmony_ci * Sample code:\n 241195972f6Sopenharmony_ci * @include NO_SYS_SampleCode.c 242195972f6Sopenharmony_ci */ 243195972f6Sopenharmony_ci 244195972f6Sopenharmony_ci/** 245195972f6Sopenharmony_ci * @defgroup lwip_os OS mode (TCPIP thread) 246195972f6Sopenharmony_ci * @ingroup lwip 247195972f6Sopenharmony_ci * Use this mode if you run an OS on your system. It is recommended to 248195972f6Sopenharmony_ci * use an RTOS that correctly handles priority inversion and 249195972f6Sopenharmony_ci * to use @ref LWIP_TCPIP_CORE_LOCKING.\n 250195972f6Sopenharmony_ci * Porting: implement all functions in @ref sys_layer.\n 251195972f6Sopenharmony_ci * You can use @ref callbackstyle_api together with @ref tcpip_callback, 252195972f6Sopenharmony_ci * and all @ref sequential_api. 253195972f6Sopenharmony_ci */ 254195972f6Sopenharmony_ci 255195972f6Sopenharmony_ci/** 256195972f6Sopenharmony_ci * @page sys_init System initalization 257195972f6Sopenharmony_ciA truly complete and generic sequence for initializing the lwIP stack 258195972f6Sopenharmony_cicannot be given because it depends on additional initializations for 259195972f6Sopenharmony_ciyour runtime environment (e.g. timers). 260195972f6Sopenharmony_ci 261195972f6Sopenharmony_ciWe can give you some idea on how to proceed when using the raw API. 262195972f6Sopenharmony_ciWe assume a configuration using a single Ethernet netif and the 263195972f6Sopenharmony_ciUDP and TCP transport layers, IPv4 and the DHCP client. 264195972f6Sopenharmony_ci 265195972f6Sopenharmony_ciCall these functions in the order of appearance: 266195972f6Sopenharmony_ci 267195972f6Sopenharmony_ci- lwip_init(): Initialize the lwIP stack and all of its subsystems. 268195972f6Sopenharmony_ci 269195972f6Sopenharmony_ci- netif_add(struct netif *netif, ...): 270195972f6Sopenharmony_ci Adds your network interface to the netif_list. Allocate a struct 271195972f6Sopenharmony_ci netif and pass a pointer to this structure as the first argument. 272195972f6Sopenharmony_ci Give pointers to cleared ip_addr structures when using DHCP, 273195972f6Sopenharmony_ci or fill them with sane numbers otherwise. The state pointer may be NULL. 274195972f6Sopenharmony_ci 275195972f6Sopenharmony_ci The init function pointer must point to a initialization function for 276195972f6Sopenharmony_ci your Ethernet netif interface. The following code illustrates its use. 277195972f6Sopenharmony_ci 278195972f6Sopenharmony_ci@code{.c} 279195972f6Sopenharmony_ci err_t netif_if_init(struct netif *netif) 280195972f6Sopenharmony_ci { 281195972f6Sopenharmony_ci u8_t i; 282195972f6Sopenharmony_ci 283195972f6Sopenharmony_ci for (i = 0; i < ETHARP_HWADDR_LEN; i++) { 284195972f6Sopenharmony_ci netif->hwaddr[i] = some_eth_addr[i]; 285195972f6Sopenharmony_ci } 286195972f6Sopenharmony_ci init_my_eth_device(); 287195972f6Sopenharmony_ci return ERR_OK; 288195972f6Sopenharmony_ci } 289195972f6Sopenharmony_ci@endcode 290195972f6Sopenharmony_ci 291195972f6Sopenharmony_ci For Ethernet drivers, the input function pointer must point to the lwIP 292195972f6Sopenharmony_ci function ethernet_input() declared in "netif/etharp.h". Other drivers 293195972f6Sopenharmony_ci must use ip_input() declared in "lwip/ip.h". 294195972f6Sopenharmony_ci 295195972f6Sopenharmony_ci- netif_set_default(struct netif *netif) 296195972f6Sopenharmony_ci Registers the default network interface. 297195972f6Sopenharmony_ci 298195972f6Sopenharmony_ci- netif_set_link_up(struct netif *netif) 299195972f6Sopenharmony_ci This is the hardware link state; e.g. whether cable is plugged for wired 300195972f6Sopenharmony_ci Ethernet interface. This function must be called even if you don't know 301195972f6Sopenharmony_ci the current state. Having link up and link down events is optional but 302195972f6Sopenharmony_ci DHCP and IPv6 discover benefit well from those events. 303195972f6Sopenharmony_ci 304195972f6Sopenharmony_ci- netif_set_up(struct netif *netif) 305195972f6Sopenharmony_ci This is the administrative (= software) state of the netif, when the 306195972f6Sopenharmony_ci netif is fully configured this function must be called. 307195972f6Sopenharmony_ci 308195972f6Sopenharmony_ci- dhcp_start(struct netif *netif) 309195972f6Sopenharmony_ci Creates a new DHCP client for this interface on the first call. 310195972f6Sopenharmony_ci You can peek in the netif->dhcp struct for the actual DHCP status. 311195972f6Sopenharmony_ci 312195972f6Sopenharmony_ci- sys_check_timeouts() 313195972f6Sopenharmony_ci When the system is running, you have to periodically call 314195972f6Sopenharmony_ci sys_check_timeouts() which will handle all timers for all protocols in 315195972f6Sopenharmony_ci the stack; add this to your main loop or equivalent. 316195972f6Sopenharmony_ci */ 317195972f6Sopenharmony_ci 318195972f6Sopenharmony_ci/** 319195972f6Sopenharmony_ci * @page multithreading Multithreading 320195972f6Sopenharmony_ci * lwIP started targeting single-threaded environments. When adding multi- 321195972f6Sopenharmony_ci * threading support, instead of making the core thread-safe, another 322195972f6Sopenharmony_ci * approach was chosen: there is one main thread running the lwIP core 323195972f6Sopenharmony_ci * (also known as the "tcpip_thread"). When running in a multithreaded 324195972f6Sopenharmony_ci * environment, raw API functions MUST only be called from the core thread 325195972f6Sopenharmony_ci * since raw API functions are not protected from concurrent access (aside 326195972f6Sopenharmony_ci * from pbuf- and memory management functions). Application threads using 327195972f6Sopenharmony_ci * the sequential- or socket API communicate with this main thread through 328195972f6Sopenharmony_ci * message passing. 329195972f6Sopenharmony_ci * 330195972f6Sopenharmony_ci * As such, the list of functions that may be called from 331195972f6Sopenharmony_ci * other threads or an ISR is very limited! Only functions 332195972f6Sopenharmony_ci * from these API header files are thread-safe: 333195972f6Sopenharmony_ci * - api.h 334195972f6Sopenharmony_ci * - netbuf.h 335195972f6Sopenharmony_ci * - netdb.h 336195972f6Sopenharmony_ci * - netifapi.h 337195972f6Sopenharmony_ci * - pppapi.h 338195972f6Sopenharmony_ci * - sockets.h 339195972f6Sopenharmony_ci * - sys.h 340195972f6Sopenharmony_ci * 341195972f6Sopenharmony_ci * Additionaly, memory (de-)allocation functions may be 342195972f6Sopenharmony_ci * called from multiple threads (not ISR!) with NO_SYS=0 343195972f6Sopenharmony_ci * since they are protected by @ref SYS_LIGHTWEIGHT_PROT and/or 344195972f6Sopenharmony_ci * semaphores. 345195972f6Sopenharmony_ci * 346195972f6Sopenharmony_ci * Netconn or Socket API functions are thread safe against the 347195972f6Sopenharmony_ci * core thread but they are not reentrant at the control block 348195972f6Sopenharmony_ci * granularity level. That is, a UDP or TCP control block must 349195972f6Sopenharmony_ci * not be shared among multiple threads without proper locking. 350195972f6Sopenharmony_ci * 351195972f6Sopenharmony_ci * If @ref SYS_LIGHTWEIGHT_PROT is set to 1 and 352195972f6Sopenharmony_ci * @ref LWIP_ALLOW_MEM_FREE_FROM_OTHER_CONTEXT is set to 1, 353195972f6Sopenharmony_ci * pbuf_free() may also be called from another thread or 354195972f6Sopenharmony_ci * an ISR (since only then, mem_free - for PBUF_RAM - may 355195972f6Sopenharmony_ci * be called from an ISR: otherwise, the HEAP is only 356195972f6Sopenharmony_ci * protected by semaphores). 357195972f6Sopenharmony_ci * 358195972f6Sopenharmony_ci * How to get threading done right 359195972f6Sopenharmony_ci * ------------------------------- 360195972f6Sopenharmony_ci * 361195972f6Sopenharmony_ci * It is strongly recommended to implement the LWIP_ASSERT_CORE_LOCKED() 362195972f6Sopenharmony_ci * macro in an application that uses multithreading. lwIP code has 363195972f6Sopenharmony_ci * several places where a check for a correct thread context is 364195972f6Sopenharmony_ci * implemented which greatly helps the user to get threading done right. 365195972f6Sopenharmony_ci * See the example sys_arch.c files in unix and Win32 port 366195972f6Sopenharmony_ci * in the contrib repository. 367195972f6Sopenharmony_ci * 368195972f6Sopenharmony_ci * In short: Copy the functions sys_mark_tcpip_thread() and 369195972f6Sopenharmony_ci * sys_check_core_locking() to your port and modify them to work with your OS. 370195972f6Sopenharmony_ci * Then let @ref LWIP_ASSERT_CORE_LOCKED() and @ref LWIP_MARK_TCPIP_THREAD() 371195972f6Sopenharmony_ci * point to these functions. 372195972f6Sopenharmony_ci * 373195972f6Sopenharmony_ci * If you use @ref LWIP_TCPIP_CORE_LOCKING, you also need to copy and adapt 374195972f6Sopenharmony_ci * the functions sys_lock_tcpip_core() and sys_unlock_tcpip_core(). 375195972f6Sopenharmony_ci * Let @ref LOCK_TCPIP_CORE() and @ref UNLOCK_TCPIP_CORE() point 376195972f6Sopenharmony_ci * to these functions. 377195972f6Sopenharmony_ci */ 378195972f6Sopenharmony_ci 379195972f6Sopenharmony_ci/** 380195972f6Sopenharmony_ci * @page optimization Optimization hints 381195972f6Sopenharmony_ciThe first thing you want to optimize is the lwip_standard_checksum() 382195972f6Sopenharmony_ciroutine from src/core/inet.c. You can override this standard 383195972f6Sopenharmony_cifunction with the \#define LWIP_CHKSUM your_checksum_routine(). 384195972f6Sopenharmony_ci 385195972f6Sopenharmony_ciThere are C examples given in inet.c or you might want to 386195972f6Sopenharmony_cicraft an assembly function for this. RFC1071 is a good 387195972f6Sopenharmony_ciintroduction to this subject. 388195972f6Sopenharmony_ci 389195972f6Sopenharmony_ciOther significant improvements can be made by supplying 390195972f6Sopenharmony_ciassembly or inline replacements for htons() and htonl() 391195972f6Sopenharmony_ciif you're using a little-endian architecture. 392195972f6Sopenharmony_ci\#define lwip_htons(x) your_htons() 393195972f6Sopenharmony_ci\#define lwip_htonl(x) your_htonl() 394195972f6Sopenharmony_ciIf you \#define them to htons() and htonl(), you should 395195972f6Sopenharmony_ci\#define LWIP_DONT_PROVIDE_BYTEORDER_FUNCTIONS to prevent lwIP from 396195972f6Sopenharmony_cidefining htonx / ntohx compatibility macros. 397195972f6Sopenharmony_ci 398195972f6Sopenharmony_ciCheck your network interface driver if it reads at 399195972f6Sopenharmony_cia higher speed than the maximum wire-speed. If the 400195972f6Sopenharmony_cihardware isn't serviced frequently and fast enough 401195972f6Sopenharmony_cibuffer overflows are likely to occur. 402195972f6Sopenharmony_ci 403195972f6Sopenharmony_ciE.g. when using the cs8900 driver, call cs8900if_service(ethif) 404195972f6Sopenharmony_cias frequently as possible. When using an RTOS let the cs8900 interrupt 405195972f6Sopenharmony_ciwake a high priority task that services your driver using a binary 406195972f6Sopenharmony_cisemaphore or event flag. Some drivers might allow additional tuning 407195972f6Sopenharmony_cito match your application and network. 408195972f6Sopenharmony_ci 409195972f6Sopenharmony_ciFor a production release it is recommended to set LWIP_STATS to 0. 410195972f6Sopenharmony_ciNote that speed performance isn't influenced much by simply setting 411195972f6Sopenharmony_cihigh values to the memory options. 412195972f6Sopenharmony_ci */ 413