Login
升级VIP 登录 注册 安全退出
当前位置: 首页 > word文档 > 合同模板 > LWIP协议栈的分析和设计

LWIP协议栈的分析和设计

收藏

本作品内容为LWIP协议栈的分析和设计,格式为 doc ,大小 375336 KB ,页数为 11页

LWIP协议栈的分析和设计


('《计算机网络与控制》论文LwIP协议栈的分析---《计算机网络与控制》论文LWIP协议栈的分析-1-《计算机网络与控制》论文LwIP协议栈的分析摘要近些年来,随着互联网和通讯技术的迅猛发展,除了计算机之外,大量的嵌入式设备也需求接入网络。目前,互联网中使用的通讯协议基本是TCP/IP协议族,可运行于不同的网络上,本文研究的就是嵌入式TCP/IP协议栈LWIP。文章首先分析了LWIP的整体结构和协议栈的实现,再介绍协议栈的内存管理,最后讲解协议栈应用程序接口。关键词:嵌入式系统;协议;LWIP;以太网AbstractWiththerapiddevelopmentofinternetandcommunicationtechnology,Notonlycomputersbutalsoembededequipmentsareneedtoconnectnetworks.Atpresent,thebasiccommunicationprotocolusingininternetisTCP/IP,itcanrunindifferentnetwork.ThispaperanalysestheLight-WeightTCP/IP.Theprocessmodelofaprotocolimplementationandprocessingofeverylayeraredescribedfirst,andthengivesthedetailedmanagementofBufferandmemory.Atlast,areferencelwIPAPIisgiven.Keywords:EmbeddedSystem,Protocol,LightweightTCP/IP,Ethernet引言-2-《计算机网络与控制》论文LwIP协议栈的分析近期互联网络硬件、软件的迅猛发展,使得网络用户呈指数增长,在使用计算机进行网络互联的同时,各种家电设备、仪器仪表以及工业生产中的数据采集与控制设备在逐步地走向网络化,以便共享网络中庞大的信息资源。在电子设备日趋网络化的背景下,引人TCP/IP协议栈,以支持嵌人式设备接人网络,成为嵌人式领域重要的研究方向。本文分析一个轻量级的嵌入式系统的TCP/IP协议栈-LWIP,LWIP是一个比较完整和可靠的TCP/IP协议栈,具有开源,易用,系统资源要求不高等优点。一、LWIP概览LWIP是瑞典计算机科学院(SwedishInstituteofComputerScience)开发的一套用于嵌入式系统的开放源代码TCP/IP协议栈。LWIP的含义是LightWeight(轻型)IP协议。LWIPTCP/IP实现的重点是在保持TCP协议主要功能的基础上减少处理和内存需求,因为LWIP使用无顺数据复制并经裁剪的API,一般它只需要几十KB的RAM和40KB左右的ROM就可以运行。同时LWIP可以移植到操作系统上,也可以在无操作系统的情况下独立运行。这使LWIP协议栈适合在低端嵌入式系统中使用。LWIP的特性如下:1.支持多网络接口下的IP转发;2.支持ICMP协议;3.支持主机和路由器进行多播的Internet组管理协议(IGMP);4.包括实验性扩展的UDP(用户数据报协议);5.包括阻塞控制,RTT估算和快速恢复和快速转发的TCP;6.提供专门的内部回调接口(rawAPI)用;7.支持DNS;8.支持SNMP;9.支持PPP;10.支持ARP;11.IPfragment的支持;12.支持DHCP协议,动态分配IP地址;13.可选择的Berkeley接口API(多线程情况下);LWIP的源代码从作者AdamDunkels的官方网站上下载(网址为:www.sics.se/~adam/lwip/),版本号为1.3.1。以下为解压后的目录结构。LWIP的目录结构主要分为五个部分:1.Api\\:应用程序接口文件,包括RAW,BSD以及正式提供的3种API。2.Arch\\:与硬件和OS有关的文件,包括网络驱动,移植需要修改的文件。3.Core\\:ICMP,IP,TCP,UDP协议的实现文件,以及一些辅助函数,LWIP实现的核心代码。4.Include\\:LWIP的包括文件。5.Netif\\:ARP协议和LWIP网络设备驱动程序的模板,用户为自己的网络接口设计的驱动程序应该与ethernetif.c中给出的驱动框架相同。二、LwIP的整体构架和进程模型:传统的TCP/IP协议栈的实现方法严格分层,一般每一层都是一个独立的进程。这样方法虽然有利于协议栈的调试,但是,其最大的弊端为数据包跨层传递时会引起频繁的上下文的切换,尤其是在多任务系统中,这样导致时间的浪费而直接影响到系统的实时性。LWIP将所有TCP/IP协议都-3-《计算机网络与控制》论文LwIP协议栈的分析放在在一个进程当中,这样TCP/IP协议栈就和操作系统内核分开了。而应用层程序既可以是单独的进程也可以驻留在TCP/IP进程中。如果应用程序是单独的进程,可以通过操作系统的邮箱、消息队列等通讯机制和TCP/IP进程进行通讯。如果应用层程序驻留在TCP/IP程中,那应用层程序就利用内部回调函数接口(RawAPI)和TCP/IP协议栈通讯。LWIP进程模式的主要优点是可以很方便的移植到各种操作系统上去,进行应用程序的开发。图2-1LWIP的进程模型LwIP的进程模型如图2-1。在图2-1中可以看到整个TCP/IP协议栈都在同一个名为“tcpip_thread”任务中,而位于图中最上方的“Applicationlayer”(应用层)和下方的“Networkinterfacelayer”(网络接口驱动层)由用户自己来实现。应用层程序既可以是独立的任务(如图中正上方的“tftp_thread”和“tcpecho_thread”),通过mbox(消息队列)和LWIP进程通讯;也可以在“tcpip_thread”(如图左上角)中利用原始接口(RawAPI)和TCP/IP协议栈通讯。LWIP的数据流程主要分为接收和发送两种情况。●接收数据时:数据包从一个网络接口被接收,如果网络接口驱动通过low_level_input函数读到这个数据包,简单的区分是ARP包还是IP包。如果是ARP包,将调用ARP的功能处理这个包。通常将更新一个ARP地址映射表,然后将数据包发送给IP_input函数处理。如是查一个IP包,将把数据包发送给ip_input函数处理。IP_input函数将数据包进行简单的处理(如计算校验和)后,分析该包是发送到本机的正常数据包,IP_input则根据包的类型,分别发送给udp_input、tcp_input、icmp_input函数处理。如果是发送给UDP或TCP协议的数据包,UDP、TCP协议的处理函数将做相应的处理,最后发送给应用程序。●发送数据流程:当应用程序需要发送一个数据包的时候,它将调用UDP和TCP协议处理函数-4-《计算机网络与控制》论文LwIP协议栈的分析udp_sender或tcp_write函数发送该数据包。UDP和TCP协议的处理函数接收数据后,将数据打包、分段,然后发送给IP层ip_output_if函数(需要时,将调用ip_route函数进行路由选择),该函数把数据打包、封装,然后调用网络接口驱动的low_level_output函数传给网络接口。三、LWIP协议栈的实现3.1网络接口LwIP使用一个与BSD中相似的网络接口结构来表示底层网络驱动,结构体的原型定义如下所示。structnetif{structnetifnext;charname[2];intnum;structip_addrip_addr;structip_addrnetmask;structip_addrgw;void(input)(structpbufp,structnetifinp);int(output)(structnetifnetif,structpbufp,structip_addripaddr);voidstate;}next指针用于将网络接口链入到全局链表中。Name域用于表示网络接口的类型,只用于这个接口在运行时由人工操作进行配置。Name由设备驱动设置并且应该反映硬件的种类。num用来区分相同类别的不同网络接口。三个IP地址ip_addr,netmask与gw分别用来表示IP地址,子网掩码,网关。State表示设备驱动所包含的网络接口状态,由设备驱动设置。当设备驱动接受到一个信息包的时候需要调用input指向的函数。而网络接口通过output指针与设备驱动连接。这个指针指向处于设备驱动中的发送信息包的函数,这个函数将在一个信息包发送出去后,被IP层调用。指针output将在设备驱动初始化的时候赋值。3.2IP处理LwIP仅实现了IP层大部分的基本功能,能够发送、接收以及转发信息包,但是不能接收和发送IP分片包,也不能处理携带IP参数选项的信息包。不过对大多数的应用来说,这不会引起任何问题。●接收信息包收到的IP信息包,由网络设备驱动调用ip_input()函数开始处理。在这里完成对IP版本字段及包头长度的初始完整性检查,同时还要计算和验证包头校验和。协议栈假定代理会重新组合IP分片包为一个完整的包。接下来,函数检查目的地址是否与网络接口的IP地址相符以确定信息包是否到达预定主机。网络接口在链表中被排序并且采用了线性检索。如果一个到达的信息包被发现已经到达了目的主机,则由协议字段来决定信息包应该传送到哪一个上层协议。●发送信息包外发的信息包由ip_output()函数处理,该函数使用ip_route()函数查找适当的网络接口来传送信息包。当外发的网络接口确定后,信息包传给以外发网络接口为参数的ip_output_if()函数。在这里,所有的IP包头字段被填充,并且计算IP包头校验和。IP信息包的源及目标地址作为参数-5-《计算机网络与控制》论文LwIP协议栈的分析被传递给ip_output_if()函数。●转发信息包如果没有网络接口的地址与到达的信息包的目标地址相同,信息包应该被转发。这项工作由ip_forward()函数完成。在这里,TTL字段值被减少(TimeToLive的简写,生存时间的意思,译者注),当减为0的时候,将会给IP信息包的最初发送者发送ICMP错误信息,并抛弃该信息包。最后,信息包被转发到适当的网络接口。查找适当的网络接口的算法与发送信息包使用的算法相同。●ICMP处理网际控制报文协议ICMP(IntemetControlMessageProtoc01)总是与IP协议配置在一起,它运行在IP协议之上,发送一些控制信息,帮助Intemet处理差错。ICMP处理是相当简单的。由ip_input()收到的ICMP包被移交到icmp—input(),它解析ICMP报头并且进行适当的处理。ICMP处理过程如图3-1所示图3-1ICMP处理3.3UDP处理用户数据报协议UDP(UserDatagramProtoc01)较为简单,输出处理也较简单,基本的UDP处理过程被分割为三个功能函数来实现:如图3-2所示。\uf075udp_input()函数与UDP输入有关\uf075udp_send()及udp_output()则用于UDP输出图3-2UDP处理3.4TCP处理传输层控制协议TCP为应用层提供可靠的二进制数据流服务。TCP协议比这里描述的其它协议都要复杂,基本TCP处理如图3-3所示,被划分成六个函数:函数-6-《计算机网络与控制》论文LwIP协议栈的分析tcp_input()、tcp_process()、tep_receive()与TCP输入处理有关;tep_write()、top_enqueue()、tcp_output()对输出进行处理。当应用程序想要发送TCP数据时,函数tcp_write()将被调用,函数tcp_write()将控制权交给tcp_enqueue(),该函数将数据分成合适大小的TCP段(如果必要),并放进发送队列。接下来函数top_output()将检查数据是否可以发送。也就是说,如果接收器的窗口有足够的空间并且拥塞窗口足够大,则使用ip_route()和ip_output_if()两个函数发送数据。当ip_input()对IP报头进行检验且把TCP段移交给tcp_input()函数后,输入处理开始。在该函数中将进行初始检验(也就是checksumming和TCP剖析)并决定该段属于哪个TCP连接。该段于是由tcp_process()处理,它实现TCP状态机和其他任何必须的状态转换。如果一个连接处于从网络接收数据的状态,函数tcp_receive()将被调用。如果那样,tcp_receive()将把段上传给应用程序。如果段构成未应答数据(先前放入缓冲区的)的ACK,数据将从缓冲被移走并且收回该存储区。同样,如果接收到请求数据的ACK,接收者可能希望接收更多的数据,这时tcp_output()将被调用。图3-3TCP处理四、LWIP协议栈的内存管理4.1LWIP协议栈中pbuf介绍TCP/IP是一种基于OSI参考模型的分层网络体系结构,它由应用层、运输层、网络层、数据链路层、物理层组成。各层之间消息的传递通过数据报的形式进行。由于各层之间报头长度不一样,当数据在不同协议层之间传递时,对数据进行封装和去封装、增加和删除操作将十分频繁。因此,必须有一种能适应数据动态增删、但在逻辑上又呈现连续性的数据结构,以满足在各协议层之间传递数据而不需要进行内存拷贝。嵌人式TCP/IP协议栈要求简单高效,并减少对内存的需求。这些都需要相应的内存管理机制实现。LwIP利用pbuf结构实现数据传递,它与BSD中的Mbuf很相似。pbuf的主要用途是保存在应用程序和网络接口间互相传递的用户数据。pbuf的内部结构为:structpbuf{structpbufnext;/指向下一个pbuf/voidpayload;/指向pbuf数据中的起始位置1ul6_ttot_len;/该pbuf和后续pbuf中数据.长度的总和u16_tlen;/该pbuf中数据的长度/u16-tflags;/pbuf的类型/-7-《计算机网络与控制》论文LwIP协议栈的分析ul6_tref;/该pbuf被引用的次数/}4.2LWIP内存管理的实现在运行TCP/IP协议栈的嵌人式系统中,可以把整个系统的存储区域分为协议栈管理的存储器和应用程序管理的存储器两部分。4.2.1协议栈管理的存储器协议栈管理的存储器是指TCP/IP内核能够操作的内存区域,主要用于装载待接收和发送的网络数据分组。当接收到分组或者有分组要发送时,TCP/IP协议栈为这些分组分配缓存;接收到的分组交付给应用程序或者分组已经发送完毕后,对分配的缓存回收重用。协议栈分配的缓存必须能容纳各种大小的报文,例如从仅仅几个字节的ICMP回答报文到几百个字节的TCP分段报文。LWIP中的pbuf有四种类型;PBUF_POOL、PBUF_RAM、PBUF_ROM、PBUF_REF。这四种类型的pbuf都是从TCP/IP协议栈管理的存储器中分配的,其中PBUF_ROM和PBUF_REF与应用程序管理的存储区域密切相关。PBUF_POOL是具有固定容量的pbuf,主要供网络设备驱动使用,为收到的数据分组分配缓存。在协议栈管理的内存中初始化了一个pbuf池(PBUF_POOL),具有相同尺寸的pbuf都是从这个pbuf池中分配得到。一般使用多个PBUF_POOL链接成一个链表,用于存储数据分组。如图1所示。图4–1PBUF_POOL链表LwIP用一个宏定义一个PBUF_POOL的大小。一个分组需要分配几个PBUF_POOL,而在数据较少时分配一个PBUF_POOL即可。由于分配一个PBUF_POOL类型的pbuf很快,适合在中断处理中使用,所以PBUF_POOL主要供网络设备驱动使用,为收到的数据分组分配缓存。应用程序发送动态产生的数据时,可以用PBUF_RAM类型的pbuf。PBUF_RAM在事先划分好的内存堆中分配。对该内存堆的操作类似于C语言中的malloc/free。内存堆分配的结构如图4-2所示。图2中每个被分配的存储块附带了一个小结构,该结构的两个指针指向相邻的内存块。used标识位用来指示该内存块的分配情况,阴影部分表示已经被分配了,此时used为1。当需要一块N字节的存储块时,就对整个存储堆进行搜索。如果找到一块未用的(used=0)并且容量不小于N字节的区域就表示分配成功,并且置use为I。而分配的内存块使用完后需要释放,为了不产生碎片,相邻且未用的内存块需要进行合并。PBUF_POOL和PBUF_RAM都可以根据需要从存储器中动态分配,这种分配机制又称为动态存储器分配机制。该分配机制不仅能为应用程序的数据分配存储空间,而且能为协议首部分配存储空间。在层与层之间传递数据时,真正需要修改的只是数据的格式,使之符合各层的规范,而数据本身不需-8-图4-2内存堆《计算机网络与控制》论文LwIP协议栈的分析要变动。实际上数据格式反应的是各层的首部,当数据在各层之间传送时,需要动态地添加和移去相应的首部,用动态分配机制可以很好地实现。4.2.1应用程序管理的存储器应用程序管理的存储器是指应用程序管理、操作的存储区域,二般从该区域为应用程序发送数据分配缓存。虽然该存储区域不由TCP/IP协议栈管理,但在不严格分层的协议栈中,该存储区域必须与TCP/IP管理的存储器协同工作。为节省内存,LWIP不采取分级访问模式,而是通过指针访问数据。这样就不需要为数据的传递分配存储空间。应用程序发送的数据在交付LWIP后,LWIP就认为这些数据是不能被改动的,因此应用程序的数据被认为是永远存在并且不能被改变的。这一点与ROM很相似。类型名PBUF_ROM也由此而来。如图4-3所示,PBUF_ROM的数据指针payload指向Externalmemory(外部存储区)。Externalmemory指不由TCP/IP协议栈管理的存储区,它可以是应用程序管理的存储器为用户数据分配的缓存,也可以是ROM区域,如静态网页中的字符串常量等。由于由应用程序交付的数据不能被改动,因此就需要动态地分配一个PBUF_RAM来装载协议的首部,然后将PBUF_RAM(首部)添加到PBUF_ROM(数据)的前面。这样就构成了一个完整的数据分组。图4-3PBUFRAM与PBUFROM的连接图4-3中的PBUF_ROM还可以是PBUF_REF。PBUF_REF和PBUF_ROM的特性非常相似,都可以实现数据的零拷贝。但是当发送的数据需要排队时就表现出PBUF_REF的特性了。例如在发送分组时,待发送的分组需要在ARP队列中排队,假如这些分组中有PBUF_ROM类型的pbuf,则说明该类型pbuf中的数据位于应用程序的存储区域,是通过指针被PBUF_ROM引用的。这样直到分组被处理之前,被引用的应用程序的这块存储区域都不能另作它用。在此情况下要用到PBUF_REF类型的pbuf。在排队时,LWIP会为PBUF_REF类型的pbuf分配缓存(PBUF_POOL或PBUF_RAM),并将引用的应用程序的数据拷贝到分配的缓存中。这样应用程序中被引用数据的存储区域就能被释放。pbuf结构实现了层与层之间的数据传递,但其非常消耗内存,并且需要TCP/IP协议栈为之分配存储空间,例如协议控制udp_pcb,tcp-pcb等。通常,嵌人式TCP/IP协议栈都不是严格分层的,尽量减少对内存的需求是实现嵌人式TCP/IP的重点,内核的内存管理机制直接关系到嵌人式TCP/IP协议栈的性能。五、LWIP的应用编程接口(API)LwIP为我们提供了三种应用程序接口(API函数)来实现TCP/IP协议栈,它们分别是:1.low-level"core"/"callback"or"raw"API.是一种低水平的、基于回调函数的API(后面直接称RAWAPI),整个通信流程依靠协议栈里-9-《计算机网络与控制》论文LwIP协议栈的分析的回调函数来驱动。因为回调函数的调用不能超越任务边界,这样应用程序和TCP/IP协议栈必须运行在同一个任务中,而用户不再增加其它的任务,应用程序直接在TCP/IP任务空间运行。因此,就要避免调用诸如挂起、等待的函数,以防止整个TCP/IP任务被挂起。RAWAPI接口函数不仅在程序代码的执行时间上更快,而且在运行中它也占用更少的内存资源。唯一的缺点是应用程序的编写比较困难,并且代码较难理解。尽管如此,在CODE和RAM都较小的嵌入式系统中,这也是我们优先考虑采用的方法。2.higher-level"sequential"API/LWIPAPI是一种高水平的、连续的API,LWIPAPI为我们提供了一种通用的方法,它与BSD标准的socketAPI非常相似,程序的执行过程同样是基于"open-read-write-close"模型的,但操作相对低级。API不需要在应用程序和协议栈之间复制数据,因为应用程序可以巧妙的直接处理内部缓冲区。(充分利用LwIP的内部结构以实现其设计目标)因为BSDSocketAPI易于理解,并且很多应用程序为它而写,所以LwIP保留一个BSDSocket兼容层是很有用的。尽管LwIP与BSDSocketAPI非常相似,但是它们之间仍然存在着值得注意的区别,使用BSDSocketAPI的应用程序不必知道普通文件和网络连接的差别,而使用LwIPAPI的应用程序就必须知道正在使用的是一个网络连接。它不适合于应用在比较小的嵌入式系统中,因为它的实现要求应用程序必须支持多线程。从本质上讲,TCP/IP协议栈的通信过程是事件驱动的,因此,TCP/IP的代码和用户应用程序的代码,应该在不同的线程里面。当然,在不同的应用程序中,这两种API我们可以同时采用。实际上,sequentialAPI就是一种利用RAWAPI来实现的一种属于协议本体的应用程序。3.BSDSocketAPIBSDSocketAPI在连续的内存区域处理数据非常便于编写应用程序。因为应用程序内的数据处理通常是在这样的连续内存区域内进行的。但是,对于LwIP,采用这种机制不具备任何优势。特别是BSDSocket需要将要发送的数据从应用程序复制到TCP/IP协议栈的内部缓冲区。复制数据的原因是应用程序与TCP/IP协议栈通常驻留在不同的受保护空间。大多数情况是应用程序是一个用户进程,而TCP/IP协议栈则驻留在操作系统内核。通过避免额外的复制操作,API的性能可以大幅度提升。同样,为了复制数据,系统还需要为此分配额外的内存,这样每一个信息包都需要使用双倍的内存。虽然LWIP提供了一些接口函数,但操作相对低级,使用起来不方便,不利用于后续开发。由于BSDSOCKETAPI很容易理解且己经有很多人为它写过应用程序,且应用程序使用BSDSOCKETAPI时候不需要知道普通文件和网络连接之间的差别,所以为了便要理解和应用,LWI提供了基于LWIP接口函数的BSDSOCKETAPI,但没有任何容错机制,没有select()与poll()函数。以下就一些重要的SOCKETAPI函数做一介绍。(1)socket()函数用于创建网络通信的套接字,并返回该套接字的整数描述符。函数原型为intsocket(intdomain,inttype,intprotocol),其中参数domain代表协议族或地址族,对于TCP/IP为PF_INET或AF_INET;type代表服务类型,对于TCP为SOCK_STREAM(流式),对于UDP为SOCK-DGRAM(数据报);protocol代表使用的协议号,对于TCP为IPPROTO_TCP,对于UDP为IPPROTO_UDP,传递0表示根据协议族和给定的服务类型选择默认的协议号。若socket成功返回,返回大于或等于0的有效套接字描述符,返回一1表示发生了差错。(2)bind()函数将BSDsocket绑定到本地(本机)地址上。在调用bind()时,本地IP地址和端口号将被指定。(3)connect()允许调用者为先前创建的套接字指明远程端点的地址。如果套接字使用TCP,该函数就使用三次握手建立连接;如果套接字使用UDP,则仅指明远程端点,但不向它传送任何数据报。(4)listen()使套接字处于被动状态(即准备接受传入的连接请求)。在服务器处理某个请求时,协议软件应将后续收到的请求排队,listen也设置排队的连接请求的数目。listen只用于TCP套接字。-10-《计算机网络与控制》论文LwIP协议栈的分析(5)accept()函数被用来等待TCPsocket口上的输入连接。在此之前,这个TCPsocket口通过调用listen()已经被设置成监听状态,对accept()调用一直被阻塞,直到与远程主机建立连接。(6)send()数在UDP和TCP两种连接中被用来发送数据。在调用send()前,数据接收器必须被设置成正在使用connect(),应用程序在调用send()后可以直接修改发送的数据。(7)sendto()调用函数与send()调用函数类似,但是在参数调用中他们允许应用程序指定数据接收器。sendto()仅能在UDP连接中使用,实现这功能要使用netconnconnect()来设置数据包接收器。如果以前socket口被连接,必须重设远程IP地址和端口号。(8)write()调用函数通过连接来发送数据并且能在UDP和TCP连接中使用。参考文献[1]W.RichardStevens著.TCP/IP详解卷1:协议.范建华等译.机械工业出版社.2000[2]GaryR.Wright,W.RichardStevens著.TCP/IP详解卷2:实现..陆雪莹等译.机械工业出版社.2000[3]W.RichardStevens著.TCP/IP详解卷三:TCP事务协议,HTTP,NNTP和UNIX域协议.胡谷雨,昊礼发等译.机械工业出版社.2000[3]JanAxelson.编著.嵌入式Ethernet和internet通信设计技术.骆丽,张岳强,欧小龙译.北京:北京航空航天大学出版社,2006.1[4]焦海波,刘健康.编著.嵌入式网络系统设计—基于AtmelARM7,北京:北京航空航天大学出版社,2008.4[5]AdamDunkels.DesignandImplementationofthelwIPTCP/IPStack,Feb20,2001[6]Jea.Labrosse.编著.嵌入式实时操作系统uC/OS-II(第二版).邵贝贝等译.北京:北京航空航天大学出版社,2003.5[7]DouglassE.Comer,DavidL.Stevens著.用TCP/IP进行网际互连第二卷—设计、实现与内核:ANSIC版(第三版).张娟王海等译北京:电子工业出版社,2008.10[8]BSDSocketsInterfaceProgrammer’sGuideEdition6.HPCompany[9]GuidoMoritz,SteffenPrüter,WebservicesonDeeplyEmbeddedDeviceswithReal-TimeProcessingProconETFA\'08.IEEE[10]邱书波,陈伟,基于ARM的轻量级TCP/IP协议栈的研究及移植计算机应用与软件,2009.8[11]王海波,基于以太网的LED图文显示系统的设计,大连理工大学硕士学位论文,2006.12[11]彭义波,uCOS与TCPIP协议栈的分析与移植,华中师范大学硕士学位论文,2005.6[12]付晓军,夏应清,何轩,嵌入式LWIP协议栈的内存管理,嵌入式技术,2005.10和以下相关网站:http://savannah.nongnu.org/projects/lwiphttp://lwip.wikia.com/wiki/LwIP_Wikihttp://www.21ic.com-11-',)


  • 编号:1700665516
  • 分类:合同模板
  • 软件: wps,office word
  • 大小:11页
  • 格式:docx
  • 风格:商务
  • PPT页数:375336 KB
  • 标签:

广告位推荐

相关合同模板更多>