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

📄 xmodem.c

📁 STR71X系列ARM微控制器原理与实践配套光盘
💻 C
字号:
#include "Xmodem.h"
#include "Buffer.h"

static enum {
	ST_HEAD,
	ST_SEQ,
	ST_SEQC,
	ST_DATA,
	ST_CHKSUM,
	ST_STORE
} CurState;

static u32 RecvBuf[PACKET_1K_SIZE >> 2];
static unsigned PackLen, RecvLen;
static unsigned TimeCount;
static u8 FirstWait, Chksum;
static u8 CurSeq, SeqNum, SeqComp;
unsigned Xmodem_RecvSize;

static void Xmodem_Send(u8 c)
{
	UART_ByteSend(UARTX, &c);
}

void Xmodem_Reset(void)
{
	CurSeq = 0;
	CurState = ST_HEAD;
	TimeCount = NAK_TIMEOUT_WAIT;
	FirstWait = 1;
	Xmodem_RecvSize = 0;
}

int Xmodem_Action(void)
{
	u8 c;
	if(CurState == ST_STORE)
	{
		if(Buf_Put(RecvBuf, PackLen >> 2))
			return 0;
		CurSeq = SeqNum;
		c = ACK;
		goto Restart;
	}
	if(TimeCount)
	{
		if(UART_FlagStatus(UARTX) & (UART_RxHalfFull | UART_RxBufFull))
		{
			UART_ByteReceive(UARTX, &c, 0xFF);
			switch(CurState)
			{
			case ST_HEAD:
				switch(c)
				{
				case SOH:
					PackLen = PACKET_SIZE;
					break;
				case STX:
					PackLen = PACKET_1K_SIZE;
					break;
				case EOT:
					Xmodem_Send(ACK);
					return 1;
				default:
					c = NAK;
					goto Restart;
				}
				FirstWait = 0;
				CurState = ST_SEQ;
				break;
			case ST_SEQ:
				SeqNum = c;
				CurState = ST_SEQC;
				break;
			case ST_SEQC:
				SeqComp = c;
				RecvLen = 0;
				Chksum = 0;
				CurState = ST_DATA;
				break;
			case ST_DATA:
				((u8 *)RecvBuf)[RecvLen++] = c;
				Chksum += c;
				if(RecvLen >= PackLen)
					CurState = ST_CHKSUM;
				break;
			case ST_CHKSUM:
				if(SeqNum + SeqComp == 255 && Chksum == c)
				{
					if(SeqNum == CurSeq)
					{
						c = ACK;
						goto Restart;
					}
					else if(SeqNum == (CurSeq + 1 & 255))
					{
						Xmodem_RecvSize += PackLen;
						CurState = ST_STORE;
						break;
					}
				}
				c = NAK;
				goto Restart;
			}
			TimeCount = NAK_TIMEOUT_RECV;
		}
		else
			TimeCount--;
		return 0;
	}
	c = NAK;

Restart:
	Xmodem_Send(c);
	CurState = ST_HEAD;
	TimeCount = NAK_TIMEOUT_WAIT;
	return 0;
}

⌨️ 快捷键说明

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