26 #ifdef USE_SERIAL_4WAY_BLHELI_INTERFACE
29 #include "drivers/io.h"
30 #include "drivers/serial.h"
31 #include "drivers/system.h"
33 #include "io/serial.h"
40 #ifdef USE_SERIAL_4WAY_SK_BOOTLOADER
42 #define BIT_LO_US (32) //32uS
43 #define BIT_HI_US (2*BIT_LO_US)
45 static uint8_t StkInBuf[16];
47 #define STK_BIT_TIMEOUT 250 // micro seconds
48 #define STK_WAIT_TICKS (1000 / STK_BIT_TIMEOUT) // per ms
49 #define STK_WAITCYLCES (STK_WAIT_TICKS * 35) // 35ms
50 #define STK_WAITCYLCES_START (STK_WAIT_TICKS / 2) // 0.5 ms
51 #define STK_WAITCYLCES_EXT (STK_WAIT_TICKS * 5000) //5 s
53 #define WaitPinLo while (ESC_IS_HI) {if (micros() > timeout_timer) goto timeout;}
54 #define WaitPinHi while (ESC_IS_LO) {if (micros() > timeout_timer) goto timeout;}
56 static uint32_t LastBitTime;
57 static uint32_t HiLoTsh;
59 static uint8_t SeqNumber;
60 static uint8_t StkCmd;
61 static uint8_t ckSumIn;
62 static uint8_t ckSumOut;
65 #define MESSAGE_START 0x1B
68 #define CMD_SIGN_ON 0x01
69 #define CMD_LOAD_ADDRESS 0x06
70 #define CMD_CHIP_ERASE_ISP 0x12
71 #define CMD_PROGRAM_FLASH_ISP 0x13
72 #define CMD_READ_FLASH_ISP 0x14
73 #define CMD_PROGRAM_EEPROM_ISP 0x15
74 #define CMD_READ_EEPROM_ISP 0x16
75 #define CMD_READ_SIGNATURE_ISP 0x1B
76 #define CMD_SPI_MULTI 0x1D
78 #define STATUS_CMD_OK 0x00
80 #define CmdFlashEepromRead 0xA0
81 #define EnterIspCmd1 0xAC
82 #define EnterIspCmd2 0x53
83 #define signature_r 0x30
85 #define delay_us(x) delayMicroseconds(x)
86 #define IRQ_OFF // dummy
87 #define IRQ_ON // dummy
89 static void StkSendByte(uint8_t dat)
92 for (uint8_t
i = 0;
i < 8;
i++) {
114 static void StkSendPacketHeader(
void)
122 StkSendByte(MESSAGE_START);
123 StkSendByte(++SeqNumber);
126 static void StkSendPacketFooter(
void)
128 StkSendByte(ckSumOut);
137 static int8_t ReadBit(
void)
139 uint32_t btimer = micros();
140 uint32_t timeout_timer = btimer + STK_BIT_TIMEOUT;
143 LastBitTime = micros() - btimer;
144 if (LastBitTime <= HiLoTsh) {
145 timeout_timer = timeout_timer + STK_BIT_TIMEOUT;
157 static uint8_t ReadByte(uint8_t *bt)
160 for (uint8_t
i = 0;
i < 8;
i++) {
161 int8_t bit = ReadBit();
162 if (bit == -1)
goto timeout;
173 static uint8_t StkReadLeader(
void)
177 HiLoTsh = BIT_HI_US + BIT_LO_US;
182 if((StkCmd == CMD_PROGRAM_EEPROM_ISP) || (StkCmd == CMD_CHIP_ERASE_ISP)) {
183 waitcycl = STK_WAITCYLCES_EXT;
184 }
else if(StkCmd == CMD_SIGN_ON) {
185 waitcycl = STK_WAITCYLCES_START;
187 waitcycl= STK_WAITCYLCES;
189 for ( ; waitcycl >0 ; waitcycl--) {
191 if (ReadBit() >- 1)
break;
199 for (uint8_t
i = 0;
i < 10;
i++) {
200 if (ReadBit() == -1)
goto timeout;
204 HiLoTsh = (LastBitTime >> 1) + (LastBitTime >> 2);
210 if (bit == -1)
goto timeout;
217 static uint8_t StkRcvPacket(uint8_t *pstring)
223 if (!StkReadLeader())
goto Err;
225 if (!ReadByte(&bt) || (bt != MESSAGE_START))
goto Err;
226 if (!ReadByte(&bt) || (bt != SeqNumber))
goto Err;
227 ReadByte(&Len.bytes[1]);
228 if (Len.bytes[1] > 1)
goto Err;
229 ReadByte(&Len.bytes[0]);
230 if (Len.bytes[0] < 1)
goto Err;
231 if (!ReadByte(&bt) || (bt != TOKEN))
goto Err;
232 if (!ReadByte(&bt) || (bt != StkCmd))
goto Err;
233 if (!ReadByte(&bt) || (bt != STATUS_CMD_OK))
goto Err;
234 for (uint16_t
i = 0;
i < (Len.word - 2);
i++)
236 if (!ReadByte(pstring))
goto Err;
240 if (ckSumIn != 0)
goto Err;
248 static uint8_t _CMD_SPI_MULTI_EX(
volatile uint8_t * ResByte,uint8_t Cmd,uint8_t AdrHi,uint8_t AdrLo)
250 StkCmd= CMD_SPI_MULTI;
251 StkSendPacketHeader();
255 StkSendByte(CMD_SPI_MULTI);
263 StkSendPacketFooter();
264 if (StkRcvPacket((
void *)StkInBuf)) {
265 if ((StkInBuf[0] == 0x00) && ((StkInBuf[1] == Cmd)||(StkInBuf[1] == 0x00)) &&(StkInBuf[2] == 0x00)) {
266 *ResByte = StkInBuf[3];
273 static uint8_t _CMD_LOAD_ADDRESS(
ioMem_t *pMem)
278 StkCmd = CMD_LOAD_ADDRESS;
279 StkSendPacketHeader();
283 StkSendByte(CMD_LOAD_ADDRESS);
288 StkSendPacketFooter();
289 return (StkRcvPacket((
void *)StkInBuf));
292 static uint8_t _CMD_READ_MEM_ISP(
ioMem_t *pMem)
300 StkSendPacketHeader();
307 StkSendByte(CmdFlashEepromRead);
308 StkSendPacketFooter();
309 return (StkRcvPacket(pMem->
D_PTR_I));
312 static uint8_t _CMD_PROGRAM_MEM_ISP(
ioMem_t *pMem)
319 Len.word = LenLo + 10;
324 StkSendPacketHeader();
325 StkSendByte(Len.bytes[1]);
326 StkSendByte(Len.bytes[0]);
343 StkSendPacketFooter();
344 return StkRcvPacket((
void *)StkInBuf);
350 StkSendPacketHeader();
354 StkSendByte(CMD_SIGN_ON);
355 StkSendPacketFooter();
356 return (StkRcvPacket((
void *) StkInBuf));
362 if (_CMD_SPI_MULTI_EX(&pDeviceInfo->bytes[1], signature_r,0,1)) {
363 if (_CMD_SPI_MULTI_EX(&pDeviceInfo->bytes[0], signature_r,0,2)) {
373 StkCmd = CMD_CHIP_ERASE_ISP;
374 StkSendPacketHeader();
378 StkSendByte(CMD_CHIP_ERASE_ISP);
385 StkSendPacketFooter();
386 return (StkRcvPacket(StkInBuf));
391 if (_CMD_LOAD_ADDRESS(pMem)) {
392 StkCmd = CMD_READ_FLASH_ISP;
393 return (_CMD_READ_MEM_ISP(pMem));
401 if (_CMD_LOAD_ADDRESS(pMem)) {
402 StkCmd = CMD_READ_EEPROM_ISP;
403 return (_CMD_READ_MEM_ISP(pMem));
410 if (_CMD_LOAD_ADDRESS(pMem)) {
411 StkCmd = CMD_PROGRAM_FLASH_ISP;
412 return (_CMD_PROGRAM_MEM_ISP(pMem));
419 if (_CMD_LOAD_ADDRESS(pMem)) {
420 StkCmd = CMD_PROGRAM_EEPROM_ISP;
421 return (_CMD_PROGRAM_MEM_ISP(pMem));
uint8_t Stk_WriteEEprom(ioMem_t *pMem)
uint8_t Stk_WriteFlash(ioMem_t *pMem)
uint8_t Stk_ConnectEx(uint8_32_u *pDeviceInfo)
uint8_t Stk_Chip_Erase(void)
uint8_t Stk_ReadFlash(ioMem_t *pMem)
uint8_t Stk_ReadEEprom(ioMem_t *pMem)