⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 hardware.c

📁 很好的网络编程协议源码
💻 C
📖 第 1 页 / 共 2 页
字号:
			WriteToNet(0x10,send_buff.words);	
		}
		ExPtr=ExPtr->STPTR;
	}
	//如果少于60
	
	/***************************************/
	//以下为终止DMA操作
	WriteToNet(0x0b,0x00); 
	WriteToNet(0x0a,0x00);
	WriteToNet(0x00,0x22);			//结束或放弃DMA操作
	
	WriteToNet(0x07,0xff);         //clear interrupt status register
	if(Tx_Buff_Sel)
	{
		WriteToNet(0x04,0x40);   //txd packet start;
	}
	else
	{
		WriteToNet(0x04,0x46);  //txd packet start;
    	}
	ii=length;
	if(length<60)
	{
		//如果数据长度<60字节,设置长度为60字节
		ii=60;
	}
	
	WriteToNet(0x06,ii>>8);	//high byte counter
	WriteToNet(0x05,ii&0x00ff);//low byte counter
	WriteToNet(0x07,0xff);//clear interrupt status register
	WriteToNet(0x00,0x3e);       //to sendpacket;
	/***************************************/
	//重发数据的处理
	
	for(length=0;length<6;length++)	//最多重发6次
	{
		for(ii=0;ii<1000;ii++)
		{//检查CR寄存器的txp位是否为低,为1说明正在发送,为0说明发完或出错放弃
			if((ReadFromNet(0X00)&0x04)==0)  
			{ break; }
        	}
		if((ReadFromNet(0X04)&0x01)!=0)//表示发送成功,判断发送状态寄存器TSR,决定是否出错
		{break;};
		WriteToNet(0x00,0x3e);       //to sendpacket;
	}
	
	/**************************************/
	//OS_EXIT_CRITICAL();
}

