• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /**
2  * @file
3  * netif API (to be used from TCPIP thread)
4  */
5 
6 /*
7  * Copyright (c) 2001-2004 Swedish Institute of Computer Science.
8  * All rights reserved.
9  *
10  * Redistribution and use in source and binary forms, with or without modification,
11  * are permitted provided that the following conditions are met:
12  *
13  * 1. Redistributions of source code must retain the above copyright notice,
14  *    this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright notice,
16  *    this list of conditions and the following disclaimer in the documentation
17  *    and/or other materials provided with the distribution.
18  * 3. The name of the author may not be used to endorse or promote products
19  *    derived from this software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
22  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
23  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
24  * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
26  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
29  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
30  * OF SUCH DAMAGE.
31  *
32  * This file is part of the lwIP TCP/IP stack.
33  *
34  * Author: Adam Dunkels <adam@sics.se>
35  *
36  */
37 #ifndef LWIP_HDR_NETIF_H
38 #define LWIP_HDR_NETIF_H
39 
40 #include "lwip/opt.h"
41 
42 #define ENABLE_LOOPBACK (LWIP_NETIF_LOOPBACK || LWIP_HAVE_LOOPIF)
43 
44 #include "lwip/err.h"
45 
46 #include "lwip/ip_addr.h"
47 
48 #include "lwip/def.h"
49 #include "lwip/pbuf.h"
50 #include "lwip/stats.h"
51 #ifdef LOSCFG_NET_CONTAINER
52 #include "lwip/net_group.h"
53 #endif
54 
55 #ifdef __cplusplus
56 extern "C" {
57 #endif
58 
59 /* Throughout this file, IP addresses are expected to be in
60  * the same byte order as in IP_PCB. */
61 
62 /** Must be the maximum of all used hardware address lengths
63     across all types of interfaces in use.
64     This does not have to be changed, normally. */
65 #ifndef NETIF_MAX_HWADDR_LEN
66 #define NETIF_MAX_HWADDR_LEN 6U
67 #endif
68 
69 /** The size of a fully constructed netif name which the
70  * netif can be identified by in APIs. Composed of
71  * 2 chars, 3 (max) digits, and 1 \0
72  */
73 #define NETIF_NAMESIZE 6
74 
75 /**
76  * @defgroup netif_flags Flags
77  * @ingroup netif
78  * @{
79  */
80 
81 /** Whether the network interface is 'up'. This is
82  * a software flag used to control whether this network
83  * interface is enabled and processes traffic.
84  * It must be set by the startup code before this netif can be used
85  * (also for dhcp/autoip).
86  */
87 #define NETIF_FLAG_UP           0x01U
88 /** If set, the netif has broadcast capability.
89  * Set by the netif driver in its init function. */
90 #define NETIF_FLAG_BROADCAST    0x02U
91 /** If set, the interface has an active link
92  *  (set by the network interface driver).
93  * Either set by the netif driver in its init function (if the link
94  * is up at that time) or at a later point once the link comes up
95  * (if link detection is supported by the hardware). */
96 #define NETIF_FLAG_LINK_UP      0x04U
97 /** If set, the netif is an ethernet device using ARP.
98  * Set by the netif driver in its init function.
99  * Used to check input packet types and use of DHCP. */
100 #define NETIF_FLAG_ETHARP       0x08U
101 /** If set, the netif is an ethernet device. It might not use
102  * ARP or TCP/IP if it is used for PPPoE only.
103  */
104 #define NETIF_FLAG_ETHERNET     0x10U
105 /** If set, the netif has IGMP capability.
106  * Set by the netif driver in its init function. */
107 #define NETIF_FLAG_IGMP         0x20U
108 /** If set, the netif has MLD6 capability.
109  * Set by the netif driver in its init function. */
110 #define NETIF_FLAG_MLD6         0x40U
111 
112 /**
113  * @}
114  */
115 
116 enum lwip_internal_netif_client_data_index
117 {
118 #if LWIP_IPV4
119 #if LWIP_DHCP
120    LWIP_NETIF_CLIENT_DATA_INDEX_DHCP,
121 #endif
122 #if LWIP_AUTOIP
123    LWIP_NETIF_CLIENT_DATA_INDEX_AUTOIP,
124 #endif
125 #if LWIP_IGMP
126    LWIP_NETIF_CLIENT_DATA_INDEX_IGMP,
127 #endif
128 #endif /* LWIP_IPV4 */
129 #if LWIP_IPV6
130 #if LWIP_IPV6_DHCP6
131    LWIP_NETIF_CLIENT_DATA_INDEX_DHCP6,
132 #endif
133 #if LWIP_IPV6_MLD
134    LWIP_NETIF_CLIENT_DATA_INDEX_MLD6,
135 #endif
136 #endif /* LWIP_IPV6 */
137    LWIP_NETIF_CLIENT_DATA_INDEX_MAX
138 };
139 
140 #if LWIP_CHECKSUM_CTRL_PER_NETIF
141 #define NETIF_CHECKSUM_GEN_IP       0x0001
142 #define NETIF_CHECKSUM_GEN_UDP      0x0002
143 #define NETIF_CHECKSUM_GEN_TCP      0x0004
144 #define NETIF_CHECKSUM_GEN_ICMP     0x0008
145 #define NETIF_CHECKSUM_GEN_ICMP6    0x0010
146 #define NETIF_CHECKSUM_CHECK_IP     0x0100
147 #define NETIF_CHECKSUM_CHECK_UDP    0x0200
148 #define NETIF_CHECKSUM_CHECK_TCP    0x0400
149 #define NETIF_CHECKSUM_CHECK_ICMP   0x0800
150 #define NETIF_CHECKSUM_CHECK_ICMP6  0x1000
151 #define NETIF_CHECKSUM_ENABLE_ALL   0xFFFF
152 #define NETIF_CHECKSUM_DISABLE_ALL  0x0000
153 #endif /* LWIP_CHECKSUM_CTRL_PER_NETIF */
154 
155 struct netif;
156 
157 /** MAC Filter Actions, these are passed to a netif's igmp_mac_filter or
158  * mld_mac_filter callback function. */
159 enum netif_mac_filter_action {
160   /** Delete a filter entry */
161   NETIF_DEL_MAC_FILTER = 0,
162   /** Add a filter entry */
163   NETIF_ADD_MAC_FILTER = 1
164 };
165 
166 /** Function prototype for netif init functions. Set up flags and output/linkoutput
167  * callback functions in this function.
168  *
169  * @param netif The netif to initialize
170  */
171 typedef err_t (*netif_init_fn)(struct netif *netif);
172 /** Function prototype for netif->input functions. This function is saved as 'input'
173  * callback function in the netif struct. Call it when a packet has been received.
174  *
175  * @param p The received packet, copied into a pbuf
176  * @param inp The netif which received the packet
177  * @return ERR_OK if the packet was handled
178  *         != ERR_OK is the packet was NOT handled, in this case, the caller has
179  *                   to free the pbuf
180  */
181 typedef err_t (*netif_input_fn)(struct pbuf *p, struct netif *inp);
182 
183 #if LWIP_IPV4
184 /** Function prototype for netif->output functions. Called by lwIP when a packet
185  * shall be sent. For ethernet netif, set this to 'etharp_output' and set
186  * 'linkoutput'.
187  *
188  * @param netif The netif which shall send a packet
189  * @param p The packet to send (p->payload points to IP header)
190  * @param ipaddr The IP address to which the packet shall be sent
191  */
192 typedef err_t (*netif_output_fn)(struct netif *netif, struct pbuf *p,
193        const ip4_addr_t *ipaddr);
194 #endif /* LWIP_IPV4*/
195 
196 #if LWIP_IPV6
197 /** Function prototype for netif->output_ip6 functions. Called by lwIP when a packet
198  * shall be sent. For ethernet netif, set this to 'ethip6_output' and set
199  * 'linkoutput'.
200  *
201  * @param netif The netif which shall send a packet
202  * @param p The packet to send (p->payload points to IP header)
203  * @param ipaddr The IPv6 address to which the packet shall be sent
204  */
205 typedef err_t (*netif_output_ip6_fn)(struct netif *netif, struct pbuf *p,
206        const ip6_addr_t *ipaddr);
207 #endif /* LWIP_IPV6 */
208 
209 /** Function prototype for netif->linkoutput functions. Only used for ethernet
210  * netifs. This function is called by ARP when a packet shall be sent.
211  *
212  * @param netif The netif which shall send a packet
213  * @param p The packet to send (raw ethernet packet)
214  */
215 typedef err_t (*netif_linkoutput_fn)(struct netif *netif, struct pbuf *p);
216 /** Function prototype for netif status- or link-callback functions. */
217 typedef void (*netif_status_callback_fn)(struct netif *netif);
218 #if LWIP_IPV4 && LWIP_IGMP
219 /** Function prototype for netif igmp_mac_filter functions */
220 typedef err_t (*netif_igmp_mac_filter_fn)(struct netif *netif,
221        const ip4_addr_t *group, enum netif_mac_filter_action action);
222 #endif /* LWIP_IPV4 && LWIP_IGMP */
223 #if LWIP_IPV6 && LWIP_IPV6_MLD
224 /** Function prototype for netif mld_mac_filter functions */
225 typedef err_t (*netif_mld_mac_filter_fn)(struct netif *netif,
226        const ip6_addr_t *group, enum netif_mac_filter_action action);
227 #endif /* LWIP_IPV6 && LWIP_IPV6_MLD */
228 
229 #if LWIP_DHCP || LWIP_AUTOIP || LWIP_IGMP || LWIP_IPV6_MLD || LWIP_IPV6_DHCP6 || (LWIP_NUM_NETIF_CLIENT_DATA > 0)
230 #if LWIP_NUM_NETIF_CLIENT_DATA > 0
231 u8_t netif_alloc_client_data_id(void);
232 #endif
233 /** @ingroup netif_cd
234  * Set client data. Obtain ID from netif_alloc_client_data_id().
235  */
236 #define netif_set_client_data(netif, id, data) netif_get_client_data(netif, id) = (data)
237 /** @ingroup netif_cd
238  * Get client data. Obtain ID from netif_alloc_client_data_id().
239  */
240 #define netif_get_client_data(netif, id)       (netif)->client_data[(id)]
241 #endif
242 
243 #if (LWIP_IPV4 && LWIP_ARP && (ARP_TABLE_SIZE > 0x7f)) || (LWIP_IPV6 && (LWIP_ND6_NUM_DESTINATIONS > 0x7f))
244 typedef u16_t netif_addr_idx_t;
245 #define NETIF_ADDR_IDX_MAX 0x7FFF
246 #else
247 typedef u8_t netif_addr_idx_t;
248 #define NETIF_ADDR_IDX_MAX 0x7F
249 #endif
250 
251 #if LWIP_NETIF_HWADDRHINT
252 #define LWIP_NETIF_USE_HINTS              1
253 struct netif_hint {
254   netif_addr_idx_t addr_hint;
255 };
256 #else /* LWIP_NETIF_HWADDRHINT */
257 #define LWIP_NETIF_USE_HINTS              0
258 #endif /* LWIP_NETIF_HWADDRHINT */
259 
260 /** Generic data structure used for all lwIP network interfaces.
261  *  The following fields should be filled in by the initialization
262  *  function for the device driver: hwaddr_len, hwaddr[], mtu, flags */
263 struct netif {
264 #if !LWIP_SINGLE_NETIF
265   /** pointer to next in linked list */
266   struct netif *next;
267 #endif
268 
269 #if LWIP_IPV4
270   /** IP address configuration in network byte order */
271   ip_addr_t ip_addr;
272   ip_addr_t netmask;
273   ip_addr_t gw;
274 #endif /* LWIP_IPV4 */
275 #if LWIP_IPV6
276   /** Array of IPv6 addresses for this netif. */
277   ip_addr_t ip6_addr[LWIP_IPV6_NUM_ADDRESSES];
278   /** The state of each IPv6 address (Tentative, Preferred, etc).
279    * @see ip6_addr.h */
280   u8_t ip6_addr_state[LWIP_IPV6_NUM_ADDRESSES];
281 #if LWIP_IPV6_ADDRESS_LIFETIMES
282   /** Remaining valid and preferred lifetime of each IPv6 address, in seconds.
283    * For valid lifetimes, the special value of IP6_ADDR_LIFE_STATIC (0)
284    * indicates the address is static and has no lifetimes. */
285   u32_t ip6_addr_valid_life[LWIP_IPV6_NUM_ADDRESSES];
286   u32_t ip6_addr_pref_life[LWIP_IPV6_NUM_ADDRESSES];
287 #endif /* LWIP_IPV6_ADDRESS_LIFETIMES */
288 #endif /* LWIP_IPV6 */
289   /** This function is called by the network device driver
290    *  to pass a packet up the TCP/IP stack. */
291   netif_input_fn input;
292 #if LWIP_IPV4
293   /** This function is called by the IP module when it wants
294    *  to send a packet on the interface. This function typically
295    *  first resolves the hardware address, then sends the packet.
296    *  For ethernet physical layer, this is usually etharp_output() */
297   netif_output_fn output;
298 #endif /* LWIP_IPV4 */
299   /** This function is called by ethernet_output() when it wants
300    *  to send a packet on the interface. This function outputs
301    *  the pbuf as-is on the link medium. */
302   netif_linkoutput_fn linkoutput;
303 #if LWIP_IPV6
304   /** This function is called by the IPv6 module when it wants
305    *  to send a packet on the interface. This function typically
306    *  first resolves the hardware address, then sends the packet.
307    *  For ethernet physical layer, this is usually ethip6_output() */
308   netif_output_ip6_fn output_ip6;
309 #endif /* LWIP_IPV6 */
310 #if LWIP_NETIF_STATUS_CALLBACK
311   /** This function is called when the netif state is set to up or down
312    */
313   netif_status_callback_fn status_callback;
314 #endif /* LWIP_NETIF_STATUS_CALLBACK */
315 #if LWIP_NETIF_LINK_CALLBACK
316   /** This function is called when the netif link is set to up or down
317    */
318   netif_status_callback_fn link_callback;
319 #endif /* LWIP_NETIF_LINK_CALLBACK */
320 #if LWIP_NETIF_REMOVE_CALLBACK
321   /** This function is called when the netif has been removed */
322   netif_status_callback_fn remove_callback;
323 #endif /* LWIP_NETIF_REMOVE_CALLBACK */
324   /** This field can be set by the device driver and could point
325    *  to state information for the device. */
326   void *state;
327 #ifdef netif_get_client_data
328   void* client_data[LWIP_NETIF_CLIENT_DATA_INDEX_MAX + LWIP_NUM_NETIF_CLIENT_DATA];
329 #endif
330 #if LWIP_NETIF_HOSTNAME
331   /* the hostname for this netif, NULL is a valid value */
332   const char*  hostname;
333 #endif /* LWIP_NETIF_HOSTNAME */
334 #if LWIP_CHECKSUM_CTRL_PER_NETIF
335   u16_t chksum_flags;
336 #endif /* LWIP_CHECKSUM_CTRL_PER_NETIF*/
337   /** maximum transfer unit (in bytes) */
338   u16_t mtu;
339 #if LWIP_IPV6 && LWIP_ND6_ALLOW_RA_UPDATES
340   /** maximum transfer unit (in bytes), updated by RA */
341   u16_t mtu6;
342 #endif /* LWIP_IPV6 && LWIP_ND6_ALLOW_RA_UPDATES */
343   /** link level hardware address of this interface */
344   u8_t hwaddr[NETIF_MAX_HWADDR_LEN];
345   /** number of bytes used in hwaddr */
346   u8_t hwaddr_len;
347   /** flags (@see @ref netif_flags) */
348   u8_t flags;
349   /** descriptive abbreviation */
350   char name[2];
351   /** number of this interface. Used for @ref if_api and @ref netifapi_netif,
352    * as well as for IPv6 zones */
353   u8_t num;
354 #if LWIP_IPV6_AUTOCONFIG
355   /** is this netif enabled for IPv6 autoconfiguration */
356   u8_t ip6_autoconfig_enabled;
357 #endif /* LWIP_IPV6_AUTOCONFIG */
358 #if LWIP_IPV6_SEND_ROUTER_SOLICIT
359   /** Number of Router Solicitation messages that remain to be sent. */
360   u8_t rs_count;
361 #endif /* LWIP_IPV6_SEND_ROUTER_SOLICIT */
362 #if MIB2_STATS
363   /** link type (from "snmp_ifType" enum from snmp_mib2.h) */
364   u8_t link_type;
365   /** (estimate) link speed */
366   u32_t link_speed;
367   /** timestamp at last change made (up/down) */
368   u32_t ts;
369   /** counters */
370   struct stats_mib2_netif_ctrs mib2_counters;
371 #endif /* MIB2_STATS */
372 #if LWIP_IPV4 && LWIP_IGMP
373   /** This function could be called to add or delete an entry in the multicast
374       filter table of the ethernet MAC.*/
375   netif_igmp_mac_filter_fn igmp_mac_filter;
376 #endif /* LWIP_IPV4 && LWIP_IGMP */
377 #if LWIP_IPV6 && LWIP_IPV6_MLD
378   /** This function could be called to add or delete an entry in the IPv6 multicast
379       filter table of the ethernet MAC. */
380   netif_mld_mac_filter_fn mld_mac_filter;
381 #endif /* LWIP_IPV6 && LWIP_IPV6_MLD */
382 #if LWIP_NETIF_USE_HINTS
383   struct netif_hint *hints;
384 #endif /* LWIP_NETIF_USE_HINTS */
385 #if ENABLE_LOOPBACK
386   /* List of packets to be queued for ourselves. */
387   struct pbuf *loop_first;
388   struct pbuf *loop_last;
389 #if LWIP_LOOPBACK_MAX_PBUFS
390   u16_t loop_cnt_current;
391 #endif /* LWIP_LOOPBACK_MAX_PBUFS */
392 #if LWIP_NETIF_LOOPBACK_MULTITHREADING
393   /* Used if the original scheduling failed. */
394   u8_t reschedule_poll;
395 #endif /* LWIP_NETIF_LOOPBACK_MULTITHREADING */
396 #endif /* ENABLE_LOOPBACK */
397 };
398 
399 #if LWIP_CHECKSUM_CTRL_PER_NETIF
400 #define NETIF_SET_CHECKSUM_CTRL(netif, chksumflags) do { \
401   (netif)->chksum_flags = chksumflags; } while(0)
402 #define IF__NETIF_CHECKSUM_ENABLED(netif, chksumflag) if (((netif) == NULL) || (((netif)->chksum_flags & (chksumflag)) != 0))
403 #else /* LWIP_CHECKSUM_CTRL_PER_NETIF */
404 #define NETIF_SET_CHECKSUM_CTRL(netif, chksumflags)
405 #define IF__NETIF_CHECKSUM_ENABLED(netif, chksumflag)
406 #endif /* LWIP_CHECKSUM_CTRL_PER_NETIF */
407 
408 #if LWIP_SINGLE_NETIF
409 #ifdef LOSCFG_NET_CONTAINER
410 #define NETIF_FOREACH(netif, group) if (((netif) = group->netif_default) != NULL)
411 #else
412 #define NETIF_FOREACH(netif) if (((netif) = netif_default) != NULL)
413 #endif
414 #else /* LWIP_SINGLE_NETIF */
415 #ifdef LOSCFG_NET_CONTAINER
416 #define NETIF_FOREACH(netif, group) for ((netif) = group->netif_list; (netif) != NULL; (netif) = (netif)->next)
417 #else
418 /** The list of network interfaces. */
419 extern struct netif *netif_list;
420 #define NETIF_FOREACH(netif) for ((netif) = netif_list; (netif) != NULL; (netif) = (netif)->next)
421 #endif
422 
423 #endif /* LWIP_SINGLE_NETIF */
424 #ifndef LOSCFG_NET_CONTAINER
425 /** The default network interface. */
426 extern struct netif *netif_default;
427 #endif
428 
429 #ifdef LOSCFG_NET_CONTAINER
430 struct net_group *get_net_group_from_netif(struct netif *netif);
431 void netif_init(struct net_group *group);
432 #else
433 void netif_init(void);
434 #endif
435 
436 #ifdef LOSCFG_NET_CONTAINER
437 struct netif *netif_add_noaddr(struct netif *netif, struct net_group *group,
438                                     void *state, netif_init_fn init, netif_input_fn input);
439 #else
440 struct netif *netif_add_noaddr(struct netif *netif, void *state, netif_init_fn init, netif_input_fn input);
441 #endif
442 
443 #if LWIP_IPV4
444 #ifdef LOSCFG_NET_CONTAINER
445 struct netif *netif_add(struct netif *netif, struct net_group *group,
446 #else
447 struct netif *netif_add(struct netif *netif,
448 #endif
449                             const ip4_addr_t *ipaddr, const ip4_addr_t *netmask, const ip4_addr_t *gw,
450                             void *state, netif_init_fn init, netif_input_fn input);
451 void netif_set_addr(struct netif *netif, const ip4_addr_t *ipaddr, const ip4_addr_t *netmask,
452                     const ip4_addr_t *gw);
453 #else /* LWIP_IPV4 */
454 struct netif *netif_add(struct netif *netif, void *state, netif_init_fn init, netif_input_fn input);
455 #endif /* LWIP_IPV4 */
456 void netif_remove(struct netif * netif);
457 
458 /* Returns a network interface given its name. The name is of the form
459    "et0", where the first two letters are the "name" field in the
460    netif structure, and the digit is in the num field in the same
461    structure. */
462 struct netif *netif_find(const char *name);
463 
464 #ifdef LOSCFG_NET_CONTAINER
465 void netif_set_default(struct netif *netif, struct net_group *group);
466 void netif_set_default2(struct netif *netif);
467 #else
468 void netif_set_default(struct netif *netif);
469 #endif
470 
471 #if LWIP_IPV4
472 void netif_set_ipaddr(struct netif *netif, const ip4_addr_t *ipaddr);
473 void netif_set_netmask(struct netif *netif, const ip4_addr_t *netmask);
474 void netif_set_gw(struct netif *netif, const ip4_addr_t *gw);
475 /** @ingroup netif_ip4 */
476 #define netif_ip4_addr(netif)    ((const ip4_addr_t*)ip_2_ip4(&((netif)->ip_addr)))
477 /** @ingroup netif_ip4 */
478 #define netif_ip4_netmask(netif) ((const ip4_addr_t*)ip_2_ip4(&((netif)->netmask)))
479 /** @ingroup netif_ip4 */
480 #define netif_ip4_gw(netif)      ((const ip4_addr_t*)ip_2_ip4(&((netif)->gw)))
481 /** @ingroup netif_ip4 */
482 #define netif_ip_addr4(netif)    ((const ip_addr_t*)&((netif)->ip_addr))
483 /** @ingroup netif_ip4 */
484 #define netif_ip_netmask4(netif) ((const ip_addr_t*)&((netif)->netmask))
485 /** @ingroup netif_ip4 */
486 #define netif_ip_gw4(netif)      ((const ip_addr_t*)&((netif)->gw))
487 #endif /* LWIP_IPV4 */
488 
489 #define netif_set_flags(netif, set_flags)     do { (netif)->flags = (u8_t)((netif)->flags |  (set_flags)); } while(0)
490 #define netif_clear_flags(netif, clr_flags)   do { (netif)->flags = (u8_t)((netif)->flags & (u8_t)(~(clr_flags) & 0xff)); } while(0)
491 #define netif_is_flag_set(netif, flag)        (((netif)->flags & (flag)) != 0)
492 
493 void netif_set_up(struct netif *netif);
494 void netif_set_down(struct netif *netif);
495 /** @ingroup netif
496  * Ask if an interface is up
497  */
498 #define netif_is_up(netif) (((netif)->flags & NETIF_FLAG_UP) ? (u8_t)1 : (u8_t)0)
499 
500 #if LWIP_NETIF_STATUS_CALLBACK
501 void netif_set_status_callback(struct netif *netif, netif_status_callback_fn status_callback);
502 #endif /* LWIP_NETIF_STATUS_CALLBACK */
503 #if LWIP_NETIF_REMOVE_CALLBACK
504 void netif_set_remove_callback(struct netif *netif, netif_status_callback_fn remove_callback);
505 #endif /* LWIP_NETIF_REMOVE_CALLBACK */
506 
507 void netif_set_link_up(struct netif *netif);
508 void netif_set_link_down(struct netif *netif);
509 /** Ask if a link is up */
510 #define netif_is_link_up(netif) (((netif)->flags & NETIF_FLAG_LINK_UP) ? (u8_t)1 : (u8_t)0)
511 
512 #if LWIP_NETIF_LINK_CALLBACK
513 void netif_set_link_callback(struct netif *netif, netif_status_callback_fn link_callback);
514 #endif /* LWIP_NETIF_LINK_CALLBACK */
515 
516 #if LWIP_NETIF_HOSTNAME
517 /** @ingroup netif */
518 #define netif_set_hostname(netif, name) do { if((netif) != NULL) { (netif)->hostname = name; }}while(0)
519 /** @ingroup netif */
520 #define netif_get_hostname(netif) (((netif) != NULL) ? ((netif)->hostname) : NULL)
521 #endif /* LWIP_NETIF_HOSTNAME */
522 
523 #if LWIP_IGMP
524 /** @ingroup netif */
525 #define netif_set_igmp_mac_filter(netif, function) do { if((netif) != NULL) { (netif)->igmp_mac_filter = function; }}while(0)
526 #define netif_get_igmp_mac_filter(netif) (((netif) != NULL) ? ((netif)->igmp_mac_filter) : NULL)
527 #endif /* LWIP_IGMP */
528 
529 #if LWIP_IPV6 && LWIP_IPV6_MLD
530 /** @ingroup netif */
531 #define netif_set_mld_mac_filter(netif, function) do { if((netif) != NULL) { (netif)->mld_mac_filter = function; }}while(0)
532 #define netif_get_mld_mac_filter(netif) (((netif) != NULL) ? ((netif)->mld_mac_filter) : NULL)
533 #define netif_mld_mac_filter(netif, addr, action) do { if((netif) && (netif)->mld_mac_filter) { (netif)->mld_mac_filter((netif), (addr), (action)); }}while(0)
534 #endif /* LWIP_IPV6 && LWIP_IPV6_MLD */
535 
536 #if ENABLE_LOOPBACK
537 err_t netif_loop_output(struct netif *netif, struct pbuf *p);
538 void netif_poll(struct netif *netif);
539 #if !LWIP_NETIF_LOOPBACK_MULTITHREADING
540 void netif_poll_all(void);
541 #endif /* !LWIP_NETIF_LOOPBACK_MULTITHREADING */
542 #endif /* ENABLE_LOOPBACK */
543 
544 err_t netif_input(struct pbuf *p, struct netif *inp);
545 
546 #if LWIP_IPV6
547 /** @ingroup netif_ip6 */
548 #define netif_ip_addr6(netif, i)  ((const ip_addr_t*)(&((netif)->ip6_addr[i])))
549 /** @ingroup netif_ip6 */
550 #define netif_ip6_addr(netif, i)  ((const ip6_addr_t*)ip_2_ip6(&((netif)->ip6_addr[i])))
551 void netif_ip6_addr_set(struct netif *netif, s8_t addr_idx, const ip6_addr_t *addr6);
552 void netif_ip6_addr_set_parts(struct netif *netif, s8_t addr_idx, u32_t i0, u32_t i1, u32_t i2, u32_t i3);
553 #define netif_ip6_addr_state(netif, i)  ((netif)->ip6_addr_state[i])
554 void netif_ip6_addr_set_state(struct netif* netif, s8_t addr_idx, u8_t state);
555 s8_t netif_get_ip6_addr_match(struct netif *netif, const ip6_addr_t *ip6addr);
556 void netif_create_ip6_linklocal_address(struct netif *netif, u8_t from_mac_48bit);
557 err_t netif_add_ip6_address(struct netif *netif, const ip6_addr_t *ip6addr, s8_t *chosen_idx);
558 #define netif_set_ip6_autoconfig_enabled(netif, action) do { if(netif) { (netif)->ip6_autoconfig_enabled = (action); }}while(0)
559 #if LWIP_IPV6_ADDRESS_LIFETIMES
560 #define netif_ip6_addr_valid_life(netif, i)  \
561     (((netif) != NULL) ? ((netif)->ip6_addr_valid_life[i]) : IP6_ADDR_LIFE_STATIC)
562 #define netif_ip6_addr_set_valid_life(netif, i, secs) \
563     do { if (netif != NULL) { (netif)->ip6_addr_valid_life[i] = (secs); }} while (0)
564 #define netif_ip6_addr_pref_life(netif, i)  \
565     (((netif) != NULL) ? ((netif)->ip6_addr_pref_life[i]) : IP6_ADDR_LIFE_STATIC)
566 #define netif_ip6_addr_set_pref_life(netif, i, secs) \
567     do { if (netif != NULL) { (netif)->ip6_addr_pref_life[i] = (secs); }} while (0)
568 #define netif_ip6_addr_isstatic(netif, i)  \
569     (netif_ip6_addr_valid_life((netif), (i)) == IP6_ADDR_LIFE_STATIC)
570 #else /* !LWIP_IPV6_ADDRESS_LIFETIMES */
571 #define netif_ip6_addr_isstatic(netif, i)  (1) /* all addresses are static */
572 #endif /* !LWIP_IPV6_ADDRESS_LIFETIMES */
573 #if LWIP_ND6_ALLOW_RA_UPDATES
574 #define netif_mtu6(netif) ((netif)->mtu6)
575 #else /* LWIP_ND6_ALLOW_RA_UPDATES */
576 #define netif_mtu6(netif) ((netif)->mtu)
577 #endif /* LWIP_ND6_ALLOW_RA_UPDATES */
578 #endif /* LWIP_IPV6 */
579 
580 #if LWIP_NETIF_USE_HINTS
581 #define NETIF_SET_HINTS(netif, netifhint)  (netif)->hints = (netifhint)
582 #define NETIF_RESET_HINTS(netif)      (netif)->hints = NULL
583 #else /* LWIP_NETIF_USE_HINTS */
584 #define NETIF_SET_HINTS(netif, netifhint)
585 #define NETIF_RESET_HINTS(netif)
586 #endif /* LWIP_NETIF_USE_HINTS */
587 
588 u8_t netif_name_to_index(const char *name);
589 #ifdef LOSCFG_NET_CONTAINER
590 char * netif_index_to_name(u8_t idx, char *name, struct net_group *group);
591 struct netif* netif_get_by_index(u8_t idx, struct net_group *group);
592 #else
593 char * netif_index_to_name(u8_t idx, char *name);
594 struct netif* netif_get_by_index(u8_t idx);
595 #endif
596 
597 /* Interface indexes always start at 1 per RFC 3493, section 4, num starts at 0 (internal index is 0..254)*/
598 #define netif_get_index(netif)      ((u8_t)((netif)->num + 1))
599 #define NETIF_NO_INDEX              (0)
600 
601 /**
602  * @ingroup netif
603  * Extended netif status callback (NSC) reasons flags.
604  * May be extended in the future!
605  */
606 typedef u16_t netif_nsc_reason_t;
607 
608 /* used for initialization only */
609 #define LWIP_NSC_NONE                     0x0000
610 /** netif was added. arg: NULL. Called AFTER netif was added. */
611 #define LWIP_NSC_NETIF_ADDED              0x0001
612 /** netif was removed. arg: NULL. Called BEFORE netif is removed. */
613 #define LWIP_NSC_NETIF_REMOVED            0x0002
614 /** link changed */
615 #define LWIP_NSC_LINK_CHANGED             0x0004
616 /** netif administrative status changed.\n
617   * up is called AFTER netif is set up.\n
618   * down is called BEFORE the netif is actually set down. */
619 #define LWIP_NSC_STATUS_CHANGED           0x0008
620 /** IPv4 address has changed */
621 #define LWIP_NSC_IPV4_ADDRESS_CHANGED     0x0010
622 /** IPv4 gateway has changed */
623 #define LWIP_NSC_IPV4_GATEWAY_CHANGED     0x0020
624 /** IPv4 netmask has changed */
625 #define LWIP_NSC_IPV4_NETMASK_CHANGED     0x0040
626 /** called AFTER IPv4 address/gateway/netmask changes have been applied */
627 #define LWIP_NSC_IPV4_SETTINGS_CHANGED    0x0080
628 /** IPv6 address was added */
629 #define LWIP_NSC_IPV6_SET                 0x0100
630 /** IPv6 address state has changed */
631 #define LWIP_NSC_IPV6_ADDR_STATE_CHANGED  0x0200
632 
633 /** @ingroup netif
634  * Argument supplied to netif_ext_callback_fn.
635  */
636 typedef union
637 {
638   /** Args to LWIP_NSC_LINK_CHANGED callback */
639   struct link_changed_s
640   {
641     /** 1: up; 0: down */
642     u8_t state;
643   } link_changed;
644   /** Args to LWIP_NSC_STATUS_CHANGED callback */
645   struct status_changed_s
646   {
647     /** 1: up; 0: down */
648     u8_t state;
649   } status_changed;
650   /** Args to LWIP_NSC_IPV4_ADDRESS_CHANGED|LWIP_NSC_IPV4_GATEWAY_CHANGED|LWIP_NSC_IPV4_NETMASK_CHANGED|LWIP_NSC_IPV4_SETTINGS_CHANGED callback */
651   struct ipv4_changed_s
652   {
653     /** Old IPv4 address */
654     const ip_addr_t* old_address;
655     const ip_addr_t* old_netmask;
656     const ip_addr_t* old_gw;
657   } ipv4_changed;
658   /** Args to LWIP_NSC_IPV6_SET callback */
659   struct ipv6_set_s
660   {
661     /** Index of changed IPv6 address */
662     s8_t addr_index;
663     /** Old IPv6 address */
664     const ip_addr_t* old_address;
665   } ipv6_set;
666   /** Args to LWIP_NSC_IPV6_ADDR_STATE_CHANGED callback */
667   struct ipv6_addr_state_changed_s
668   {
669     /** Index of affected IPv6 address */
670     s8_t addr_index;
671     /** Old IPv6 address state */
672     u8_t old_state;
673     /** Affected IPv6 address */
674     const ip_addr_t* address;
675   } ipv6_addr_state_changed;
676 } netif_ext_callback_args_t;
677 
678 /**
679  * @ingroup netif
680  * Function used for extended netif status callbacks
681  * Note: When parsing reason argument, keep in mind that more reasons may be added in the future!
682  * @param netif netif that is affected by change
683  * @param reason change reason
684  * @param args depends on reason, see reason description
685  */
686 typedef void (*netif_ext_callback_fn)(struct netif* netif, netif_nsc_reason_t reason, const netif_ext_callback_args_t* args);
687 
688 #if LWIP_NETIF_EXT_STATUS_CALLBACK
689 struct netif_ext_callback;
690 typedef struct netif_ext_callback
691 {
692   netif_ext_callback_fn callback_fn;
693   struct netif_ext_callback* next;
694 } netif_ext_callback_t;
695 
696 #define NETIF_DECLARE_EXT_CALLBACK(name) static netif_ext_callback_t name;
697 void netif_add_ext_callback(netif_ext_callback_t* callback, netif_ext_callback_fn fn);
698 void netif_remove_ext_callback(netif_ext_callback_t* callback);
699 void netif_invoke_ext_callback(struct netif* netif, netif_nsc_reason_t reason, const netif_ext_callback_args_t* args);
700 #else
701 #define NETIF_DECLARE_EXT_CALLBACK(name)
702 #define netif_add_ext_callback(callback, fn)
703 #define netif_remove_ext_callback(callback)
704 #define netif_invoke_ext_callback(netif, reason, args)
705 #endif
706 
707 #ifdef __cplusplus
708 }
709 #endif
710 
711 #endif /* LWIP_HDR_NETIF_H */
712