📄 xmodem.c
字号:
g_xmodemProperty.ucCheckType = CHECK_SUM; } else { ucData = C; g_xmodemProperty.ucCheckType = CHECK_CRC; } putChar(&ucData); g_ulOldTicks = tickGet() + (U32)sysClkRateGet() * WAIT_SOH_TIME; } else { /*接收数据阶段没有回应则返回一个NAK,让发送端重发*/ ucData = NAK; putChar(&ucData); g_ulOldTicks = tickGet() + (U32)sysClkRateGet(); } g_ulRetry ++ ; } else { printf("\r\n xModemLink:Retry > MAX_RETRY!"); ucData = CAN; putChar(&ucData); free(g_xmodemProperty.pPacketData); return XMODEM_ERROR; } } } }/***************************************************************************** 函 数 名 : xModemStartSend(void) 功能描述 : xmodem发送端根据接收的字符决定发送数据采用什么校验方式 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : *****************************************************************************/ STATUS xModemStartSend(void){ unsigned char ucData; if(OK == getChar(&ucData)) { switch ( ucData ) { case C: g_xmodemProperty.ucCheckType = CHECK_CRC; g_linkState = TRANS_DATA; return XMODEM_OK; case NAK: g_xmodemProperty.ucCheckType = CHECK_SUM; g_linkState = TRANS_DATA; case CAN: g_linkState = XMODEM_REMOTE_CANCELES; return XMODEM_ERROR; default: break; } } return XMODEM_OK;}/***************************************************************************** 函 数 名 : xModemWaitAck(void) 功能描述 : xmodem发送端等待接收端的回应 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : *****************************************************************************/ STATUS xModemWaitAck(void){ U8 ucData; if(OK == getChar(&ucData)) { switch ( ucData ) { case ACK: /*如果是最后一个数据包,则发送结束*/ if(TRANS_EOT == g_linkState) { ucData = EOT; putChar(&ucData); putChar(&ucData); g_ulRetry = 0; g_linkState = END_OF_LINK; } else { g_xmodemProperty.ucPacketNo ++; g_xmodemProperty.ulDataLength += g_xmodemProperty.ulProSize; g_linkState = TRANS_DATA; } return XMODEM_OK; case NAK: g_linkState = TRANS_DATA ; case CAN: g_linkState = XMODEM_REMOTE_CANCELES; return XMODEM_ERROR; default: break; } } return XMODEM_OK;}/***************************************************************************** 函 数 名 : xModemPutPacket(void) 功能描述 : xmodem发送端发送一个数据包 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : *****************************************************************************/ STATUS xModemPutPacket(void){ U8 ucCheckSum; U16 usCrcVal; U32 ulLenTemp,i; ucCheckSum = 0; g_ulRetry = 0; g_ulOldTicks = tickGet() + (U32)sysClkRateGet (); g_xmodemProperty.pPacketData[0] = SOH; g_xmodemProperty.pPacketData[1] = g_xmodemProperty.ucPacketNo; g_xmodemProperty.pPacketData[2] = ~g_xmodemProperty.ucPacketNo; if(g_ulFileMaxLen > g_xmodemProperty.ulProSize) { ulLenTemp = g_ulFileMaxLen - g_xmodemProperty.ulDataLength; } else { ulLenTemp = g_ulFileMaxLen; } if(ulLenTemp > g_xmodemProperty.ulProSize) { memcpy (&g_xmodemProperty.pPacketData[3], &g_xmodemProperty.pDataPtr[g_xmodemProperty.ulDataLength],g_xmodemProperty.ulProSize); g_linkState = WAIT_FOR_ACK; } else { memcpy (&g_xmodemProperty.pPacketData[3], &g_xmodemProperty.pDataPtr[g_xmodemProperty.ulDataLength],ulLenTemp); memset (&g_xmodemProperty.pPacketData[3+ulLenTemp], CTZ, g_xmodemProperty.ulProSize - ulLenTemp); g_linkState = TRANS_EOT; } ulLenTemp = g_xmodemProperty.ulProSize; if(CHECK_CRC == g_xmodemProperty.ucCheckType) { usCrcVal = CRC16_CCITT(&g_xmodemProperty.pPacketData[3], ulLenTemp); g_xmodemProperty.pPacketData[ulLenTemp+3] = (usCrcVal>>8) & 0xFF; g_xmodemProperty.pPacketData[ulLenTemp+4] = usCrcVal & 0xFF; } else { for (i = 3; i < ulLenTemp + 3; ++i) { ucCheckSum += g_xmodemProperty.pPacketData[i]; } g_xmodemProperty.pPacketData[ulLenTemp+3] = ucCheckSum; } for(i = 0; i < g_xmodemProperty.ulProSize+ 4 +(g_xmodemProperty.ucCheckType ? 1:0); ++i) { putChar(&g_xmodemProperty.pPacketData[i]); } return XMODEM_OK;}/***************************************************************************** 函 数 名 : xmodemTransmit(unsigned char *pBuffer, U32 ulLength) 功能描述 : xmodem发送端发送文件接口函数 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : pBuffer:发送数据的内存起始地址*****************************************************************************/ STATUS xmodemTransmit(unsigned char *pBuffer, U32 ulLength){ if(NULL == pBuffer) return XMODEM_ERROR; memset(&g_xmodemProperty,0,sizeof(XMODEM_PROPERTY_STRUCT)); g_ulFileMaxLen = ulLength; g_xmodemProperty.pDataPtr = pBuffer; g_xmodemProperty.pPacketData = malloc(PACKET_MAX_LEM);/* 1024(XModem 1k数据) + 2(序列号空间) + 2 (crc 空间)+ NULL */ memset(g_xmodemProperty.pPacketData,0,PACKET_MAX_LEM); g_xmodemProperty.ucPacketNo = 1; g_xmodemProperty.ulProSize = XMODEM_DATA_LENGTH; g_ulRetry = 0; g_ulOldTicks = tickGet () + (U32)sysClkRateGet() * WAIT_SOH_TIME; g_linkState = START_OF_LINK; flushSerial( ); while(1) { switch(g_linkState) { case START_OF_LINK: xModemStartSend( );/*等待接收端发送的校验方式*/ break; case TRANS_DATA: xModemPutPacket( );/*发送一个完整的数据包*/ break; case TRANS_EOT: case WAIT_FOR_ACK: xModemWaitAck( );/*等待接收端的回应*/ break; case END_OF_LINK: free(g_xmodemProperty.pPacketData); return XMODEM_OK; default: free(g_xmodemProperty.pPacketData); return XMODEM_ERROR; } /*接收端没有回应时超时处理*/ if ( tickGet() >= g_ulOldTicks ) { if ( g_ulRetry < MAX_RETRY ) { if(START_OF_LINK == g_linkState) { g_ulOldTicks = tickGet () + (U32)sysClkRateGet () * WAIT_SOH_TIME; } else { g_ulOldTicks = tickGet () + (U32)sysClkRateGet (); } g_ulRetry ++ ; } else { printf("\r\n xModemLink:Retry > MAX_RETRY!"); free(g_xmodemProperty.pPacketData); return XMODEM_ERROR; } } }}/***************************************************************************** 函 数 名 : xmodemRevTest(unsigned char *pBuffer, U32 *pLength) 功能描述 : xmodem接收测试接口 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : 使用前注意:设置串口模式为原始模式。由于CTRL+X对应vxworks的复位, 使用时可以通过tyMonitorTrapSet(0);将其功能屏蔽。*****************************************************************************/ STATUS xmodemRevTest(unsigned char *pBuffer, U32 *pLength){ U32 ulRval; (void)ioctl(STD_IN,FIOSETOPTIONS,OPT_RAW); (void)ioctl(STD_OUT,FIOSETOPTIONS,OPT_RAW); (void)ioctl(STD_ERR,FIOSETOPTIONS,OPT_RAW); (void) flushSerial( ); tyMonitorTrapSet(0); ulRval = xmodemReceive(pBuffer,pLength); (void) ioctl (STD_IN, FIOSETOPTIONS, OPT_TERMINAL); (void) ioctl (STD_OUT, FIOSETOPTIONS, OPT_TERMINAL); (void) ioctl (STD_ERR, FIOSETOPTIONS, OPT_TERMINAL); (void) flushSerial( ); printf("g_linkState:%d",g_linkState); return ulRval;}/***************************************************************************** 函 数 名 :xmodemTraTest(unsigned char *pBuffer, U32 pLength) 功能描述 : xmodem发送测试接口 日 期 : 2008年6月26日 作 者 : gateWay 说 明 : 使用前注意:设置串口模式为原始模式。由于CTRL+X对应vxworks的复位, 使用时可以通过tyMonitorTrapSet(0);将其功能屏蔽。*****************************************************************************/ STATUS xmodemTraTest(unsigned char *pBuffer, U32 pLength){ U32 ulRval; tyMonitorTrapSet(0); (void)ioctl(STD_IN,FIOSETOPTIONS,OPT_RAW); (void)ioctl(STD_OUT,FIOSETOPTIONS,OPT_RAW); (void)ioctl(STD_ERR,FIOSETOPTIONS,OPT_RAW); (void) flushSerial( ); ulRval = xmodemTransmit(pBuffer,pLength); (void) ioctl (STD_IN, FIOSETOPTIONS, OPT_TERMINAL); (void) ioctl (STD_OUT, FIOSETOPTIONS, OPT_TERMINAL); (void) ioctl (STD_ERR, FIOSETOPTIONS, OPT_TERMINAL); (void) flushSerial( ); printf("g_linkState:%d",g_linkState); return ulRval;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -