ESP32-S2: fractional SPI byte in master mode: input not captured

hpeteranvin
Posts: 29
Joined: Tue Feb 28, 2017 3:44 am

ESP32-S2: fractional SPI byte in master mode: input not captured

Postby hpeteranvin » Wed Mar 30, 2022 7:59 pm

Hi,

I'm trying to use SPI in full duplex mode on ESP32-S2 to transmit a number of bits into a shift register chain which needs to be shifted by a number of bits that is not a multiple of 8. I am using CPU-controlled master mode on SPI3.

It seems to work great on the output side, but I find is that the final fractional input byte is never written to the SPI data buffers; that byte simply retains the value previously in that byte.

How can one flush out these additional bits? Transmitting additional clock pulses seen by peripherals is not acceptable, and the data appears to be lost if one starts a second (dummy) transaction.

Is there a workaround, or am I setting it up wrong? Here is a register dump of the registers set up for a 31-bit transaction, and the resulting register values:

SPI: *** Before
SPI: reg 0x000 = 0x00000000 0
SPI: reg 0x004 = 0x00000000 0
SPI: reg 0x008 = 0x06000000 100663296
SPI: reg 0x00c = 0x00000010 16
SPI: reg 0x010 = 0x00000000 0
SPI: reg 0x014 = 0x063c1001 104599553
SPI: reg 0x018 = 0x18000001 402653185
SPI: reg 0x01c = 0x00000000 0
SPI: reg 0x020 = 0x70000000 1879048192
SPI: reg 0x024 = 0x0000001e 30
SPI: reg 0x028 = 0x0000001e 30
SPI: reg 0x02c = 0x00000000 0
SPI: reg 0x030 = 0x06800200 109052416
SPI: reg 0x034 = 0x00000000 0
SPI: reg 0x038 = 0xd8000000 3623878656
SPI: reg 0x03c = 0x00000000 0
SPI: reg 0x040 = 0x0a000000 167772160
SPI: reg 0x044 = 0x00000000 0
SPI: reg 0x048 = 0x00000000 0
SPI: reg 0x04c = 0x00000200 512
SPI: reg 0x050 = 0x00000000 0
SPI: reg 0x054 = 0x00100000 1048576
SPI: reg 0x058 = 0x00000000 0
SPI: reg 0x05c = 0x00000000 0
SPI: reg 0x060 = 0x00000000 0
SPI: reg 0x064 = 0x00000000 0
SPI: reg 0x068 = 0x00000000 0
SPI: reg 0x06c = 0x00000000 0
SPI: reg 0x070 = 0x00000000 0
SPI: reg 0x074 = 0x00000000 0
SPI: reg 0x078 = 0x00000000 0
SPI: reg 0x07c = 0x00000000 0
SPI: reg 0x080 = 0x00000000 0
SPI: reg 0x084 = 0x00000000 0
SPI: reg 0x088 = 0x00000000 0
SPI: reg 0x08c = 0x00000000 0
SPI: reg 0x090 = 0x80000000 2147483648
SPI: reg 0x094 = 0xc0000000 3221225472
SPI: reg 0x098 = 0x6c80ffff 1820393471
SPI: reg 0x09c = 0x02020202 33686018
SPI: reg 0x0a0 = 0x03030303 50529027
SPI: reg 0x0a4 = 0x04040404 67372036
SPI: reg 0x0a8 = 0x05050505 84215045
SPI: reg 0x0ac = 0x06060606 101058054
SPI: reg 0x0b0 = 0x07070707 117901063
SPI: reg 0x0b4 = 0x08080808 134744072
SPI: reg 0x0b8 = 0x09090909 151587081
SPI: reg 0x0bc = 0x0a0a0a0a 168430090
SPI: reg 0x0c0 = 0x0b0b0b0b 185273099
SPI: reg 0x0c4 = 0x0c0c0c0c 202116108
SPI: reg 0x0c8 = 0x0d0d0d0d 218959117
SPI: reg 0x0cc = 0x0e0e0e0e 235802126
SPI: reg 0x0d0 = 0x0f0f0f0f 252645135
SPI: reg 0x0d4 = 0x10101010 269488144
SPI: reg 0x0d8 = 0x11111111 286331153
SPI: reg 0x0dc = 0x12121212 303174162
SPI: reg 0x0e0 = 0x00000000 0
SPI: reg 0x0e4 = 0x00000000 0
SPI: reg 0x0e8 = 0x00000000 0
SPI: reg 0x0ec = 0x00000000 0
SPI: reg 0x0f0 = 0x00000000 0
SPI: reg 0x0f4 = 0x00000000 0
SPI: reg 0x0f8 = 0x00000000 0
SPI: reg 0x0fc = 0x00000000 0
SPI: reg 0x100 = 0x00000000 0
SPI: *** After
SPI: reg 0x000 = 0x00000000 0
SPI: reg 0x004 = 0x00000000 0
SPI: reg 0x008 = 0x06000000 100663296
SPI: reg 0x00c = 0x00000010 16
SPI: reg 0x010 = 0x00000000 0
SPI: reg 0x014 = 0x063c1001 104599553
SPI: reg 0x018 = 0x18000001 402653185
SPI: reg 0x01c = 0x00000000 0
SPI: reg 0x020 = 0x70000000 1879048192
SPI: reg 0x024 = 0x0000001e 30
SPI: reg 0x028 = 0x0000001e 30
SPI: reg 0x02c = 0x00000000 0
SPI: reg 0x030 = 0x07000200 117441024
SPI: reg 0x034 = 0x00000000 0
SPI: reg 0x038 = 0xd8000000 3623878656
SPI: reg 0x03c = 0x00000000 0
SPI: reg 0x040 = 0x0a000000 167772160
SPI: reg 0x044 = 0x00000000 0
SPI: reg 0x048 = 0x00000000 0
SPI: reg 0x04c = 0x00000200 512
SPI: reg 0x050 = 0x00000000 0
SPI: reg 0x054 = 0x00100000 1048576
SPI: reg 0x058 = 0x00000000 0
SPI: reg 0x05c = 0x00000000 0
SPI: reg 0x060 = 0x00000000 0
SPI: reg 0x064 = 0x00000000 0
SPI: reg 0x068 = 0x00000000 0
SPI: reg 0x06c = 0x00000000 0
SPI: reg 0x070 = 0x00000000 0
SPI: reg 0x074 = 0x00000000 0
SPI: reg 0x078 = 0x00000000 0
SPI: reg 0x07c = 0x00000000 0
SPI: reg 0x080 = 0x00000000 0
SPI: reg 0x084 = 0x00000000 0
SPI: reg 0x088 = 0x00000000 0
SPI: reg 0x08c = 0x00000000 0
SPI: reg 0x090 = 0x80000000 2147483648
SPI: reg 0x094 = 0xc0000000 3221225472
SPI: reg 0x098 = 0x6c0f20dd 1812930781
SPI: reg 0x09c = 0x02020202 33686018
SPI: reg 0x0a0 = 0x03030303 50529027
SPI: reg 0x0a4 = 0x04040404 67372036
SPI: reg 0x0a8 = 0x05050505 84215045
SPI: reg 0x0ac = 0x06060606 101058054
SPI: reg 0x0b0 = 0x07070707 117901063
SPI: reg 0x0b4 = 0x08080808 134744072
SPI: reg 0x0b8 = 0x09090909 151587081
SPI: reg 0x0bc = 0x0a0a0a0a 168430090
SPI: reg 0x0c0 = 0x0b0b0b0b 185273099
SPI: reg 0x0c4 = 0x0c0c0c0c 202116108
SPI: reg 0x0c8 = 0x0d0d0d0d 218959117
SPI: reg 0x0cc = 0x0e0e0e0e 235802126
SPI: reg 0x0d0 = 0x0f0f0f0f 252645135
SPI: reg 0x0d4 = 0x10101010 269488144
SPI: reg 0x0d8 = 0x11111111 286331153
SPI: reg 0x0dc = 0x12121212 303174162
SPI: reg 0x0e0 = 0x00000000 0
SPI: reg 0x0e4 = 0x00000000 0
SPI: reg 0x0e8 = 0x00000000 0
SPI: reg 0x0ec = 0x00000000 0
SPI: reg 0x0f0 = 0x00000000 0
SPI: reg 0x0f4 = 0x00000000 0
SPI: reg 0x0f8 = 0x00000000 0
SPI: reg 0x0fc = 0x00000000 0
SPI: reg 0x100 = 0x00000000 0

Note that the top byte of SPI_W0 (0x098) is 0x6c both before and after the transaction. The actual data transmitted (using littleendian bit order) is 0100000 and so one would expect this byte to contain 0x02, 0x04, 0x05, or 0x82 (with 0x02 being the preferred result, of course.)
Last edited by hpeteranvin on Mon Apr 18, 2022 4:24 pm, edited 1 time in total.

ESP_Sprite
Posts: 9757
Joined: Thu Nov 26, 2015 4:08 am

Re: ESP32-S2: fractional SPI bits in master mode: input not captured

Postby ESP_Sprite » Thu Mar 31, 2022 1:32 am

I'll ask the digital team for this... but please do note that the team that was responsible for this peripheral is located in Shanghai, so I can't tell you when they'll respond as the city is under lockdown now.

ESP_Sprite
Posts: 9757
Joined: Thu Nov 26, 2015 4:08 am

Re: ESP32-S2: fractional SPI bits in master mode: input not captured

Postby ESP_Sprite » Fri Apr 01, 2022 1:03 am

By the way, we would appreciate it if you could share a project with the minimum code to reproduce this issue, that way we know for sure we can reproduce this. If you can't do that, that's okay too, though, it doesn't look like this should be too hard to reproduce.

hpeteranvin
Posts: 29
Joined: Tue Feb 28, 2017 3:44 am

Re: ESP32-S2: fractional SPI bits in master mode: input not captured

Postby hpeteranvin » Tue Apr 05, 2022 11:55 pm

I would if I could, but the problem is that it is a custom board. The register set dump should be all you need, though.

ESP_Sprite
Posts: 9757
Joined: Thu Nov 26, 2015 4:08 am

Re: ESP32-S2: fractional SPI bits in master mode: input not captured

Postby ESP_Sprite » Tue Apr 05, 2022 11:58 pm

Okay, no worries, after the lockdown is over we'll take care of this.

hpeteranvin
Posts: 29
Joined: Tue Feb 28, 2017 3:44 am

Re: ESP32-S2: fractional SPI byte in master mode: input not captured

Postby hpeteranvin » Sat May 14, 2022 1:33 am

So if I'm reading it right, this is actually a documented erratum. Fractional bytes are lost on read; there doesn't seem to be anything anyone can do about it on existing hardware. I have worked around it by bitbanging any fractional byte at the end in read mode; it is slow but it works well enough for my needs. It would probably be nicer if one could do it without switching the GPIO matrix every time (hence question 9 in my post "SPI documentation ambiguities" in the documentation forum.)

Who is online

Users browsing this forum: No registered users and 107 guests