/**********************************************************************
**函数原型:    unsigned char * Rec_Packet()
**入口参数:?无
**出口参数:		返回数据指针			unsigned char * 
**返 回 值:	NULL          			没有新数据包
**              unsigned char *         接收到新数据包
**说    明:	查询是否有新数据包并接收进缓冲区
************************************************************************/
uint8 Rec_Packet() 
{
	static uint8 REC_BUFF_NUM=0;
	static uint8 bnry,curr;  //?可否只做局部?
	static uint16 tmp[2];
	//static uint16 crt=0;
	uint16 * REC_BUFF_PTR_WORDS;
	uint8 * REC_BUFF_PTR_BYTES;
	uint8 i;
	uint16 ii,length;
	//OS_ENTER_CRITICAL();
	
rea1:
	page(0);
	i = ReadFromNet(0X07);		//读取中断状态
	if(( i & 0x90) != 0)//如果复位或益出就重新初试化
	{
		InitNic(0);
		//OS_EXIT_CRITICAL();
		return(0);
	}
	bnry=ReadFromNet(0X03);		//bnry page have read 读页指针
	page(1);
	curr=ReadFromNet(0X07);		//curr writepoint 8019写页指针
	page(0);
	if(curr==0)
	{
		//OS_EXIT_CRITICAL();
		return(0);	//读的过程出错
	}
	bnry++;//bnry=bnry++;
	if(bnry>0x7f)
	{
		bnry=0x4c;
		//crt++;//统计内部16K循环了多少次(仿真器29次后出错)52、
	}
	
	if(bnry!=curr)	//此时表示有新的数据包在缓冲区里
   	{			//在任何操作都最好返回page0
		if(REC_BUFF_NUM==MAX_REC_BUFF)//接收缓冲区号清零
		{
			REC_BUFF_NUM=0;
		}
		REC_BUFF_PTR_WORDS=REC_BUFF[REC_BUFF_NUM].words;//设定接收缓冲区的起始地址
		//=======================================
		
		WriteToNet(0x09,bnry); //RSAR1写入读页地址的高字节
		WriteToNet(0x08,0x00); //RSAR0写入读页地址的低字节
		WriteToNet(0x0b,0x00); //RSCR1写入读取字节计数高字节
		WriteToNet(0x0a,18);   //RSCR0写入读取字节计数高字节
		WriteToNet(0x00,0x0a); //启动Remote DMA读操作
		//读取一包的前4个字节:4字节的8019头部
		for(i=0;i<2;i++)
		{
			*REC_BUFF_PTR_WORDS=ReadFromNet(0x10);
			tmp[i]=*REC_BUFF_PTR_WORDS;
			REC_BUFF_PTR_WORDS++;
		}
		//0:接收状态;1:下一包的指针;2:本包低位;3:本包高位;
		//=======================================中止DMA操作
		WriteToNet(0x0b,0x00);	//RSCR1写入读取字节计数高字节
		WriteToNet(0x0a,0x00);	//RSCR0写入读取字节计数高字节
		WriteToNet(0x00,0x22);	//结束或放弃DMA操作
		//=======================================
		tmp[1]=tmp[1]-4;//去掉4个字节的CRC
		REC_BUFF[REC_BUFF_NUM].words[1]=tmp[1];	//把真正的接收的帧的长度保存到缓冲区
		//=====================以上各步操作表示读入的数据包有效
		//0:接收状态;1:下一包的指针;2:本包高位;3:本包低位;
		if(((tmp[0]&0x0001)==0)||((tmp[0]&0xff00)>0x7f00)
			||((tmp[0]&0xff00)<0x4c00)||(tmp[1]>0x0600))
		{//接收状态错误或下一数据包的起始页地址错误或接收的数据包长度>1536字节
			page(1);
			curr=ReadFromNet(0X07); 	//page1读取CURR的值
			page(0);		//切换回page0
			bnry = curr -1;	//把bnry恢复为下16K中的空余部分
			if(bnry < 0x4c) 
			{
				bnry =0x7f;
			}
			WriteToNet(0x03,bnry); 	//把BNRY恢复到指向下一帧write to bnry		
			WriteToNet(0x07,0xff);	//清除中断标志
			//goto rea1;
			//OS_EXIT_CRITICAL();
			return(0);
		}//end of if(((tmp[0]&0x0001)
		//=============================================
		else//表示数据包是完好的.读取剩下的数据
		{
			WriteToNet(0x09,bnry);   	//RSAR1写入读页地址的高字节//read page address high
			WriteToNet(0x08,4);      	//RSAR0写入读页地址的低字节//read page address low
			//WriteToNet(0x0b,tmp[0]);  	//RSCR1写入读取字节计数高字节//read count high

			//WriteToNet(0x0a,tmp[1]);	//RSCR0写入读取字节计数低字节//read count low;
			WriteToNet(0x0a,tmp[1]);
			WriteToNet(0x0b,tmp[1]>>8);
			
			WriteToNet(0x00,0x0a); 	//启动Remote DMA读操作
			//read dma
			SendByte(0xff);
			SendByte(0xff);
			SendByte(tmp[1]);
			SendByte(tmp[1]>>8);
			length=tmp[1];//计算出要读取的帧的长度
			
			for(ii=0;ii<((length+1)/2);ii++)
			{
				*REC_BUFF_PTR_WORDS=ReadFromNet(0x10);
				REC_BUFF_PTR_WORDS++;
			}
			//================终止DMA操作
			WriteToNet(0x0b,0x00);			//RSCR1写入读取字节计数高字节//read count high   
			WriteToNet(0x0a,0x00);			//RSCR0写入读取字节计数高字节//read count low;
			WriteToNet(0x00,0x22);			//结束或放弃DMA操作//结束或放弃DMA
			//============================
		}//end of else
		//=========================================
		bnry=(tmp[0]/256)-1;	//tmp[1]是当前有效的CURR
		if(bnry<0x4c)
			bnry=0x7f;
		WriteToNet(0x03,bnry);   	//写入有效的BNRY   //write to bnry
		WriteToNet(0x07,0xff);		//清除中断标志	
		REC_BUFF_PTR_BYTES=REC_BUFF[REC_BUFF_NUM].bytes;
		REC_BUFF_PTR_BYTES=REC_BUFF_PTR_BYTES+4;//把指针恢复到数据包的起始
		
#ifdef Little_End
		if((((ipethernet*)REC_BUFF_PTR_BYTES)->NextProtocal==0x0008)//可以减少对数据缓冲取的利用
			||(((ipethernet*)REC_BUFF_PTR_BYTES)->NextProtocal==0x0608))//不过如果缓冲区足够大就最好不要
#endif
#ifdef Big_End
		if((((ipethernet*)REC_BUFF_PTR_BYTES)->NextProtocal==0x0800)//可以减少对数据缓冲取的利用
			||(((ipethernet*)REC_BUFF_PTR_BYTES)->NextProtocal==0x0806))//不过如果缓冲区足够大就最好不要
#endif
		{
			REC_BUFF_NUM++;
			//OS_EXIT_CRITICAL();
			
			Rec_Ethernet_Packed(REC_BUFF_PTR_BYTES,0);
			//OS_ENTER_CRITICAL();
			goto rea1;
			//可以直接退出。
		}
		else 
			{SendByte('y');goto rea1;}
	}//end of if(bnry!=curr)
	//OS_EXIT_CRITICAL();
	return(0);
}


uint16 swap_int16(uint16 temp)
{uint16 temp1;
temp1=(temp&0xff00)>>8;  
temp=(temp&0x00ff)<<8;
return(temp+temp1);
}
uint32 swap_int32(uint32 temp)
{ 
 u16 temp1,temp2;
 temp1 = temp & 0xffff;
 temp2 = temp >> 16;
 temp = 0;
 swap_int16(temp1);
 swap_int16(temp2);
 temp = temp2 | (temp1 << 16);
 return(temp);
}

uint16 Char2ToInt16(uint8 * temp)
{
	uint16 temp16;
	temp16=((uint16)(*temp))<<8;
	temp++;
	temp16=temp16+(uint16)(*temp);
	return(temp16);
}

uint32 Char4ToInt32(uint8 * temp)
{
	uint32 temp32;
	temp32=((uint32)(*temp))<<24;
	temp++;
	temp32=temp32+(((uint32)(*temp))<<16);
	temp++;
	temp32=temp32+(((uint32)(*temp))<<8);
	temp++;
	temp32=temp32+(uint32)(*temp);
	return(temp32);
}
/*
+FFTR--------------------------------------------------------------------
$Log: hardware.c,v $
Revision 1.3  2006/12/31 16:08:37  tony
由于write_file慢(1KB/S)导致FTP服务器put file失序,不写file时序正常

Revision 1.2  2006/12/31 16:05:20  tony
增加FTP代码,SOCKET_status字段


-FFTR--------------------------------------------------------------------
*/

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -