New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
STM32H7 serial TX DMA fix #11871
base: master
Are you sure you want to change the base?
STM32H7 serial TX DMA fix #11871
Conversation
How is this checking for the DMA idle? |
The semaphore is used to indicate when DMA is idle or not. The call to nxsem_trywait() in up_dma_txavailable() perform this check. Did you notice the reverts? The revert commits reintroduces the call to nxsem_trywait() - not my patch. |
yes. I am not clear on the flow, here is my concern Half done check will run the queue has data check and call |
071de55
to
48d521f
Compare
The half transfer interrupt is not enabled (for TX), only the completion interrupt is enabled. I had forgot to remove that. I have pushed version where the half transfer interrupt handling is removed (from TX). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There are 2 paths, through up_dma_txavailable
one under interrupt and one from the foreground. The issue that was solved by the critical section was
If a TX DMA completion interrups a forground write.
The TX DMA completion can start a dma_send and it will
then followed by the forground write's dma_send
stoping the,then in progress DMA.
By atomicaly marking the tx dma busy, the forground
write will not perform the dma_send, and will only
enqueue the data. At the next TX dma completion any
data pending in the tx queue will be sent
This case was a random failure and needs to be tested, It was hard to recreate.
The current software in master is not working, because the test in up_dma_txavailable() does not correctly determine whether TX DMA is active or not. This could be fixed, but isn't it better to use a semaphore than a critical section? I personally also find the code with the semaphore simpler and more intuitive: if TX DMA is running, it is always the ISR which initiates the next transfer. The if-statement in up_dma_txavailable() could be fixed like this: I have a setup, which easily and immediately detects the errors with TX DMA the driver has and have had. |
If the only change required is fixing the typo by adding the "== 0" why not do that? I think the CS is a few uS and a nit compared to the semaphore code time and complexity. |
To my surprise, nuttx implements nxsem_trywait() using a critical section... so yes, using a critical section instead of the semaphore provides better performance. I believe the call to stm32_dmaresidual() should be removed. I think is redundant and not a reliable method for testing whether DMA is running? I don't like dma_up_txcallback() calling up_dma_txavailable(). It works, but it is unnecessary. The ISR doesn't need to enter a critical section. I prefer the dma_up_txcallback() implementation in my patch - just leave out the call to nxsem_post(). What do you think? I will make another version with the above changes and push to this branch later this week when I have had time to verify it. I'm a little preoccupied by something at the moment. |
I am glad you went through the If you consider the foregrounds looping trying to transmit. I have concerns about the completion call back interrupting that looping. So the CS protects that. Now there is the case of Not accessing the |
Summary
Fixes TX DMA for STM32H7
Testing
Works for me on an STM32H723