LWIP移植说明及程序分析

LWIP移植说明及程序分析
LWIP移植说明及程序分析

LWIP移植说明及程序分析

新哥NUAA(技术交流279141909)2015年8月

说在前面

LWIP,这个轻量级的TCP/IP协议,说来惭愧,把我虐得够惨的,今天算是第三次接触lwip了,第一次是认真看了别人移植可以ping通的程序,后来我也参照野火的以太网文档一步步的移植了一次,但不管怎么调都有bug!bug!bug!一气之下就不想再碰了!!这两天想想又很不甘心,于是乎,我又开始移植起来~~~

移植要点

这次也首先是基于无操作系统的移植,在后期再移植基于ucou2的网络协议。那么在这里我就首先带领那些炙热于lwip协议但又因网上的移植资料残缺不全而苦无移植良策的同志们来一次彻底的lwip移植吧(好长,说的我好累)!

本文档是基于stm32f103+ENC28J06的移植(如果是stm32f107就不是这种方法了,107处理器自带MAC控制器,只需要外接一个PHY控制器和以太网变压器就可以实现以太网功能。)我发现上一次移植是照葫芦画瓢,完全没有理解移植的要点,在这里我简单的总结一下移植要点和出现bug的原因吧。

移植要点1:复制opt.h文件到新建的lwipopt.h文件,并按照处理器资源与实际需求修改。(虽然lwipopt.h是有opt.h文件修改得到的,但opt.h文件仍然有用,里面涉及到的条件编译在协议的正常运行中是必要的,在keil4中要同样包含在路径中。换句话说,只要在其他文件里没有对opt.h中条件编译的对象进行重定义,那么就要以opt.h中的条件编译为准,如果读者删掉opt.h后可以看到很多bug)。

移植要点二:编写enc28j60的驱动文件(含头文件)。(函数模块包括读控制寄存器、向以太网控制器写入命令、读取buff的数据、向buffer写入数据、选定将要操作的bank、读取控制寄存器的内容、写入数据到控制寄存器、向PHY写入控制参数、初始化以太网控制器、发送数据包函数、接收数据包函数)。以上括号中的函数可以查看enc28j60的datasheet 自己写,也可以网上下载借鉴别人写好的。

移植要点三:编写网络处理函数netconfig.c(与对应的netconfig.h)。主要是初始化lwip 协议栈、以及做一些系统时钟中断等处理。这一句将enc28j6与lwip连接起来:netif_add(&enc28j60, &ipaddr, &netmask, &gw, NULL, ðernetif_init, ðernet_input); ethernetif_init, ethernet_input是lwip协议中neif与外设接口的函数。

移植要点四:修改路径为\LWIP\lwip-1.3.2\lwip-1.3.2\src\netif中ethernetif.c文件。原协议栈中ethernetif.c只提供了一些子函数的模板,要实现通信功能还要根据网卡(enc28j60)进一步修改。需修改的子函数有:网卡初始化函数(low_level_init)、底层发送数据函数(low_level_output)、底层接收数据函数(low_level_input)、数据输入处理函数(ethernetif_input)。

对以上四个要点进行正确的配置后,就完成了移植步骤的一大半了。但移植的最大问题往往不是出在这儿。往往是读者对keil的不熟悉,比方说头文件路径是不是正确的包含了,这往往是出现bug的根本原因所在。

移植过程

好了,说完以上要注意的要点后,其实我们对lwip的移植过程也有一个大体的了解。那接下来我们就真正手把手去移植lwip吧,在移植的过程中呢,带读者简要分析一下程序,

就当做学习一下嵌入式及编程咯。

Step1:

在移植的时候,我们也常常需要利用contrib-1.3.0.zip 中的文件。解压后,在

\contrib-1.3.2_\contrib\ports 目录下有一些针对特定平台移植时使用的文件,选择进入其中

一个目录,如\contrib-1.3.0_\contrib\ports old\6502\include\arch。

我们需要用到的是cc.h、perf.h(不需修改)和sys_arch.h (可以暂不移植,根据操作系统而定)文件,通常把它复制出来存放到自己工程中的arch 文件夹中。cc.h 包含了LwIP 对于基本数据类型的定义。perf.h文件是和系统统计和测量有关的头文件,sys_arch.h 定义了

与系统有关的信号量、邮箱及线程(这里是基于无操作系统的移植暂时不需要对其进行更改)。其中cc.h要根据编译器平台与处理器平台等进行修改。还有一个lwipopt.h文件也要根据

\LWIP\lwip-1.3.2\lwip-1.3.2\src\include\lwip中的opt.h文件进行修改。

(其实lwiopts.h起名无所谓,只要将opt.h中包含的头文件lwipopts.h改为你新建的.h文件一致就可以了,但里面的内容配置包含用户对协议栈内核的参数配置,要根据实际情况进行更改,有时候严格按照文档对应来更改也会出错,可能要删除opt.t中的条件编译,尽量简洁明朗一点,其中

#define NO_SYS 1

#define LWIP_NETCONN 0

这两个是很重要的!定义错了或不定义都会导致bug!!)

Step2:

在完成以上的三个文件的移植后,就已经完成一小部分工作量,虽然很简单,但一定要细心哦亲!接下来看一下enc28j60的驱动文件吧。这部分文件批量购买的话芯片公司会提供源代码,也可以通过论坛等途径下载到的,需要考验读者的信息搜索能力啦!

/****************************************************

* 函数名:main.c

* 描述:main

* 输入:无

* 输出:无

****************************************************/

#include "include.h"

__IO uint32_t LocalTime = 0;

int main(void)

{

uart_init(9600); //串口初始化为9600

ENC_SPI_Init();

SysTick_Init(); //延时函数初始化

/*初始化完成之后,通过下面的心跳函数

直接通过结构体neif->input(ethernet_input())进行对函数的访问了

说明:

ethernet_input()和ethernetif_input这两个函数是有区别的,

ethernetif_input是调用ethernet_input函数的,但是初始化neif_add结构体的时候还是ethernet_input这个函数。*/

LwIP_Init();

httpd_init();

while ( 1 )

{

/*轮询*/

LwIP_Periodic_Handle(LocalTime);

}

}

在以上程序LwIP_Init()中有一句程序语句为:

netif_add(&enc28j60, &ipaddr, &netmask, &gw, NULL, ðernetif_init, ðernet_input);

其中ethernetif_init, ethernet_input将LWIP协议与enc28j60结合起来了,实现了网卡的网络功能。ethernetif_init中的low_level_init( netif )是网卡初始化函数(包括mac地址写入网卡及网卡的初始化。mac地址结构为00:00:00:00:00:00:00,48位,其中前三个为芯片生产商定义的,后面三个可以认为定义,如果前面的数据随意改动了再编译的话,结果一想而知:有bug!!)下面就结合enc28j60的datasheet分析一下以太网的初始化程序:

/****************************************************

* 函数名:enc28j60Init

* 描述:初始化以太网控制器

* 输入:MAC地址

* 输出:无

****************************************************/

void enc28j60Init(u8 * macaddr)

{

/* CS端口为输出*/

01// ENC28J60_RSTH();

/* 禁止ENC28J60 */

02 ENC28J60_CSH();

/* ENC28J60软件复位该函数可以改进*/

03 enc28j60WriteOp(ENC28J60_SOFT_RESET, 0, ENC28J60_SOFT_RESET);

/* 设置接收缓冲区起始地址该变量用于每次读取缓冲区时保留下一个包的首地址*/

04 NextPacketPtr = RXSTART_INIT;

/* 设置接收缓冲区起始指针*/

05 enc28j60Write(ERXSTL, RXSTART_INIT & 0xFF);

06 enc28j60Write(ERXSTH, RXSTART_INIT >> 8);

/* 设置接收缓冲区读指针*/

07 enc28j60Write(ERXRDPTL, RXSTART_INIT & 0xFF);

08 enc28j60Write(ERXRDPTH, RXSTART_INIT >> 8);

/* 设置接收缓冲区结束指针*/

09 enc28j60Write(ERXNDL, RXSTOP_INIT & 0xFF);

10 enc28j60Write(ERXNDH, RXSTOP_INIT >> 8);

/* 设置发送缓冲区起始指针*/

11 enc28j60Write(ETXSTL, TXSTART_INIT & 0xFF);

12 enc28j60Write(ETXSTH, TXSTART_INIT >> 8);

/* 设置发送缓冲区结束指针*/

13 enc28j60Write(ETXNDL, TXSTOP_INIT & 0xFF);

14 enc28j60Write(ETXNDH, TXSTOP_INIT >> 8);

/* 使能单播过滤使能CRC校验使能格式匹配自动过滤*/

15 enc28j60Write(ERXFCON, ERXFCON_UCEN | ERXFCON_CRCEN | ERXFCON_PMEN);

16 enc28j60Write(EPMM0, 0x3f); //格式匹配字节

17 enc28j60Write(EPMM1, 0x30); //格式匹配字节

18 enc28j60Write(EPMCSL, 0xf9); //格式匹配字节

19 enc28j60Write(EPMCSH, 0xf7); //格式匹配字节

/* 使能MAC接收允许MAC发送暂停控制帧当接收到暂停控制帧时停止发送*/

20 enc28j60Write(MACON1, MACON1_MARXEN | MACON1_TXPAUS | MACON1_RXPAUS);

/* 退出复位状态*/

21 enc28j60Write(MACON2, 0x00);

/* 用0填充所有短帧至60字节长并追加一个CRC 发送CRC使能帧长度校验使能MAC全双工使能*/

/* 提示由于ENC28J60不支持802.3的自动协商机制,所以对端的网络卡需要强制设置为全双工*/

22 enc28j60WriteOp(ENC28J60_BIT_FIELD_SET, MACON3, MACON3_PADCFG0 |

MACON3_TXCRCEN | MACON3_FRMLNEN | MACON3_FULDPX );//MACON3_HFRMLEN /* 填入默认值*/

23 enc28j60Write(MAIPGL, 0x12);

/* 填入默认值*/

24 enc28j60Write(MAIPGH, 0x0C);

/* 填入默认值*/

25 enc28j60Write(MABBIPG, 0x12);

/* 最大帧长度*/

26 enc28j60Write(MAMXFLL, MAX_FRAMELEN & 0xFF);

27 enc28j60Write(MAMXFLH, MAX_FRAMELEN >> 8);

/* 写入MAC地址*/

28 enc28j60Write(MAADR5, macaddr[0]);

29 enc28j60Write(MAADR4, macaddr[1]);

30 enc28j60Write(MAADR3, macaddr[2]);

31 enc28j60Write(MAADR2, macaddr[3]);

32 enc28j60Write(MAADR1, macaddr[4]);

33 enc28j60Write(MAADR0, macaddr[5]);

/* 配置PHY为全双工LEDB为拉电流*/

34 enc28j60PhyWrite(PHCON1, PHCON1_PDPXMD);

/* 半双工回环禁止*/

35 enc28j60PhyWrite(PHCON2, PHCON2_HDLDIS);

/* 返回BANK0 */

36 enc28j60SetBank(ECON1);

/* 使能中断全局中断接收中断接收错误中断*/

37 enc28j60WriteOp(ENC28J60_BIT_FIELD_SET, EIE, EIE_INTIE | EIE_PKTIE);

/* 接收使能位*/

38 enc28j60WriteOp(ENC28J60_BIT_FIELD_SET, ECON1, ECON1_RXEN);

}

程序分析:(以此为例带读者学习一下如何看datasheet编写驱动程序)

02ENC28J60_CSH();是一个宏定义,#define ENC28J60_CSH() (GPIOB->ODR |= 1<<12),表示将PB12置为高电平,因为在硬件接线时PB12接ENC28J60的CS端(片选),高电平表示禁止使用此网卡。

04~14 设置接收/发送缓冲区,根据datasheet的地址查询,分离出高低地址。

分离低地址:(以起始指针为例)enc28j60Write(ERXSTL, RXSTART_INIT & 0xFF);保留低8位即可;分离高地址:enc28j60Write(ERXSTH, RXSTART_INIT >> 8);将地址右移8位,保留高八位即可。其中,ERXSTL与ERXSTH都是宏定义,如下:

#define ERXSTL (0x08|0x00)

#define ERXSTH (0x09|0x00)

Datasheet中bank0的地址映射如下图所示。因为是bank0所以(0x08|0x00)。若是bank1,则(0x08|0x20)。

15 enc28j60Write(ERXFCON, ERXFCON_UCEN | ERXFCON_CRCEN | ERXFCON_PMEN);请详细看一下过滤器ERXFCON,后面几个都是它的数据位,都宏定义了,查看后可知ERXFCON被赋值为1011 0000。具体表示什么意义可以详细查看datasheet。如下图所示:(ERXFCON的地址映射位于bank1的0x18h。)#define ERXFCON (0x18|0x20)

其他的就不逐条解释了,都大同小异,看datasheet就可搞定一切。在完成网卡的驱动程序时,将网卡和mcu相连接的程序也要写好。因为硬件是怎么连接的也会影响驱动程序怎么写的对吧!但在此重申一下,自己动手写这部分的驱动文件还是挺费事的,建议小伙伴们发挥自己信息搜索能力尽量下载或拷贝吧!这都是用的比较成熟的了,好了废话不多说了,接下来我

们该干嘛呢?让我们进入第三步吧!

Step3:

诚如移植要点三所述:网络处理函数netconfig.c(与对应的netconfig.h)。主要是初始化lwip协议栈、以及做一些系统时钟中断等处理。这一句将enc28j6与lwip连接起来:netif_add(&enc28j60, &ipaddr, &netmask, &gw, NULL, ðernetif_init, ðernet_input); ethernetif_init, ethernet_input是lwip协议中neif与外设接口的函数。

