📄 ne2000.c.bak
字号:
#include "p_tcpip.h"
static BOOLEAN Adapter_bOK;
static BOOLEAN bTransmiting;
static INT8U Adapter_pRcvPacket[40];//68cb
static INT8U Adapter_RcvLenHigh; // high byte
static DSHORT Adapter_sRcvLen;
static INT8U Adapter_RcvLen; // Total length of a received packet (low byte).
static INT8U pHeaderSize[2]; //68f3
static INT8U Adapter_RcvLenHigh ; // high byte
static BOOLEAN bBroadcastPacket;
BOOLEAN NE2000INITIALIZE()
{
INT8U iTmp ;
DLONG iCount ;
iTmp=XBYTE[NE2000_BASE+NIC_COMMAND];
if (!(iTmp&01))
{
Adapter_bOK=0;
return FALSE;
}
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=0x37;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x0a;
XBYTE[NE2000_BASE+NIC_INTR_MASK]=0;
XBYTE[NE2000_BASE+NIC_DATA_CONFIG]=0x48;
XBYTE[NE2000_BASE+NIC_XMIT_CONFIG]=0;
XBYTE[NE2000_BASE+NIC_RCV_CONFIG]=0;
XBYTE[NE2000_BASE+NIC_INTR_STATUS]=0xff;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x21;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=0;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=0;
iCount=0xffff;
do
{
iTmp=XBYTE[NE2000_BASE+NIC_INTR_STATUS];
if (iTmp&80)
break;
} while (iCount--);
XBYTE[NE2000_BASE+NIC_XMIT_CONFIG]=2;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x22;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x21;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x21;
iTmp=XBYTE[NE2000_BASE+NIC_COMMAND];
if( (iTmp&0x21)^0x21)
{
Adapter_bOK=0;
return FALSE;
}
XBYTE[NE2000_BASE+NIC_DATA_CONFIG]=0x48;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=0;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=0;
XBYTE[NE2000_BASE+NIC_RCV_CONFIG]=4;
XBYTE[NE2000_BASE+NIC_XMIT_CONFIG]=2;
XBYTE[NE2000_BASE+NIC_BOUNDARY]=0x46;
XBYTE[NE2000_BASE+NIC_PAGE_START]=0x46;
XBYTE[NE2000_BASE+NIC_PAGE_STOP]=0x80;
XBYTE[NE2000_BASE+NIC_INTR_STATUS]=0xff;
XBYTE[NE2000_BASE+NIC_INTR_MASK]=0;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x61;
iCount=0;
while (iCount<6)
XBYTE[NE2000_BASE+NIC_PHYS_ADDR+iCount]=Local_pMacAddress[iCount];
pHeaderSize[1]=0x47;
XBYTE[NE2000_BASE+NIC_CURRENT]=0x47;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x21;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x22;
XBYTE[NE2000_BASE+NIC_XMIT_CONFIG]=0;
bTransmiting=0;
Adapter_bOK=1;
return TRUE;
}
UCHAR CardGetCurrent()
{
UCHAR iTemp ;
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_PAGE1+CR_NO_DMA+CR_START;
iTemp=XBYTE[NE2000_BASE+NIC_CURRENT];
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_NO_DMA+CR_START;
return (iTemp);
}
void p_input(PINT8U Adapter_pReceiveBuff,UCHAR iNextPacket)
{
PINT8U pBuf;
pBuf=Adapter_pReceiveBuff;
while (iNextPacket--)
{
*pBuf=XBYTE[NE2000_BASE+NIC_RACK_NIC];
pBuf++;
}
}
void WaitRcvComplete()
{
DSHORT k ;
bdata UCHAR i;
k=65535;
while (k--)
{
i=XBYTE[NE2000_BASE+NIC_INTR_STATUS];
if (i&0x40) return; //remote DMA operation has been completed
}
}
void CardCopyUp(UCHAR iNextPacket,PINT8U Adapter_pReceiveBuff) //;Remote DMA WRITE
{
XBYTE[NE2000_BASE+NIC_RMT_ADDR_LSB]=*pHeaderSize;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_MSB]=*(pHeaderSize+1);
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=iNextPacket;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=0;
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_START+CR_DMA_READ;
if (iNextPacket)
p_input(Adapter_pReceiveBuff,iNextPacket);
WaitRcvComplete();
}
void CalcRecevLen(UCHAR i)
{
DSHORT Adapter_RcvLenS ;
Adapter_RcvLenS=P_MAKEWORD(Adapter_RcvLen,Adapter_RcvLenHigh);
Adapter_RcvLenS=Adapter_RcvLenS-i; //subtract IP header size
Adapter_RcvLenHigh=P_HIBYTE(Adapter_RcvLenS);
Adapter_RcvLen=P_LOBYTE(Adapter_RcvLenS);
}
void CardSaveLargePacket()
{
INT8U i ;
i=XBYTE[NE2000_BASE+NIC_COMMAND];
CalcRecevLen(0x26);
XBYTE[NE2000_BASE+NIC_RMT_ADDR_LSB]=*pHeaderSize;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_MSB]=*(pHeaderSize+1);
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=Adapter_RcvLen;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=Adapter_RcvLenHigh;
XBYTE[NE2000_BASE+NIC_COMMAND]=0x0a;
i=0;
while (i<Adapter_RcvLenHigh)
{
p_inp(0x5010,Sdram_pDataCache,0);
SramWrite(Sdram_pDataCache,i+NE2000_IN_INDEX);
i++;
}
if (Adapter_RcvLen)
{
p_inp(0x5010,Sdram_pDataCache,Adapter_RcvLen);
SramWrite(Sdram_pDataCache,i+NE2000_IN_INDEX);
}
WaitRcvComplete();
}
BOOLEAN CARDCHECKHEADER(PINT8U Adapter_pReceiveHeader)
{
PINT8U pBuf;
pBuf=Adapter_pReceiveHeader;
//5ah=Adapter_pReceiveHeader[0]
if (*pBuf & 0X5e)
return FALSE;
if (*pBuf & 0X20)
bBroadcastPacket=TRUE;
else bBroadcastPacket=FALSE; //26.7h
*(pHeaderSize+2)=*(pBuf+1) ;
if (*(pBuf+1)<0X46)
return FALSE;
else if (*(pBuf+1)>0X80)
return FALSE; //iNextPacket must>=0x46 <=0x80
Adapter_RcvLenHigh=*(pBuf+3);
if (*(pBuf+3) >=0X06)
return FALSE; //packet too big >1536
Adapter_RcvLen=*(pBuf+2);
//packet size must lager 64
return TRUE;
}
void IPRECEIVELARGEPACKET()
{
INT8U type ;
CardCopyUp(0x14,Adapter_pRcvPacket+0x14);
if (Adapter_pRcvPacket[0x14] ^ 0x45) //ip version
return;
pHeaderSize[0]=pHeaderSize[0]+0x14;
type=Adapter_pRcvPacket[0x1d]; //proto type
if (type==0x11) //UDP packet proto=17
{
CardSaveLargePacket();
SramRead(Adapter_pReceivePacket,NE2000_IN_INDEX,0,8);
UdpPort_HIGH=*(Adapter_pReceivePacket+2);
UdpPort_LOW=*(Adapter_pReceivePacket+3); //udp dest port
CalcRecevLen(0x08);
if (Adapter_RcvLenHigh>3) return;
SramRead(Adapter_pReceivePacket,NE2000_IN_INDEX,3,0);
UdpRun();
return;
}
if(!bDhcpUnFinished) return;
if(type==06) //tcp proto=6
{
CardSaveLargePacket();
if (Adapter_RcvLenHigh>3) return;
SramRead(Adapter_pReceivePacket,NE2000_IN_INDEX,3,0);
DebugVal(0x1023);
TcpRun();
return ;
}
if (type==01) //icmp proto=1
{
DebugVal(0x102A);
return;
}//_pIPReceivHeader[9]==01
}
void IpReceive()
{
INT8U type ;
struct tcp_packet *pep;
pep=(sruct tcp_packet *)Adapter_pRcvPacket;
DSHORT Adapter_RcvLenS;
CardCopyUp(0x14,Adapter_pRcvPacket+0x14);
if (Adapter_pRcvPacket[0x14] ^ 0x45) //ip version
return;
Adapter_RcvLenS=P_MAKEWORD(Adapter_pRcvPacket[0x17],Adapter_pReceivePacket[0x16]);
if(Adapter_RcvLenS<=0x14) return; // packetsize <30
if(Adapter_RcvLenS>0x600)return; //packet size>1536
CalcRecevLen(0x14);
pHeaderSize[0]=pHeaderSize[0]+0x14;
type=Adapter_pRcvPacket[0x1d]; //proto type
if (type==0x11) //UDP packet proto=17
{
if(Adapter_RcvLen<=0x08) return; //ip data <=8
CardCopyUp(Adapter_RcvLen,Adapter_pReceivePacket); //receive data to Receive buf
UdpPort_HIGH=*(Adapter_pReceivePacket+2);
UdpPort_LOW=*(Adapter_pReceivePacket+3); //udp dest port
Adapter_RcvLen+=0xf8; //ReceiveLen add 248
UdpRun();
return;
}
if(!bDhcpUnFinished) return;
if(type==06) //tcp proto=6
{
CardCopyUp(Adapter_RcvLen,Adapter_pReceivePacket);
TcpRun();
return ;
}
if (type==01) //icmp proto=1
{
CardCopyUp(Adapter_RcvLen,Adapter_pReceivePacket);
IcmpRun();
return;
}//_pIPReceivHeader[9]==01
}
void READPACKET()
{
*pHeaderSize=0;
CardCopyUp(6,Adapter_pReceivePacket+10); //read mac header 6 bytes;
*pHeaderSize=04;
if (CARDCHECKHEADER(Adapter_pReceivePacket+10))
goto X1;
pHeaderSize[0]=pHeaderSize[0]+1;
if (CARDCHECKHEADER(Adapter_pReceivePacket+11))
goto X1;
pHeaderSize[0]=pHeaderSize[0]+1;
if (!CARDCHECKHEADER(Adapter_pReceivePacket+12))
{
*(pHeaderSize+2)=0; //header invalid
return ; //38h=0
}
X1: //read Mac
CardCopyUp(0x0e,Adapter_pReceivePacket+EP_DATA+2);
*pHeaderSize=*pHeaderSize+0x0e;
if (*(Adapter_pReceivePacket+NE2000_IN_INDEX)!=0x08)
return;
ACC=*(Adapter_pReceivePacket+0x1d);
if (!ACC)
{
if (bBroadcastPacket)
if(bDhcpUnFinished) return;
if (Adapter_RcvLenHigh)
{
IPRECEIVELARGEPACKET();
return;
}
else
{
IpReceive();
return;
}
}
if (ACC!=0x06)
return;
if (!bDhcpUnFinished) return;
CardCopyUp(0x1c,Adapter_pReceivePacket);
ArpRun();
}
void NE2000RUN()
{
INT8U iCurrentPacket ;
iCurrentPacket=CardGetCurrent(); // GET the page address of the first receive buffer page OF CURRENT RECEPT PACKET
if (pHeaderSize[1]==iCurrentPacket)
return ;
READPACKET(); //;read packet
iCurrentPacket=CardGetCurrent();
if (pHeaderSize[2])
pHeaderSize[1]=pHeaderSize[2];
else pHeaderSize[1]=iCurrentPacket;
if (pHeaderSize[1]==0x46)
XBYTE[NE2000_BASE+NIC_BOUNDARY]=0x7f;
else
XBYTE[NE2000_BASE+NIC_BOUNDARY]=pHeaderSize[1]+0xff;
}
void CARDPREPARESEND()
{
INT8U i ;
DSHORT j ;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_LSB]=0;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_MSB]=0x40;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=0x02;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=0x0;
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_DMA_READ+CR_START;
i=XBYTE[NE2000_BASE+NIC_RACK_NIC];
i=XBYTE[NE2000_BASE+NIC_RACK_NIC];
j=65535;
while (j--)
{
if (XBYTE[NE2000_BASE+NIC_CRDA_LSB])
return;
if (XBYTE[NE2000_BASE+NIC_CRDA_MSB] ^0x40)
return;
}
}
void CARDDOTRANSMIT(UCHAR LengthHI,UCHAR LengthLO)
{
INT8U i ;
DSHORT j ;
bTransmiting=1;
XBYTE[NE2000_BASE+NIC_XMIT_START]=0x40;
XBYTE[NE2000_BASE+NIC_XMIT_COUNT_MSB]=LengthHI;
XBYTE[NE2000_BASE+NIC_XMIT_COUNT_LSB]=LengthLO;
i=XBYTE[NE2000_BASE+NIC_COMMAND];
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_NO_DMA+CR_START+CR_XMIT;
XBYTE[NE2000_BASE+NIC_INTR_MASK]=IMR_XMIT+IMR_XMIT_ERR; // enable IRQ
j=65535;
while (j--)
if(!bTransmiting) break;
XBYTE[NE2000_BASE+NIC_INTR_MASK]=0; //DISABLE ALL IRQ
}
void Ne2000HandleInterrupt()
{
INT8U iStatus ;
iStatus=XBYTE[NE2000_BASE+NIC_INTR_STATUS];
if (!iStatus)
return;
XBYTE[NE2000_BASE+NIC_INTR_STATUS]=iStatus;
if ((iStatus & 0x0a)!=0)
bTransmiting =0;
}
void Ne2000Send(UCHAR iLength, PINT8U pData)
{
INT8U type ;
INT8U Length ;
type=iLength;
CARDPREPARESEND();
if (type>=0x3c)
Length=type;
else
Length=0x3c;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_LSB]=0;
XBYTE[NE2000_BASE+NIC_RMT_ADDR_MSB]=0x40;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_LSB]=Length;
XBYTE[NE2000_BASE+NIC_RMT_COUNT_MSB]=0x0;
XBYTE[NE2000_BASE+NIC_COMMAND]=CR_DMA_WRITE+CR_START;
p_outp(0x5010,pData,type);
type=Length-type;
if (type)
p_setp(0x5010,0x20,type);
WaitRcvComplete();
CARDDOTRANSMIT(Length,0);
}
void Ne2000SendLargePacket(USHORT w1)
{
INT8U i ;
INT8U j ;
INT8U k ;
i=P_LOBYTE(w1);
j=P_HIBYTE(w1);
CARDPREPARESEND();
if (j==0)
if(i<0x3c) i=0x3c;
XBYTE[NE2000_BASE+8]=0;
XBYTE[NE2000_BASE+9]=0x40;
XBYTE[NE2000_BASE+10]=i;
XBYTE[NE2000_BASE+11]=j;
XBYTE[NE2000_BASE+0]=0x12;
if (j!=0)
{
k=0;
while(k++<j)
{
SramRead(Sdram_pDataCache,k+NE2000_IN_INDEX,1,0);
p_outp(0x5010,Sdram_pDataCache,0);
}
}
if(i!=0)
{
SramRead(Sdram_pDataCache,j+NE2000_IN_INDEX,1,0);
p_outp(0x5010,Sdram_pDataCache,0x5A);
}
WaitRcvComplete();
CARDDOTRANSMIT(i,j);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -