Hello,
I know there are already other discussion out there about this topic.
Anyway, there are a couple of question I can't get straight right now, so I would like some kind of feedback from the community.
According to the the very helpful post by Adrian Sanchez Cano (Using DMA and SPI.pdf) he asserts that "To ensure the synchrony between the dSPI with the DMA the transfers to the PUSHR must be of 4 bytes, this includes 2 bytes command and 2 bytes data".
Furthermore, looking at the examples provided (ok, I saw the K20 one, but I think that k80 and k20 are identical for SPI and DMA) we have to prepare the buffer (MasterDataSend() function) and then send the prepared buffer.
In my opinion this inserts an heavy overhead on the overall budget of the CPU time. My question is: Can we do better, using eDMA without having to prepare that buffer for every byte we have to send?
Looking at the SPI module,
"The SPI supports 8-bit or 16-bit writes to the PUSH TX FIFO, allowing a single write to the command word followed by multiple writes to the transmit word. The TX FIFO will save the last command word written, and convert a 8-bit/16-bit write to the transmit word into a 32-bit write that pushes both the command word and transmit word into the TX FIFO."
In my understanding, after I push the command word to the SPI module I can then send the data words with 8 bit writes without configuring the command word for each data word.
The eDMA allows the transfer of 8 bytes according to DMA_TCDn_ATTR[SSIZE] & DMA_TCDN_ATTR[DSIZE].
Disabling minor loop mapping I can set DMA_TCDn_NBYTES_MLNO to Nbytes, so I can configure the number of bytes to transfer per request.
So the idea is to set the command word, then using DMA send length-1 bytes and when the DMA asserts an EOQ IRQ, I can configure the SPI command word for the last byte to be transferred.
Somehow, I suppose that if this was feasible somewhere in the forum it should have been pointed out, and guess what? It is not.
SO I suppose there are many flaws in my idea. I don't want to begin to implement something that is proven will not work (wasting a lots [debug] time) , so I'm asking you:
is this feasible? Or, in your opinion, why not?
is the procedure suggested by Adrian the only way, or the best way of using SPI and DMA in kinetis microcontrollers?
Best regards,
Luca.
Messaggio modificato da luca toso
Solved! Go to Solution.
Hi, Catosh,
Regarding the following section, I think your understanding is correct, the SPIx_PUSHR register can be separated by the 16 bits COMMAMD register and 16 bits DATA register, you can write separately when the SPI is set up in master mode. You explanation is correct "after you push the command word to the SPI module I can then send the data words with 8 bit writes without configuring the command word for each data word.". The DMA can only write the data register part of SPIx_PUSHR, the condition is that you have written the command register of SPIx_PUSHR before.
BR
XiangJun Rong
3.9.2.11 Writing SPI Transmit FIFO
The SPI supports 8-bit or 16-bit writes to the PUSH TX FIFO, allowing a single write to
the command word followed by multiple writes to the transmit word. The TX FIFO will
save the last command word written, and convert a 8-bit/16-bit write to the transmit word
into a 32-bit write that pushes both the command word and transmit word into the TX
FIFO (PUSH TX FIFO Register In Master Mode)
A 32-bit write to the SPI_PUSH register will push all 32-bits to the TX FIFO. An 8-bit or
16-bit write to the 16-bit transmit data field will push the data together with the last
written command word. An 8-bit or 16-bit write to the command word does not push data
onto the FIFO, but that command word is pushed to the TX FIFO on all subsequent 8-bit
or 16-bit writes to the transmit data field. This allows a single 16-bit write to the
command word to be used for all subsequent 8-bit or 16-bit writes to the transmit data
word. Writing a different 16-bit command word will cause all subsequent 8-bit or 16-bit
writes to the transmit data word to be pushed to the TX FIFO with the new command
word.
Hi, Catosh,
Regarding the following section, I think your understanding is correct, the SPIx_PUSHR register can be separated by the 16 bits COMMAMD register and 16 bits DATA register, you can write separately when the SPI is set up in master mode. You explanation is correct "after you push the command word to the SPI module I can then send the data words with 8 bit writes without configuring the command word for each data word.". The DMA can only write the data register part of SPIx_PUSHR, the condition is that you have written the command register of SPIx_PUSHR before.
BR
XiangJun Rong
3.9.2.11 Writing SPI Transmit FIFO
The SPI supports 8-bit or 16-bit writes to the PUSH TX FIFO, allowing a single write to
the command word followed by multiple writes to the transmit word. The TX FIFO will
save the last command word written, and convert a 8-bit/16-bit write to the transmit word
into a 32-bit write that pushes both the command word and transmit word into the TX
FIFO (PUSH TX FIFO Register In Master Mode)
A 32-bit write to the SPI_PUSH register will push all 32-bits to the TX FIFO. An 8-bit or
16-bit write to the 16-bit transmit data field will push the data together with the last
written command word. An 8-bit or 16-bit write to the command word does not push data
onto the FIFO, but that command word is pushed to the TX FIFO on all subsequent 8-bit
or 16-bit writes to the transmit data field. This allows a single 16-bit write to the
command word to be used for all subsequent 8-bit or 16-bit writes to the transmit data
word. Writing a different 16-bit command word will cause all subsequent 8-bit or 16-bit
writes to the transmit data word to be pushed to the TX FIFO with the new command
word.
The verbiage you quoted is 'new to me'! I am not aware of such 'follow-on command-code copy', although that certainly MAKES SENSE! Wonder if that is a new 'mask specific' improvement in some way....
My solution to the problem is simply to organize the usage of the 'outbound buffer' so that the 'data source' simply knows to write only the least-byte of each 4-byte allocation, leaving the rest 'as initialized' for ALL subsequent DMA block-transfers.
EARL GOODRICH ha scritto:
The verbiage you quoted is 'new to me'! I am not aware of such 'follow-on command-code copy', although that certainly MAKES SENSE!
Sorry, My fault.
I messed up different part numbers, and obviously they weren't identical.
I was reading the datasheet of the K80 mcu and watching the K20 examples.
I modified original post to reflect the correct part number.
But the question still remains: in k80 I can use the lower bits of the fifo, while on k64 the pre-buffering seems to be a little bit inefficient.