00001 /****************************************************** 00002 * Function: Xmodem protocol for image download through 00003 * rs232 00004 * 00005 * File: xmodem.c 00006 * Author: Book Chen 00007 * Date: 2008.07.18 00008 ******************************************************* 00009 */ 00010 #include "includes.h" 00011 00012 #define XmodemIdleState 0 00013 #define XmodemRxState0 1 00014 #define XmodemRxState1 2 00015 #define XmodemRxState2 3 00016 00017 #define XmodemSohSubstate 0 00018 #define XmodemBlockNumberSubstate 1 00019 #define XmodemBlockNumber2Substate 2 00020 #define XmodemDataSubstate 3 00021 00022 #define XMODEM_DOWNLOAD_ADDRESS 0x30100000 00023 00024 XMODEM_CONTROL XmodemCtrl; 00025 00026 void F_XmodemInit(void); 00027 void F_XmodemSvc(void); 00028 BOOL F_XmodemCrcCheck(INT8U *pData); 00029 void F_XmodemRxStart(void); 00030 BOOL F_XmodemStatusCheck(void); 00031 void F_XmodemRxReset(void); 00032 00033 void F_XmodemInit(void){ 00034 XmodemCtrl.InUse=FALSE; 00035 XmodemCtrl.NewBlock=0; 00036 XmodemCtrl.BlockNumber=1; 00037 XmodemCtrl.Error=0; 00038 XmodemCtrl.ErrorCount=0; 00039 XmodemCtrl.ErrorCode=0; 00040 XmodemCtrl.ErrorRecord=0; 00041 XmodemCtrl.Buffer.Put=0; 00042 XmodemCtrl.Buffer.Get=0; 00043 XmodemCtrl.ByteCount=0; 00044 XmodemCtrl.Timer=0; 00045 XmodemCtrl.ReceiveStart=FALSE; 00046 XmodemCtrl.ReceiveFinish=FALSE; 00047 XmodemCtrl.pData=(INT8U *)XMODEM_DOWNLOAD_ADDRESS; 00048 XmodemCtrl.State=XmodemIdleState; 00049 XmodemCtrl.SubState=XmodemSohSubstate; 00050 } 00051 void F_XmodemRxStart(void){ 00052 XmodemCtrl.State=XmodemRxState0; 00053 } 00054 BOOL F_XmodemStatusCheck(void){ 00055 if(XmodemCtrl.State==XmodemIdleState) return TRUE; 00056 else return FALSE; 00057 } 00058 void F_XmodemRxReset(void){ 00059 XmodemCtrl.NewBlock=0; 00060 XmodemCtrl.BlockNumber=1; 00061 XmodemCtrl.Error=0; 00062 XmodemCtrl.ErrorCount=0; 00063 XmodemCtrl.ErrorCode=0; 00064 XmodemCtrl.ErrorRecord=0; 00065 XmodemCtrl.Buffer.Put=0; 00066 XmodemCtrl.Buffer.Get=0; 00067 XmodemCtrl.ByteCount=0; 00068 XmodemCtrl.TotalBlockCount=0; 00069 XmodemCtrl.Timer=0; 00070 XmodemCtrl.ReceiveStart=FALSE; 00071 XmodemCtrl.ReceiveFinish=FALSE; 00072 XmodemCtrl.pData=(INT8U *)XMODEM_DOWNLOAD_ADDRESS; 00073 XmodemCtrl.State=XmodemIdleState; 00074 XmodemCtrl.SubState=XmodemSohSubstate; 00075 } 00076 BOOL F_XmodemCrcCheck(INT8U *pData){ 00077 INT16U Crc16,DataCrc16; 00078 INT8U ByteCount; 00079 INT8U i; 00080 00081 Crc16=0; 00082 DataCrc16=0; 00083 ByteCount=128; 00084 while(ByteCount--){ 00085 Crc16=Crc16^((INT16U)*pData++<<8); 00086 for(i=0;i<8;i++){ 00087 if(Crc16&0x8000) Crc16=(Crc16<<1)^0x1021; 00088 else Crc16=Crc16<<1; 00089 } 00090 } 00091 DataCrc16=(*pData++)*0x100; 00092 DataCrc16+=*pData; 00093 if(DataCrc16==Crc16) return TRUE; 00094 else return FALSE; 00095 } 00096 void F_XmodemSvc(void){ 00097 INT8U Data; 00098 INT8U i; 00099 00100 if(XmodemCtrl.State==XmodemIdleState) return; 00101 switch(XmodemCtrl.State){ 00102 case XmodemIdleState: 00103 break; 00104 case XmodemRxState0: 00105 F_XmodemRxReset(); 00106 XmodemCtrl.State=XmodemRxState1; 00107 break; 00108 case XmodemRxState1: 00109 if((XmodemCtrl.Timer==0)&&(XmodemCtrl.ReceiveStart==FALSE)){ // xmodem start condition 00110 F_Uart0TxBufferPut(XMODEM_CHAR_C); 00111 while(F_Uart0TxBufferCheck()!=UART0_BUFFER_EMPTY) F_Uart0Svc(); // for usrt tx 00112 while(Uart0Ctrl.UartTxTransmit==1) F_Uart0Svc(); 00113 XmodemCtrl.Timer=3000; //300*1ms=3sec 00114 } 00115 else if((XmodemCtrl.Timer==0)&&(XmodemCtrl.ReceiveStart==TRUE)){ // time out to restart 00116 F_XmodemRxReset(); 00117 break; 00118 } 00119 if(F_Uart0RxBufferCheck()==UART0_BUFFER_EMPTY) return; 00120 //while(F_Uart0RxBufferCheck()!=UART0_BUFFER_EMPTY){ 00121 XmodemCtrl.Timer=30000; // 30000*1ms=30sec 00122 XmodemCtrl.ReceiveStart=TRUE; 00123 while(1){ 00124 while(F_Uart0RxBufferCheck()!=UART0_BUFFER_EMPTY){ 00125 if(XmodemCtrl.Timer==0) break; 00126 Data=F_Uart0RxBufferGet(); 00127 switch(XmodemCtrl.SubState){ 00128 case XmodemSohSubstate: 00129 if(Data==XMODEM_SOH) XmodemCtrl.SubState=XmodemBlockNumberSubstate; 00130 else if(Data==XMODEM_EOT) XmodemCtrl.ReceiveFinish=TRUE; 00131 else if(Data==XMODEM_ETB) XmodemCtrl.ReceiveFinish=TRUE; 00132 else if(Data==XMODEM_CAN){ // force receiver to send 'C' 00133 F_Uart0TxBufferPut(XMODEM_CHAR_C); 00134 while(F_Uart0TxBufferCheck()!=UART0_BUFFER_EMPTY) F_Uart0Svc(); // for usrt tx 00135 while(Uart0Ctrl.UartTxTransmit==1) F_Uart0Svc(); 00136 } 00137 else{ 00138 XmodemCtrl.Error=1; 00139 XmodemCtrl.ErrorCode=1; 00140 XmodemCtrl.ErrorRecord=Data; 00141 } 00142 break; 00143 case XmodemBlockNumberSubstate: 00144 if(Data==XmodemCtrl.BlockNumber) XmodemCtrl.SubState=XmodemBlockNumber2Substate; 00145 else{ 00146 XmodemCtrl.Error=1; 00147 XmodemCtrl.ErrorCode=2; 00148 } 00149 break; 00150 case XmodemBlockNumber2Substate: 00151 if(Data==(0xff-XmodemCtrl.BlockNumber)){ 00152 XmodemCtrl.SubState=XmodemDataSubstate; 00153 XmodemCtrl.Buffer.Put=0; 00154 } 00155 else{ 00156 XmodemCtrl.Error=1; 00157 XmodemCtrl.ErrorCode=3; 00158 } 00159 break; 00160 case XmodemDataSubstate: 00161 if(XmodemCtrl.Buffer.Put<130){ // 128 data byte + 2 crc byte 00162 XmodemCtrl.Buffer.Data[XmodemCtrl.Buffer.Put]=Data; 00163 XmodemCtrl.Buffer.Put++; 00164 if(XmodemCtrl.Buffer.Put==130){ 00165 XmodemCtrl.NewBlock=1; 00166 } 00167 } 00168 break; 00169 } 00170 if(XmodemCtrl.NewBlock==1) break; 00171 if(XmodemCtrl.Error==1) break; 00172 } 00173 if(XmodemCtrl.NewBlock==1){ 00174 XmodemCtrl.Timer=30000; 00175 XmodemCtrl.NewBlock=0; 00176 F_Uart0TxBufferPut(XMODEM_ACK); 00177 while(F_Uart0TxBufferCheck()!=UART0_BUFFER_EMPTY) F_Uart0Svc(); // for usrt tx 00178 while(Uart0Ctrl.UartTxTransmit==1) F_Uart0Svc(); 00179 if(F_XmodemCrcCheck(XmodemCtrl.Buffer.Data)==TRUE){ 00180 XmodemCtrl.BlockNumber++; 00181 XmodemCtrl.TotalBlockCount++; 00182 XmodemCtrl.ByteCount+=128; 00183 for(i=0;i<128;i++) *XmodemCtrl.pData++=XmodemCtrl.Buffer.Data[i]; 00184 XmodemCtrl.SubState=XmodemSohSubstate; 00185 } 00186 else{ 00187 XmodemCtrl.Error=1; 00188 XmodemCtrl.ErrorCode=4; 00189 } 00190 } 00191 if(XmodemCtrl.Error==1){ 00192 //XmodemCtrl.ErrorCount++; 00193 F_Uart0TxBufferPut(XMODEM_NAK); 00194 while(F_Uart0TxBufferCheck()!=UART0_BUFFER_EMPTY) F_Uart0Svc(); // for usrt tx 00195 while(Uart0Ctrl.UartTxTransmit==1) F_Uart0Svc(); 00196 XmodemCtrl.State=XmodemIdleState; 00197 break; 00198 } 00199 if(XmodemCtrl.ErrorCount==100){ 00200 XmodemCtrl.ByteCount=0; 00201 XmodemCtrl.State=XmodemIdleState; 00202 } 00203 if(XmodemCtrl.ReceiveFinish==TRUE){ 00204 XmodemCtrl.State=XmodemIdleState; 00205 XmodemCtrl.SubState=XmodemSohSubstate; 00206 } 00207 if((XmodemCtrl.State==XmodemIdleState)||( XmodemCtrl.Timer==0)) break; 00208 } 00209 break; 00210 default: 00211 break; 00212 } 00213 } 00214