这部分的函数比较固定,在此附上源码:(节选)

/****************************************************

* 函数名:LWIP_Init

* 描述:初始化LWIP协议栈,主要是把enc28j60与LWIP连接起来。

包括IP、MAC地址,接口函数

* 输入:无

* 输出: 无

****************************************************/

void LwIP_Init(void)

{

struct ip_addr ipaddr;

struct ip_addr netmask;

struct ip_addr gw;

/* Initializes the dynamic memory heap defined by MEM_SIZE.*/

/*内存堆的初始化函数,主要是告知内存堆的起止地址,以及初始化空闲列表,

由lwip初始化时自己调用,该接口为内部私有接口,不对用户层开放*/

mem_init();/*初始化由MEM_SIZE定义的动态内存堆*/

/*内存池的初始化,主要是为每种内存池建立链表memp_tab,其链表是逆序的,

此外,如果有统计功能使能的话,也把记录了各种内存池的数目。*/

memp_init();/*初始化由MEMP_NUM_x定义的内存池.*/

lwip_init();

IP4_ADDR(&ipaddr, 192, 168, 1, 18);

IP4_ADDR(&netmask, 255, 255, 255, 0);

IP4_ADDR(&gw, 192, 168, 1, 1);

/*初始化enc28j60与LWIP的接口,参数为网络接口结构体、ip地址、

子网掩码、网关、网卡信息指针、初始化函数、输入函数*/

/* 传入两个函数的指针,这样的话,函数才能访问得到这两个函数呢*/

netif_add(&enc28j60, &ipaddr, &netmask, &gw, NULL, ðernetif_init, ðernet_input);

/*把enc28j60设置为默认网卡.*/

netif_set_default(&enc28j60);

netif_set_up(&enc28j60); //使能enc28j60接口

}

/****************************************************

* 函数名:LwIP_Periodic_Handle

* 描述:lwip协议栈要求周期调用一些函数,LwIP的周期性任务

tcp_tmr etharp_tmr dhcp_fine_tmr dhcp_coarse_tmr

* 输入:无

* 输出: 无

****************************************************/

void LwIP_Periodic_Handle(__IO uint32_t localtime)

{

if(localtime - INPUT_Timer >= INPUT_TMR_INTERVAL)

{

/*一旦网卡接收到数据,应调用ethernetif_input函数

调用该函数让数据进入LwIP协议栈。*/

ethernetif_input(&enc28j60); //轮询是否接收到数据

}

/* TCP定时处理every 250 ms */

if (localtime - TCPTimer >= TCP_TMR_INTERVAL)

{

TCPTimer = localtime;

tcp_tmr(); //每250ms调用一次

}

/* ARP定时处理every 5s */

if (localtime - ARPTimer >= ARP_TMR_INTERVAL)

{

ARPTimer = localtime;

etharp_tmr(); //每5s调用一次

}

}

Step4:

在对以上程序进行编译及移植后,其中netif_add(&enc28j60, &ipaddr, &netmask, &gw, NULL, ðernetif_init, ðernet_input);是一条非常重要的语句。ethernetif_init,是网卡初始化函数,其由lwip协议栈已经完全编好,代码如下:

err_t ethernetif_init( struct netif *netif )

{

struct ethernetif *ethernetif;

ethernetif = mem_malloc( sizeof(struct ethernetif) );

if( ethernetif == NULL )

{

LWIP_DEBUGF( NETIF_DEBUG, ("ethernetif_init: out of memory\n\r") );

return ERR_MEM;

}

netif->state = ethernetif;

netif->name[0] = IFNAME0;

netif->name[1] = IFNAME1;

netif->output = etharp_output;

netif->linkoutput = low_level_output;

ethernetif->ethaddr = ( struct eth_addr * ) &( netif->hwaddr[0] );

low_level_init( netif );

return ERR_OK;

}

但以上程序不是最底层的,low_level_init、low_level_output才是底层的驱动函数,lwip只提供了一个模板,需要读者自己去完善。

/*-----------------------------------------------------------*/

static void low_level_init( struct netif *netif )

{

/* set MAC hardware address length */

netif->hwaddr_len = 6;

/* set MAC hardware address */

/* MAC地址*/

netif->hwaddr[0] = macaddress[0];

netif->hwaddr[1] = macaddress[1];

netif->hwaddr[2] = macaddress[2];

netif->hwaddr[3] = macaddress[3];

netif->hwaddr[4] = macaddress[4];

netif->hwaddr[5] = macaddress[5];

/* 最大传输单元*/

netif->mtu = netifMTU;

netif->flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_LINK_UP;

enc28j60Init(netif->hwaddr); //初始化enc28j60

enc28j60clkout(1); // change clkout from 6.25MHz to 12.5MHz

}

/**********************************************

* low_level_output(): Should do the actual transmission of the packet. The

* packet is contained in the pbuf that is passed to the function. This pbuf

* might be chained.

pbuf结构为一个链表,第一个pbuf结构体中的tot_len字段代表整个以太网数据包的大小

***********************************************/

static err_t low_level_output( struct netif *netif, struct pbuf *p ) /*底层发送数据函数*/

