Skip to content

Commit f9db957

Browse files
committed
fix(dap): Fix timing problems in the SPI
1 parent 1f30a57 commit f9db957

File tree

4 files changed

+45
-11
lines changed

4 files changed

+45
-11
lines changed

README.md

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -180,6 +180,24 @@ When you select max clock, we will take the following actions:
180180

181181
> Note that the most significant speed constraint of this project is still the TCP connection speed.
182182
183+
184+
## For OpenOCD user
185+
186+
This project was originally designed to run on Keil, but now you can also perform firmware flash on OpenOCD.
187+
188+
Note that if you want to use a 40MHz SPI acceleration, you need to specify the speed after the target device is connected, otherwise it will fail with the beginning.
189+
190+
```bash
191+
# Run before approaching the flash command
192+
> adapter speed 10000
193+
194+
# > halt
195+
# > flash write_image [erase] [unlock] filename [offset] [type]
196+
```
197+
198+
> Keil's timing handling is somewhat different from OpenOCD's. For example, OpenOCD lacks the SWD line reset sequence before reading the `IDCODE` registers.
199+
200+
183201
## Develop
184202

185203
0. Check other branches to know the latest development progress.

components/DAP/config/DAP_config.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -329,10 +329,11 @@ __STATIC_INLINE void PORT_JTAG_SETUP(void)
329329
*/
330330
__STATIC_INLINE void PORT_SWD_SETUP(void)
331331
{
332-
// At this stage we do not consider whether to use SPI or GPIO.
333332
// We will switch to the specific mode when setting the transfer rate.
334-
DAP_SPI_Init();
335-
DAP_SPI_Disable();
333+
334+
// Now we need to set it to ordinary GPIO mode. In most implementations,
335+
// the DAP will then read the status of the PIN via the `SWJ_PIN` command.
336+
DAP_SPI_Deinit();
336337
}
337338

338339
/**

components/DAP/source/DAP.c

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -264,6 +264,9 @@ static uint32_t DAP_ResetTarget(uint8_t *response) {
264264
// number of bytes in request (upper 16 bits)
265265
static uint32_t DAP_SWJ_Pins(const uint8_t *request, uint8_t *response) {
266266
#if ((DAP_SWD != 0) || (DAP_JTAG != 0))
267+
if (SWD_TransferSpeed == kTransfer_SPI)
268+
DAP_SPI_Deinit();
269+
267270
uint32_t value;
268271
uint32_t select;
269272
uint32_t wait;
@@ -356,6 +359,9 @@ static uint32_t DAP_SWJ_Pins(const uint8_t *request, uint8_t *response) {
356359
*response = 0U;
357360
#endif
358361

362+
if (SWD_TransferSpeed == kTransfer_SPI) // restore
363+
DAP_SPI_Init();
364+
359365
return ((6U << 16) | 1U);
360366
}
361367

@@ -505,15 +511,16 @@ static uint32_t DAP_SWD_Sequence(const uint8_t *request, uint8_t *response) {
505511
}
506512
count = (count + 7U) / 8U;
507513
#if (DAP_SWD != 0)
508-
if ((sequence_info & SWD_SEQUENCE_DIN) != 0U) {
509-
PIN_SWDIO_OUT_DISABLE();
510-
} else {
511-
PIN_SWDIO_OUT_ENABLE();
512-
}
514+
////FIXME: ?
515+
// if ((sequence_info & SWD_SEQUENCE_DIN) != 0U) {
516+
// PIN_SWDIO_OUT_DISABLE();
517+
// } else {
518+
// PIN_SWDIO_OUT_ENABLE();
519+
// }
513520
SWD_Sequence(sequence_info, request, response);
514-
if (sequence_count == 0U) {
515-
PIN_SWDIO_OUT_ENABLE();
516-
}
521+
// if (sequence_count == 0U) {
522+
// PIN_SWDIO_OUT_ENABLE();
523+
// }
517524
#endif
518525
if ((sequence_info & SWD_SEQUENCE_DIN) != 0U) {
519526
request_count++;

components/DAP/source/spi_switch.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,11 @@ typedef enum {
3737
*/
3838
void DAP_SPI_Init()
3939
{
40+
// The driving of GPIO should be stopped,
41+
// otherwise SPI has potential timing issues (This issue has been identified in OpenOCD)
42+
GPIO.out_w1tc = (0x1 << 13);
43+
GPIO.out_w1tc = (0x1 << 14);
44+
4045
// Disable flash operation mode
4146
DAP_SPI.user.flash_mode = false;
4247

@@ -145,6 +150,9 @@ __FORCEINLINE void DAP_SPI_Deinit()
145150
GPIO.enable_w1tc |= (0x1 << 12);
146151
#endif // (USE_SPI_SIO != 1)
147152

153+
// enable SWCLK output
154+
GPIO.enable_w1ts |= (0x01 << 14);
155+
148156
gpio_pin_reg_t pin_reg;
149157
GPIO.enable_w1ts |= (0x1 << 13);
150158
GPIO.pin[13].driver = 1; // OD output

0 commit comments

Comments
 (0)