整个学习的过程也打算按照这种流程来学习,先从底层看起(这部分也是我最熟悉的),依次从network interface layer -> internetwork layer -> transport layer -> application layer(这也是按照tcpip的经典四层分法的)。
首先来看网络接口层:
这一层的主要文件位于/src/netif目录,主要是网络设备驱动文件(一个skeleton程序),一个loopback文件(非常简单),arp模块,ppp协议栈。核心的netif的通用程序在/src/core目录下。
1. 重要的结构体有:
Struct netif
{
……
}
这个结构体相当linux中的net_device结构体,用lwip的原文来说就是整个网络接口层中都会用到的一个结构体,对于理解这一层非常重要。
具体看一下:
struct netif {
/*指向链表中下一个网络接口的指针 */
struct netif *next;
/** IP address configuration in network byte order */
struct ip_addr ip_addr;
struct ip_addr netmask;
struct ip_addr gw;
/*这个函数是设备驱动调用用来向tcpip协议层传递数据包*/
err_t (* input)(struct pbuf *p, struct netif *inp);
/*这个函数是当ip层想向网络接口层发送一个数据包时调用,一般会先将ip地址解析为mac地址,然后发送 */
err_t (* output)(struct netif *netif, struct pbuf *p,struct ip_addr *ipaddr);
/*这个函数是当arp模块需要向接口层发送数据包时被调用, */
err_t (* linkoutput)(struct netif *netif, struct pbuf *p);
……
/*用来指向设备的独有的一些信息,类似linux中常用的void * private. */
void *state;
#if LWIP_DHCP
/*这个netif的dhcp信息 */
struct dhcp *dhcp;
#endif /* LWIP_DHCP */
#if LWIP_AUTOIP
/** the AutoIP client state information for this netif */
struct autoip *autoip;
#endif
#if LWIP_NETIF_HOSTNAME
/* the hostname for this netif, NULL is a valid value */
char* hostname;
#endif /* LWIP_NETIF_HOSTNAME */
/*最大传送字节数,以太网一般是1500个字节(术语应该叫八位组) */
u16_t mtu;
/*硬件地址长度,对于以太网就是mac地址长度,一般为6个字节 */
u8_t hwaddr_len;
/*mac地址 */
u8_t hwaddr[NETIF_MAX_HWADDR_LEN];
/** flags (see NETIF_FLAG_ above) */
u8_t flags;
/** descriptive abbreviation */
char name[2];
/** number of this interface */
u8_t num;
……
#if LWIP_IGMP
/*这个函数在添加或者删除mac地址的多播路由表时被调用*/
err_t (*igmp_mac_filter)( struct netif *netif, struct ip_addr *group, u8_t action);
#endif /* LWIP_IGMP */
#if LWIP_NETIF_HWADDRHINT
u8_t *addr_hint;
#endif /* LWIP_NETIF_HWADDRHINT */
#if ENABLE_LOOPBACK
/* List of packets to be queued for ourselves. */
struct pbuf *loop_first;
struct pbuf *loop_last;
#if LWIP_LOOPBACK_MAX_PBUFS
u16_t loop_cnt_current;
#endif /* LWIP_LOOPBACK_MAX_PBUFS */
#endif /* ENABLE_LOOPBACK */
};
和linux中的网络驱动一样,主要的工作还是补充netif这个网络接口层最重要的结构体,相应的函数自然是收发包的Input,output函数,还有就是arp的linkoutput函数。