{

struct pbuf *q;

int i = 0;

err_t xReturn = ERR_OK;

/* Parameter not used. */

for(q = p; q != NULL; q = q->next)

{

/* Send the data from the pbuf to the interface, one pbuf at a

time. The size of the data in each pbuf is kept in the ->len

variable. */

memcpy(&Tx_Data_Buf[i], (u8_t*)q->payload, q->len); //这里的(u8_t*)q->payload仅仅是进行强制转换,没有什么特别的意思,其实也是地址

i = i + q->len;

}

//注意这里是放到数组里慢慢发的

enc28j60PacketSend(i,Tx_Data_Buf); //发送数据包

return xReturn;

结束语

好了,对以上文件进行正确编写,并配置正确的路径之后,大体上就完成了lwip的协议移植了,是不是很简单!只要细心,肯定会移植成功的!建议读者结合野火的以太网程序看!!!!

参考:STM32参考手册中文

ENC28J60中文网络芯片资料

零死角玩转STM32-V2

以太网及TCPIP通俗理解

1 以太网------EtherNet: ---------------------------参考图解 以太网最早由Xerox(施乐)公司创建,于1980年DEC、lntel和Xerox三家公司联合开发成为一个标准。以太网是应用最为广泛的局域网,包括标准的以太网(10Mbit/s)、快速以太网(100Mbit/s)和10G(10Gbit/s)以太网,采用的是CSMA/CD访问控制法,它们都符合IEEE802.3。 IEEE 802.3标准 IEEE802.3规定了包括物理层的连线、电信号和介质访问层协议的内容。以太网是当前应用最普遍的局域网技术,它很大程度上取代了其他局域网标准。如令牌环、FDDI和ARCNET。历经100M以太网在上世纪末的飞速发展后,目前千兆以太网甚至10G以太网正在国际组织和领导企业的推动下不断拓展应用范围。 常见的802.3应用为: 10M: 10base-T (铜线UTP模式) 100M: 100base-TX (铜线UTP模式) 100base-FX(光纤线) 1000M: 1000base-T(铜线UTP模式) 2 UIP协议: uIP由瑞典计算机科学学院(网络嵌入式系统小组)的Adam Dunkels 开发。其源代码由C 语言编写,并完全公开,uIP 的最新版本是1.0 版本,本指南移植和使用的版本正是此版本。uIP协议栈去掉了完整的TCP/IP中不常用的功能,简化了通讯流程,但保留了网络通信 必须使用的协议,设计重点放在了IP/TCP/ICMP/UDP/ARP这些网络层和传输层协议上,保证了其代码的通用性和结构的稳定性。 由于uIP协议栈专门为嵌入式系统而设计,因此还具有如下优越功能: 1)代码非常少,其协议栈代码不到6K,很方便阅读和移植。 2)占用的内存数非常少,RAM 占用仅几百字节。 3)其硬件处理层、协议栈层和应用层共用一个全局缓存区,不存在数据的拷贝,且发送和接收都是依靠这个缓存区,极大的节省空间和时间。 4)支持多个主动连接和被动连接并发。 5)其源代码中提供一套实例程序:web 服务器,web 客户端,电子邮件发送程序(SMTP 客户端),Telnet服务器,DNS主机名解析程序等。通用性强,移植起来基本不用修改就可以通过。 6)对数据的处理采用轮循机制,不需要操作系统的支持。 由于uIP对资源的需求少和移植容易,大部分的8位微控制器都使用过uIP 协议栈,而且很多的著名的嵌入式产品和项目(如卫星,Cisco 路由器,无线传感器网络)中都在使用uIP 协议栈。 3 TCP/IP协议: TCP/IP是(Transmission Control Protocol/Internet Protocol)的简写,中译名为传输控制协

Xmodem协议详解以及源代码剖析

研究 Xmodem 协议必看的 11个问题 Xmodem 协议作为串口数据传输主要的方式之一,恐怕只有做过 bootloader 的才有机会接触一下, 网上有关该协议的内容要么是英语要么讲解不详细。笔者以前写 bootloader 时研究过 1k-Xmodem ,参考了不少相关资料。这里和大家交流一下我对 Xmodem 的理解,多多指教! 1. Xmodem 协议是什么? XMODEM协议是一种串口通信中广泛用到的异步文件传输协议。分为标准Xmodem 和 1k-Xmodem 两种,前者以 128字节块的形式传输数据,后者字节块为 1k 即 1024字节,并且每个块都使用一个校验和过程来进行错误检测。在校验过程中如果接收方关于一个块的校验和与它在发送方的校验和相同时,接收方就向发送方发送一个确认字节 (ACK。由于 Xmodem 需要对每个块都进行认可, 这将导致性能有所下降, 特别是延时比较长的场合, 这种协议显得效率更低。 除了 Xmodem ,还有 Ymodem , Zmodem 协议。他们的协议内容和 Xmodem 类似,不同的是 Ymodem 允许批处理文件传输,效率更高; Zmodem 则是改进的了Xmodem ,它只需要对损坏的块进行重发,其它正确的块不需要发送确认字节。减少了通信量。 2. Xmodem 协议相关控制字符 SOH 0x01 STX 0x02 EOT 0x04 ACK 0x06 NAK 0x15

CAN 0x18 CTRLZ 0x1A 3.标准 Xmodem 协议(每个数据包含有 128字节数据帧格式 _______________________________________________________________ | SOH | 信息包序号 | 信息包序号的补码 | 数据区段 | 校验和 | |_____|____________|___________________|__________|____________| 4. 1k-Xmodem (每个数据包含有 1024字节数据帧格式 _______________________________________________________________ | STX | 信息包序号 | 信息包序号的补码 | 数据区段 | 校验和 | |_____|____________|___________________|__________|____________| 5.数据包说明 对于标准 Xmodem 协议来说,如果传送的文件不是 128的整数倍,那么最后一个数据包的有效内容肯定小于帧长,不足的部分需要用 CTRL- Z(0x1A来填充。这里可能有人会问,如果我传送的是 bootloader 工程生成的 .bin 文件, mcu 收到后遇到0x1A 字符会怎么处理?其实如果传送的是文本文件,那么接收方对于接收的内容是很容易识别的,因为 CTRL-Z 不是前 128个 ascii 码, 不是通用可见字符, 如果是二进制文件, mcu 其实也不会把它当作代码来执行。哪怕是 excel 文件等,由于其内部会有些结构表示各个字段长度等,所以不会读取多余的填充字符。否则 Xmodem太弱了。对于 1k-Xmodem ,同上理。 6.如何启动传输?

2012.11.6战略智慧笔记 陈果

N 《战略智慧》 --陈果 如何建立战略思维? 你现在最需要解决的是什么问题? 1、未来老百姓的健康生活方式? 2、房产中介的人力资源 3、企业做到一定程度,如何把规模缩小? 4、如何使用90后? 5、外贸出口利润越来越低,公司成本越来越大,如何突破?需要经营的: 1、原始积累(财富) 2、内部团队(精神共同体) 团队是利润,是巨大财富 3、忠实客户(了解客户需求) 企业一定要战略升级,为谁请命? 老板需要经营“空手套白狼”的本领。 企业做大的因素: 1、政府的力量 2、资金对你的加持 3、消费者对你的关注 4、优秀的人才向你靠齐

利润 (如:外婆家) 如:宋城集团,通过做“宋城千古情”项目,获得政府的支持 大老板:看似很傻,实际很厉害,用一年的时间赚10年的钱 如:王志纲老师用三十年的时间做中国最好的“战略思想智库”,一转身获得无数的财富 经营企业就是经营人,经营企业就是经营价值。 企业、产品都是媒介,关键是你想到哪里去。 战略思维思考的问题是:我要到哪里去? 老板必须为战略负责! 战略是唯一不能让职业经理人去做的事情。 没有战略就没有人追随,如果成功也是偶然的。 如:王建林(万达集团),当初做商业地产,所有人都反对如:吴亚军,(南湖地产,温州人)当初做战略十几人的核心团队全部走掉,但今天成为中国女首富。 老板不是所有事情都需要你来做,而是那些事情是你必须要做的。

如:华为,力排众议做最适合当下的战略 这是一场越来越激烈的商战,不要妄想今天的困难明天就过去了,要有打战的思维 如:微软 在战争当中总结经验,这是老板需要修炼的 战略智慧金三角: 找定位 定打法 开模具 战略之道的根本是定位。 打法和模具的关系: 模具是企业超级杀伤力的武器 如:工作室:帮企业找魂,帮企业开模具书院班:帮企业开模具,寻找战略突破打法:合适的发射装置 打法与模具的关系是炮弹和炮筒的关系 孵化人的板块: 从老板到老师的智慧

LWIP协议栈的分析和设计

---《计算机网络与控制》论文 LWIP协议栈的分析

摘要 近些年来,随着互联网和通讯技术的迅猛发展,除了计算机之外,大量的嵌入式设备也需求接入网络。目前,互联网中使用的通讯协议基本是TCP/IP协议族,可运行于不同的网络上,本文研究的就是嵌入式TCP/IP协议栈LWIP。文章首先分析了LWIP的整体结构和协议栈的实现,再介绍协议栈的内存管理,最后讲解协议栈应用程序接口。 关键词: 嵌入式系统;协议;LWIP;以太网 Abstract With the rapid development of internet and communication technology, Not only computers but also embeded equipments are need to connect networks. At present, the basic communication protocol using in internet is TCP/IP, it can run in different network. This paper analyses the Light-Weight TCP/IP. The process model of a protocol implementation and processing of every layer are described first, and then gives the detailed management of Buffer and memory. At last, a reference lwIP API is given. Key words: Embedded System, Protocol, Light weight TCP/IP,Ethernet 引言

uip移植笔记

本笔记适用于uIP1.0。 移植平台介绍:MSP430F149+cs8900a+IAR 1、阅读The uIP Embedded TCP/IP Stack The uIP 1.0 Reference Manual. 2、建立一个文件夹,起名myport,将uip-1.0下的uIP和lib两个文件夹拷贝过去,然后再在myport下建立app文件夹。 3、将unix子文件夹下的clock-arch.c、clock-arch.h拷贝到myport下,这个文件实现协议栈所用的时钟,由430的定时器完成,有三个函数: clock_time_t clock_time(void) { return ticks; } void clock_init(void) { 定时器的初始化工作 } __interrupt void timer_interrupt(void)/*定时器中断函数*/ { ++ticks; }。 4、将unix子文件夹下的uip-conf.h拷贝到myport下,这个文件实现协议栈所用的配置,按照需要修改之。 5、写cs8900a的驱动函数,这里采用8位、查询模式,替换tapdev.c 或slipdev.c。 6、将unix子文件夹下的main.c函数拷贝到myport下,这个是主调度流程,按照需要修改。 7、建立自己的工程,将以上文件包含。 8、调试,改错。 其中,uip的缓冲区是以字节数组的形式产生,为了保证它的起始地址是偶数,必须指定地址。 UDP的初始化如下 void myudp_init(void) { uip_ipaddr_t ipaddr;//定义IP类型变量 uip_ipaddr(ipaddr, 210,29,104,88); //远程IP为210.29.104.88 if(myudp_conn != NULL) { uip_udp_remove(myudp_conn);//如果连接已经建立,则删除之 } myudp_conn = uip_udp_new(&ipaddr, HTONS(1000));//建立到远程ipaddr,端口为1000的连接 if(myudp_conn != NULL) {

ucos操作系统在ARM上的移植

UC/OS-II 嵌入式系统在ARM 上的移植 UC/OS-II 操作系统是一款完全公开的源代码,它非常精简,整个操作系统的代码只有几千行,是专门针对于嵌入式开发而产生的一款代码。它有几个特点,分别是可移植性(Portable )、可固化(ROMable )、可裁剪(Scalable )、多任务、可确定性、任务栈、系统服务、中断管理、稳定性可靠性。 UC/OS-II 主要就是一个内核,由ANSIC 语言编写而成。负责任务管理和任务调度,没有文件系统和界面系统。它的代码是公开的,系统的实时性强、移植性好、可多任务。 UC/OS-II 作为基于优先级的抢占式多任务的实时操作系统,包含了实时内核、任务管理、时间管理、任务间通信同步和内存管理的功能。它使得任务的独立性,不相互干涉,非常的准时和高效,且易于设计和扩展。 UO/OS-II 共有16个内核文件,11个与CPU 类型无关,就是说可以直接使用不需要修改。还有3个内核文件与CPU 有关系,要根据需要作出相应的改动。剩下的两个内核文件和具体的应用有关。如图所示UC/OS-II 的16个内核文件的层次。 μC/OS -II 内核文件 软件 硬件

多任务操作的核心是系统调度器,利用TCB来管理任务调度功能。它的主要功能是保存任务的当前态、优先级、等待事件、代码起始地址、初始堆栈指针等。程序的设计关键就是确定划分多任务的问题,以及任务优先级和任务通信。 优先级的意思是每个任务都是无限循环的,有运行态度、就绪态、休眠态、挂起态和中断五种状态。当有高一级优先级的任务就绪后,低优先级立即停止运行,转为挂起态或就绪态。这就是可剥夺型的内核。当中断一个高优先级任务,中断时 挂起,中断结束后任务继续运行,并立即剥夺低优先级的任务。 对于这种可剥夺型内核,CPU的使用时可以确定的,可优化任务级响应。在很多单片机或ARM板上很容易就可以移植UC/OS-II。当然本次设计使用的TQ2440,也可以完美的移植它。移植程序在网上都可以找得到,所以设计中就不做解释了。 本次设计实现的是串口协议和网口协议组合成的一个数据网关。其主要的流程图如下所示:

lwip各层协议栈详解

竭诚为您提供优质文档/双击可除lwip各层协议栈详解 篇一:lwip协议栈源码分析 lwip源码分析 -----caoxw 1lwip的结构 lwip(lightweightinternetprotocol)的主要模块包括:配置模块、初始化模块、netif模块、mem(memp)模块、netarp模块、ip模块、udp模块、icmp模块、igmp模块、dhcp模块、tcp模块、snmp模块等。下面主要对我们需要关心的协议处理进行说明和梳理。配置模块: 配置模块通过各种宏定义的方式对系统、子模块进行了配置。比如,通过宏,配置了mem管理模块的参数。该配置模块还通过宏,配置了协议栈所支持的协议簇,通过宏定制的方式,决定了支持那些协议。主要的文件是opt.h。 初始化模块: 初始化模块入口的文件为tcpip.c,其初始化入口函数为: voidtcpip_init(void(*initfunc)(void*),void*arg)

该入口通过调用lwip_init()函数,初始化了所有的子模块,并启动了协议栈管理进程。同时,该函数还带有回调钩子及其参数。可以在需要的地方进行调用。 协议栈数据分发管理进程负责了输入报文的处理、超时处理、api函数以及回调的处理,原型如下: staticvoidtcpip_thread(void*arg) netif模块: netif模块为协议栈与底层驱动的接口模块,其将底层的一个网口设备描述成协议栈的一个接口设备(netinterface)。该模块的主要文件为netif.c。其通过链表的方式描述了系统中的所有网口设备。 netif的数据结构描述了网口的参数,包括ip地址、mac 地址、link状态、网口号、收发函数等等参数。一个网口设备的数据收发主要通过该结构进行。 mem(memp)模块: mem模块同一管理了协议栈使用的内容缓冲区,并管理pbuf结构以及报文的字段处理。主要的文件包括mem.c、memp.c、pbuf.c。 netarp模块: netarp模块是处理arp协议的模块,主要源文件为etharp.c。其主要入口函数为: err_tethernet_input(structpbuf*p,structnetif*netif)

uip学习笔记

uip_buf:定义如下u8_t uip_buf[UIP_BUFSIZE + 2];所有的数据处理都是通过处理它来完成的。比如接受的数据存储在这里,要发送的数据有会放在这里。 uip_len:uip_buf有用数据的字节 uip_appdata:uip_buf第一个可用字节的指针 uip_conn:总是指向当前连接的指针,定义:struct uip_conn *uip_conn; 下面是TCP连接的结构,用来区别不同的TCP连接,uip_tcp_appstate_t appstate是可以读写的且在实践应用中需要重定义,其他项read-only。 struct uip_conn { uip_ipaddr_t ripaddr; /**< The IP address of the remote host. 远程主机IP地址*/ u16_t lport; /**< The local TCP port, in network byte order. 本地TCP端口号,网络字节顺序*/ u16_t rport; /**< The local remote TCP port, in network byte order.本地远程连接主机TCP端口号*/ u8_t rcv_nxt[4]; /**< The sequence number that we expect to receive next. */ u8_t snd_nxt[4]; /**< The sequence number that was last sent by us. */ u16_t len; /**< Length of the data that was previously sent. */ u16_t mss; /**< Current maximum segment size for the connection. */ u16_t initialmss; /**< Initial maximum segment size for the connection. */ u8_t sa; /**< Retransmission time-out calculation state variable. */ u8_t sv; /**< Retransmission time-out calculation state variable. */ u8_t rto; /**< Retransmission time-out. */ u8_t tcpstateflags; /**< TCP state and flags. */ u8_t timer; /**< The retransmission timer. */ u8_t nrtx; /**< The number of retransmissions for the last segment sent. */ /** The application state. */ uip_tcp_appstate_t appstate; }; uip的应用事件: 1.接收数据:uip_newdata()为真,即远程连接的主机有发送新数据。uip_appdata指针指向实际数据。数据的大小通过uIP函数uip_datalen()获得。在数据不是被缓冲后,应用程序必须立刻启动。 2.发送数据:应用程序通过使用uIP函数uip_send()发送数据。uip_send()函数采用两个参数;一个指针指向发送数据和数据的长度。如果应用程序为了产生要发送的实际数据需要RAM 空间,包缓存(通过uip_appdata指针指向)可以用于这方面。在一个时间里应用程序只能在连接中发送一块数据。因此不可以在每个应用程序启用中调用uip_send()超过一次;只有上

LwIP协议栈源码详解

LwIP协议栈源码详解 ——TCP/IP协议的实现 Created by.. 老衲五木 at.. UESTC Contact me.. for_rest@https://www.360docs.net/doc/8f18105965.html, 540535649@https://www.360docs.net/doc/8f18105965.html,

前言 最近一个项目用到LwIP,恰好看到网上讨论的人比较多,所以有了写这篇学习笔记的冲动,一是为了打发点发呆的时间,二是为了吹过的那些NB。往往决定做一件事是简单的,而坚持做完这件事却是漫长曲折的,但终究还是写完了,时间开销大概为四个月,内存开销无法估计。。 这篇文章覆盖了LwIP协议大部分的内容,但是并不全面。它主要讲解了LwIP协议最重要也是最常被用到的部分,包括内存管理,底层网络接口管理,ARP层,IP层,TCP层,API 层等,这些部分是LwIP的典型应用中经常涉及到的。而LwIP协议的其他部分,包括UDP,DHCP,DNS,IGMP,SNMP,PPP等不具有使用共性的部分,这篇文档暂时未涉及。 原来文章是发在空间中的,每节每节依次更新,后来又改发为博客,再后来就干脆懒得发了。现在终于搞定,于是将所有文章汇总。绞尽脑汁的想写一段空前绝后,人见人爱的序言,但越写越觉得像是猫儿抓的一样。就这样,PS:由于本人文笔有限,情商又低,下里巴人一枚,所以文中的很多语句可能让您很纠结,您可以通过邮箱与我联系。共同探讨才是进步的关键。 最后,欢迎读者以任何方式使用与转载,但请保留作者相关信息,酱紫!码字。。。世界上最痛苦的事情莫过于此。。。 ——老衲五木

目录 1 移植综述------------------------------------------------------------------------------------------------------4 2 动态内存管理------------------------------------------------------------------------------------------------6 3 数据包pbuf--------------------------------------------------------------------------------------------------9 4 pbuf释放---------------------------------------------------------------------------------------------------13 5 网络接口结构-----------------------------------------------------------------------------------------------16 6 以太网数据接收--------------------------------------------------------------------------------------------20 7 ARP表-----------------------------------------------------------------------------------------------------23 8 ARP表查询-----------------------------------------------------------------------------------------------26 9 ARP层流程-----------------------------------------------------------------------------------------------28 10 IP层输入-------------------------------------------------------------------------------------------------31 11 IP分片重装1--------------------------------------------------------------------------------------------34 12 IP分片重装2--------------------------------------------------------------------------------------------37 13 ICMP处理-----------------------------------------------------------------------------------------------40 14 TCP建立与断开----------------------------------------------------------------------------------------43 15 TCP状态转换-------------------------------------------------------------------------------------------46 16 TCP控制块----------------------------------------------------------------------------------------------49 17 TCP建立流程-------------------------------------------------------------------------------------------53 18 TCP状态机----------------------------------------------------------------------------------------------56 19 TCP输入输出函数1-----------------------------------------------------------------------------------60 20 TCP输入输出函数2-----------------------------------------------------------------------------------63 21 TCP滑动窗口-------------------------------------------------------------------------------------------66 22 TCP超时与重传----------------------------------------------------------------------------------------69 23 TCP慢启动与拥塞避免-------------------------------------------------------------------------------73 24 TCP快速恢复重传和Nagle算法-------------------------------------------------------------------76 25 TCP坚持与保活定时器-------------------------------------------------------------------------------80 26 TCP定时器----------------------------------------------------------------------------------------------84 27 TCP终结与小结----------------------------------------------------------------------------------------88 28 API实现及相关数据结构-----------------------------------------------------------------------------91 29 API消息机制--------------------------------------------------------------------------------------------94 30 API函数及编程实例-----------------------------------------------------------------------------------97

uip协议栈

uIP协议栈分析 uIP特性 uIP协议栈往掉了完整的TCP/IP中不常用的功能,简化了通讯流程,但保存了网络通讯必须使用的协议,设计重点放在了IP/TCP/ICMP/UDP/ARP这些网络层和传输层协议上,保证了其代码的通用性和结构的稳定性。 由于uIP协议栈专门为嵌进式系统而设计,因此还具有如下优越功能: (1)代码非常少,其协议栈代码不到6K,很方便阅读和移植。 (2)占用的内存数非常少,RAM占用仅几百字节。 (3)其硬件处理层、协议栈层和应用层共用一个全局缓存区,不存在数据的拷贝,且发送和接收都是依靠这个缓存区,极大的节省空间和时间。 (4)支持多个主动连接和被动连接并发。 (5)其源代码中提供一套实例程序:web服务器,web客户端,电子邮件发送程序(SMTP 客户端),Telnet服务器,DNS主机名解析程序等。通用性强,移植起来基本不用修改就可以通过。 (6)对数据的处理采用轮循机制,不需要操纵系统的支持。 由于uIP对资源的需求少和移植轻易,大部分的8位微控制器都使用过uIP协议栈, 而且很多的著名的嵌进式产品和项目(如卫星,Cisco路由器,无线传感器网络)中都在使用uIP协议栈。 uIP架构 uIP相当于一个代码库,通过一系列的函数实现与底层硬件和高层应用程序的通讯,对于整个系统来说它内部的协议组是透明的,从而增加了协议的通用性。uIP协议栈与系统底层和高层应用之间的关系如图2-1所示。 从上图可以看出,uIP协议栈主要提供了三个函数供系统底层调用。即uip_init(), uip_input() 和uip_periodic()。其与应用程序的主要接口是UIP_APPCALL( )。 uip_init()是系统初始化时调用的,主要初始化协议栈的侦听端口和默认所有连接是封闭的。当网卡驱动收到一个输进包时,将放进全局缓冲区uip_buf中,包的大小由全局变量uip_len

lwip协议栈源码分析

LWIP源码分析 ----- caoxw 1 LWIP的结构 LWIP(Light weight internet protocol)的主要模块包括:配置模块、初始化模块、NetIf 模块、mem(memp)模块、netarp模块、ip模块、udp模块、icmp 模块、igmp模块、dhcp 模块、tcp模块、snmp模块等。下面主要对我们需要关心的协议处理进行说明和梳理。 配置模块: 配置模块通过各种宏定义的方式对系统、子模块进行了配置。比如,通过宏,配置了mem管理模块的参数。该配置模块还通过宏,配置了协议栈所支持的协议簇,通过宏定制的方式,决定了支持那些协议。主要的文件是opt.h。 初始化模块: 初始化模块入口的文件为tcpip.c,其初始化入口函数为: void tcpip_init(void (* initfunc)(void *), void *arg) 该入口通过调用lwip_init()函数,初始化了所有的子模块,并启动了协议栈管理进程。同时,该函数还带有回调钩子及其参数。可以在需要的地方进行调用。 协议栈数据分发管理进程负责了输入报文的处理、超时处理、API函数以及回调的处理,原型如下: static void tcpip_thread(void *arg) NetIf模块: Netif模块为协议栈与底层驱动的接口模块,其将底层的一个网口设备描述成协议栈的一个接口设备(net interface)。该模块的主要文件为netif.c。其通过链表的方式描述了系统中的所有网口设备。 Netif的数据结构描述了网口的参数,包括IP地址、MAC地址、link状态、网口号、收发函数等等参数。一个网口设备的数据收发主要通过该结构进行。 Mem(memp)模块: Mem模块同一管理了协议栈使用的内容缓冲区,并管理pbuf结构以及报文的字段处理。主要的文件包括mem.c、memp.c、pbuf.c。 netarp模块: netarp模块是处理arp协议的模块,主要源文件为etharp.c。其主要入口函数为: err_t ethernet_input(struct pbuf *p, struct netif *netif) 该入口函数通过判断输入报文p的协议类型来决定是按照arp协议进行处理还是将该报文提交到IP协议。如果报文是arp报文,该接口则调用etharp_arp_input,进行arp请求处理。 如果是ip报文,该接口就调用etharp_ip_input进行arp更新,并调用ip_input接口,将报文提交给ip层。 在该模块中,创建了设备的地址映射arp表,并提供地址映射关系查询接口。同时还提供了arp报文的发送接口。如下:

LwIP协议栈开发嵌入式网络的三种方法分析

LwIP协议栈开发嵌入式网络的三种方法分析 摘要轻量级的TCP/IP协议栈LwIP,提供了三种应用程序设计方法,且很容易被移植到多任务的操作系统中。本文结合μC/OS-II这一实时操作系统,以建立TCP服务器端通信为例,分析三种方法以及之间的关系,着重介绍基于raw API的应用程序设计。最后在ST公司STM32F107微处理器平台上验证,并给出了测试结果。 关键词LwIP协议栈;μC/OS-II;嵌入式网络;STM32F107; 随着嵌入式系统功能的多样化以及网络在各个领域的中的广泛应用,具备网络功能的嵌入式设备拥有更高的使用价值和更强的通用性。然而大部分嵌入式设备使用经济型处理器,受内存和速度限制,资源有限,不需要也不可能完整实现所有的TCP/IP协议,有时只需要满足实际需求就行。LwIP是由瑞典计算机科学研究院开发的轻量型TCP/IP协议栈,其特点是保持了以太网的基本功能,通过优化减少了对存储资源的占用。LwIP是免费、开源的,任何人可以使用,能够在裸机的环境下运行,当然设计的时候也考虑了将来的移植问题,可以很容易移植到多任务操作系统中。本文介绍了以ARM微处理器STM32F107和PHY接口DP83848为平台,构建的嵌入式系统中,采用LwIP和嵌入式操作系统μC/OS-II,使用协议栈提供的三种应用程序接口,实现嵌入式设备的网络通信功能。 1LwIP和μC/OS-II介绍 1.1 LwIP协议栈 LwIP协议是瑞士计算机科学院的Adam Dunkels等开发的一套用于嵌入式系统的开放源代码TCP/IP协议栈。LwIP含义是light weight(轻型)IP协议,在实现时保持了TCP协议的主要功能基础上减少对RAM的占用,一般它只需要几十K的RAM和40K左右的ROM 就可以运行,这使LwIP协议栈很适合在低端嵌入式系统中使用。 LwIP协议栈的设计才用分层结构的思想,每一个协议都作为一个模块来实现,提供一些与其它协议的接口函数。所有的TCP/IP协议栈都在一个进程当中,这样TCP/IP协议栈就和操作系统内核分开了。而应用程序既可以是单独的进程也可以驻留在TCP/IP进程中,它们之间利用ICP机制进行通讯。如果应用程序是单独的线程可以通过操作系统的邮箱、消息队列等,与协议栈进程通讯。如果应用程序驻留在协议栈进程中,则应用程序可以通过内部回调函数和协议栈进程通讯。 1.2 μC/OS-II实时操作系统 μC/OS-II是一个源码公开、可移植、可固化、可裁剪及占先式的实时多任务操作系统,是专门为嵌入式应用设计的实时操作系统内核,已广泛的应用在各种嵌入式系统中。 μC/OS-II是多任务系统,内核负责管理各个任务,每个任务都有其优先级,μC/OS-II 最多可以管理64个任务,其每个任务都拥有自己独立的堆栈。μC/OS-II提供了非常丰富的系统服务功能,比如信号量、消息邮箱、消息队列、事件标志、内存管理和时间管理等,这些功能可以帮助用户实现非常复杂的应用。 1.3 LwIP协议栈移植到μC/OS-II LwIP协议栈在设计的时候就考虑到了将来的移植问题,因此把所有与硬件、操作系统、编译器有关的部分都全部独立起来,形成了一个操作系统模拟层。操作系统模拟层用进程间的信号量、邮箱机制处理通信问题,而μC/OS-II是一个基于任务调度的嵌入式实时操作系

如何学习TCPIP(基于51单片机)

如何学习TCPIP(基于51单片机) 总体说来,TCPIP并不是一件十分神秘的事情,尤其是基于MCU的应用,不要求进行特别复杂的处理,很多情况下只需要实现最最基本的功能就行了。在实现MCU的TCPIP移植之前,必须对TCPIP有一定程度的了解,可以找一本合适的书籍来翻阅一下,《TCP/IP详解,卷1:协议》https://www.360docs.net/doc/8f18105965.html,/display.aspx?did=510是一本完整而详细的TCP/IP协议指南。描述了属于每一层的各个协议以及它们如何在不同操作系统中运行。 对于TCPIP在MCU上的应用并不要求对协议的所有部分都了解的那么清楚,重点需要了解TCPIP的各个层次的关系,链路层,有时也称作数据链路层或网络接口层,通常包括操作系统中的设备驱动程序和计算机中对应的网络接口卡。它们一起处理与电缆(或其他任何传输媒介)的物理接口细节。网络层,有时也称作互联网层,处理分组在网络中的活动,例如分组的选路。在T C P / I P协议族中,网络层协议包括I P协议(网际协议),I C M P协议(I n t e r n e t互联网控制报文协议),以及I G M P协议(I n t e r n e t组管理协议)。运输层主要为两台主机上的应用程序提供端到端的通信。在T C P / I P协议族中,有两个互不相同的传输协议:T C P(传输控制协议)和U D P(用户数据报协议)。T C P为两台主机提供高可靠性的数据通信。它所做的工作包括把应用程序交给它的数据分成合适的小块交给下面的网络层,确认接收到的分组,设置发送最后确认分组的超时时钟等。由于运输层提供了高可靠性的端到端的通信,因此应用层可以忽略所有这些细节。而另一方面,U D P则为应用层提供一种非常简单的服务。它只是把称作数据报的分组从一台主机发送到另一台主机,但并不保证该数据报能到达另一端。任何必需的可靠性必须由应用层来提供。这两种运输层协议分别在不同的应用程序中有不同的用途。应用层负责处理特定的应用程序细节。几乎各种不同的T C P / I P实现都会提供Telnet,FTP,SMTP 简单邮件传送协议,SNMP简单网络管理协议这些通用的应用程序。 各种类型的数据报格式也是需要了解的重点,使用Sniffer软件可以十分方便的在电脑上查看各种数据报的收发状态.同时Sniffer也是以后调试TCPIP协议寨的一个很有用的工具,Sniffer的使用方式可以在https://www.360docs.net/doc/8f18105965.html,上很方便的搜索到. TCP/IP的分层,以太网封装,IP首部,子网寻址和子网掩码,ARP地址解析协议,ICMP控制报文协议中的ECHO(Ping程序),UDP用户数据报协议,TFTP简单文件传送协议,特别是TCP传输控制协议是TCPIP在MCU上应用所必需掌握的关键知识. 在对TCPIP有了一定程度的了解之后,如何具体的实现就成了问题的关键,我在学习TCPIP 的过程中前后一共使用或阅读了下面的3中TCPIP协议寨,这里有对3个协议寨的比较和下载地址. uIP,适合8bit单片机上使用,但是结构比较复杂,不适宜进行移植,也不是一份很适合阅读的代码.下载地址http://www.sics.se/~adam/uip/ Lwip,适合16/32bit单片机上使用,是嵌入式系统开发人员最好的学习TCPIP的代码,下载地址http://www.sics.se/~adam/lwip/ zLip,南开大学电子应用实验室编写的一个协议寨,有uip和lwip的优点,推荐初学者学习https://www.360docs.net/doc/8f18105965.html,/display.aspx?did=859 在了解了具体实现之后,就有需要在MCU上具体的运行一下了,这里提供一个我做的硬件电路,但是其中我使用了GAL16V8芯片进行地址分配,所以需要有一个支持16V8的烧写器了,同时,如果将at89c55芯片换成sst89c58,并从https://www.360docs.net/doc/8f18105965.html,公司网站上下载一个monitor 51的仿真监控程序,使用烧写器写入sst89c58中,就可以通过串口和Keil软件配合进行硬件仿真了.(市场上的那些100多元的51仿真器就是这个样子的). Gal的代码如下(abel hdl语言编写),使用猜测的方式都应该明白什么意思了把?!

基于FPGA的IP核8051上实现TCPIP的设计

基于FPGA的IP核8051上实现TCP/IP的设计引言 随着芯片规模的越来越大、资源的越来越丰富, 芯片的设计复杂度也大大增加。事实上, 在芯片设计完成后, 有时还需要根据情况改变一些控制, 这在使用过程中会经常遇到。这时候如果再对芯片设计进行改变将是很不可取的, 因为需要设计人员参与这种改变, 这无论是对设计者还是用户都是不能接受的。于是就有必要让这种可以改变的简单控制在芯片设计时就存在, 而且同时还应该使这种改变相对容易, 比较通用, 并且与芯片的其它设计部分尽量不相关。为了满足上述的要求, 在FPGA中嵌入一个比较理想的选择, 而这个即通用又控制简单的IP核最好选择8051微处理器。 在FPGA中植入8051后, 还可在上面实现简单的TCP/IP协议, 以支持远程访问或进行远程调试, 这只是在嵌入FPGA的8051上的一个应用。为了保证用户能够对8051实现不同的控制操作,设计时也可以采用一个外部flash对8051进行加载, 这样, 用户只需要将编译好的汇编语言代码加到flash就可以控制8051的工作, 而此时用户完全不需要对FPGA进行操作就能实现简单的控制,而这需要的仅仅只是keil的编译环境。 1 IP核8051的FPGA实现 现在有许多免费的8051核可以利用, 这些核都可通过硬件描述语言来实现, 并且基本上都可综合, 也就是直接拿来就能用, 需要的只是根据自身的具体需求做一些简单修改即可。总的说来, IP核8051的移植是比较简单的。 本系统的设计与实现可以采用oregano system的mc8051内核, 并且加入定时计数的和串口模块, 8051单片机的设计结构框图如图1所示。

相关文档
最新文档