📄 +
字号:
#define SOH 0x01
#define STX 0x02
#define EOT 0x04
#define ACK 0x06
#define NAK 0x15
#define CAN 0x18
#define CTRLZ Ox1A
#define DLY_1S 1000
#define MAXRETRANS 25
#define DINBUFSIZE 1023
#define DOUTBUFSIZE 255
#define DPORTSPEED 9600L
#define MAX_UDP_SOCKET_BUFFERS 1
char tempbuf[512];
#memmap xmem
#use "dcrtcp.lib"
#define ERR_OTHER 0
#define ERR_NOTFOUND 1
#define ERR_ACCESS 2
#define ERR_NOSPACE 3
#define ERR_ILLEGAL 4
#define ERR_PORT 5
#define ERR_EXISTS 6
#define ERR_NOUSER 7
#use crcl6.lib
#define _outbyte serDputc
#define _inbyte xm_serDgetc
int xm_serDgetc(int msdelay);
int xm_serDgetc(int msdelay)
{
long time;
int res;
time = MS_IMER + msdelay;
for (;;)
{
res = serDgetc();
if (MS_TIMER >= time)
break;
if (res != - 1)
break;
}
return res;
}
struct RunTimeContext
{
udp_Socket *m_pSocket;
char m_pBuffer[1024];
unsigned long m_dwTimeOut;
};
void SendErrorMsg(struct RunTimeContext *pRunTime, char type, char
*pMsg)
{
char buffer[1024];
memset(buffer, 0x00, sizeof(buffer));
buffer[0] = 0;
buffer[1] = 5;
buffer[2] = 0;
buffer[3] = type;
strcpy(buffer + 4, pMsg);
udp_send(pRunTime->m_pSocket, buffer, strlen(pmsg) + 5);
printf("Error message <%d>'%s' was sent\n", type, pMsg);
}
void SendAckMsg(struct RunTimeContext *pRunTime, int block)
{
char buffer[1024];
memset(buffer, 0x00, sizeof(buffer));
buffer[0] = 0;
buffer[1] = 4;
buffer[2] = ((char*) &block)[1];
buffer[3] = ((char*) &block)[0];
udp_send(pRunTime->m_pSocket, buffer, 4);
printf("ACK <%d> was sent\n", block);
}
int WaitForACKMsg(struct RunTimeContext *pRunTime, int iBlock)
{
int iACKBlock;
int iRetval;
unsigned long dwStartTime;
char buffer[1024];
memset(buffer, 0x00, sizeof(buffer));
dwStartTime = SEC_TIMER;
while (1)
{
if (SEC_IMER > (dwStartTime + pRunTime->m_dwTimeOut))
{
printf("TIMEOUT on waiting for ACK;resendingACK. \ n ");
return 2;
}
tcp_tick(pRunTime->m_pSocket);
iRetval = udp_recv(pRunTime->m_pSocket, buffer, sizeof(buffer));
if (iRetval > 0)
{
switch (buffer[1])
{
case 4:
{
iACKBlock = buffer[3] + (256 *buffer[2]);
if (iACKBlock == iBlock)
{
printf("Got ACK <%d>\n", iACKBlock);
return 0;
}
else
{
printf("Received incorrect ACK (%d)\n", iACKBlock);
}
}
break;
case 5:
{
printf("ERROR was received. Bailing...\n");
return 1;
}
break;
default:
{
SendErrorMsg(pRunTime, ERR_ILLEGAL, "Expected ACK");
return 1;
}
break;
}
}
}
}
int check(int crc, char *buf, int sz)
{
unsigned tcrc;
int i;
char cks;
if (crc)
{
crc = (unsigned)crc16_ccitt(buf, sz);
tcrc = (buf[sz] << 8) + buf[sz + l];
if (crc == tcrc)
return 1;
}
else
{
cks = 0;
for (i = 0; i < sz; ++i)
{
cks += buf[i];
}
if (cks == buf[sz])
return 1;
}
return 0;
}
void flushinput(void)
{
while (_inbyte(((DLY_1S) *3) >> 1) >= 0);
}
int xmodemReceive(unsigned char *dest, int destsz)
{
char xbuff[1030];
auto char trychar, packetno, *p;
auto int i, count, c, len, retry, retrans, bufsz, crc, templen,
trantime;
int iSvcPort, iBlock;
int iRetVal;
udp_Socket socket;
struct RunTimeContext runtime;
struct RunTimeContext *pRunTime;
char buffer[518];
iBlock = 0;
pRunTime = &runtime;
pRunTime->m_pSocket = &socket;
pRunTime->m_dwTimeOut = 10L;
iSvcPort = 69;
if (!udp_open(pRunTime->m_pSocket, iSvcPort, 0, 0, NULL))
{
printf("Can not setup the tftp service udp open!\n");
exit(0);
} crc = 0;
trychar = 'C';
packetno = 1;
len = 0;
templen = 0;
retrans = MAXRETRANS;
trantime = 0;
for (;;)
{
for (retry = 0; retry < 16; ++retry)
{
if (trychar)
_outbyte(trychar);
if ((c = _inbyte((DLY_1S) << 1)) >= 0)
{
switch (c)
{
case SOH:
bufsz = 128;
if (trantime == 4 && Block == 0)
{
trantime = 0;
printf("begin to transmit to ethernet\n");
templen = 0;
do
{
tcp_tick(pRunTime->m_pSocket);
iRetVal = udp_recv(pRunTime->m_pSocket, pRunTime
->m_pBuffer, sizeof(pRunTime->m_pBuffer));
printf("received iRetVal is %d \n", iRetVal);
printf("received pRunTime->m_pBuffer[1] is %d \n",
pRunTime->m_pBuffer[1]);
}
while (iRetVal <= 0);
switch (pRunTime->m_pBuffer[1])
{
case 1:
{
printf("Read request received for file'%s' \n",
pRunTime->m_pBuffer + 2);
iBlock++;
ProcessRead(pRunTime, iBlock);
}
break;
case 4:
{
printf("ACK <%d> was received (error) \n",
pRunTime->m_pBuffer[3] + (256 *pRunTime
->m_pBuffer[2]));
}
break;
default:
break;
}
}
if (trantime == 4 && iBlock > 0)
{
printf("transmit 96d iBlock to ethernet\n", iBlock);
templen = 0;
trantime = 0;
iBlock++;
ProcessRead(pRunTime, iBlock);
}
goto start_recv;
case EOT:
iBlock++;
endread(pRunTime, iBlock, templen);
flushinput();
_outbyte(ACK);
sock_close(pRunTime->m_pSocket);
udp_open(pRunTime->m_pSocket, iSvcPort, 0, 0, NULL);
return len;
case CAN:
if ((c = _inbyte(DLY_1S)) == CAN)
{
flushinput();
_outbyte(ACK);
return - 1;
}
break;
default:
break;
}
}
}
if (trychar == 'C')
{
trychar = NAK;
continue;
}
flushinput();
_outbyte(CAN);
_outbyte(CAN);
_outbyte(CAN);
return - 2;
start recv;
if (trychar == 'C')
crc = 1;
trychar = 0;
p = xbuff;
*p++ = c;
for (i = 0; i < (bufsz + (crc ? 1: 0) + 3); ++i)
{
if ((c = _inbyte(DLY_1S)) < 0)
goto reject;
*p++ = c;
}
if (xbuff[1] == (char)(~xbuff[2]) && (xbuff[1] == packetno ||
xbuff[1] == (char)packetno - 1) && check(crc, &xbuff[3],
bufsz))
{
if (xbuff[1] == packetno)
{
count = destsz - templen;
if (count > bufsz)
count = bufsz;
if (count > 0)
{
memcpy(&dest[templen], &xbuff[3], count);
len += count;
templen += count;
}
printf("send %d packetno to ethernet\n", packetno);
++packetno;
retrans = MAXRETRANS + 1;
}
if (--retrans <= 0)
{
flushinput();
_outbyte(CAN);
_outbyte(CAN);
_outbyte(CAN);
return - 3;
}
_outbyte(ACK);
trantime += 1;
continue;
}
reject: flushinput();
_outbyte(NAK);
}
}
void main()
{
int st;
sock_init();
ifconfig
(
IF_ETHO,
IFS_DOWN,
IFS_IPADDR,
aton("192. 168. 1. 3"),
IFS_NETMASK,
OxFFFFFFOOuL,
IFS_ROUTER_SET,
aton("192. 168. 1. 1"),
IFS_UP, IFS_END
);
for (;;)
{
serDopen(DPORTSPEED);
printf(
"Send data using the xmodem protocol from your terminal emulator now...\n");
st = xmodemReceive(tempbuf, sizeof(tempbuf));
if (st < 0)
{
printf("Xmodem receive error:status:%d\n", st);
}
else
{
printf("Xmodem successfully received %d bytes\n", st);
}
}
}
int ProcessRead(struct RunTimeContext *pRunTime, int iBlock)
{
int iRetval;
pRunTime->m_pBuffer[0] = 0;
pRunTime->m_pBuffer[1] = 3;
pRunTime->m_pBuffer[2] = ((char*) &iBlock)[1];
pRunTime->m_pBuffer[3] = ((char*) &iBlock)[0];
memcpy(pRunTime->m_pBuffer + 4, tempbuf, 512);
memset(tempbuf, 0, 512);
udp_send(pRunTime->m_pSocket, pRunTime->m_pBuffer, 516);
printf("Wrote data block <96d> with size 512\n", iBlock);
tcp_tick(pRunTime->m_pSocket);
iRetval = WaitForACKMsg(pRunTime, iBlock);
if (iRetval == 1)
{
return 1;
}
return ;
}
int endread(struct RunTimeContext *pRunTime, int iBlock, int
templen)
{
int iRetval;
pRunTime->m_pBuffer[0] = 0;
pRunTime->m_pBuffer[1] = 3;
pRunTime->m_pBuffer[2] = ((char*) &iBlock)[1];
pRunTime->m_pBuffer[3] = ((char*) &iBlock)[0];
if (templen == 0)
memset(pRunTime->m_pBuffer + 4, CTRLZ, 1);
else
memcpy(pRunTime->m_pBuffer + 4, tempbuf, templen);
udp_send(pRunTime->m_pSocket, pRunTime->m_pBuffer, templen + 4);
printf("Wrote data block <%d> with size %d\n", iBlock, templen);
iRetval = WaitForACKMsg(pRunTime, iBlock);
if (iRetval == 1)
{
return 1;
}
printf("All done. \n\n");
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -