Re: [RFC] Switching 8250_omap to use 8250_dma RX and TX flow

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 09/20/16 20:25, Sebastian Andrzej Siewior wrote:
> On 2016-09-20 12:57:54 [+0300], Peter Ujfalusi wrote:
>> I did not really checked the OMAP UART DMA support patches from the IP point
>> of view, but now that it is back again - for some reason it caused all sort of
>> issues so far in many levels - I have taken a peek into the driver and the
>> datasheets.
>>
>> The question it brought up for me is:
>> - Why the RX FIFO threshold set to 48? 42 would be better?
> 
> The FIFO depth is 64. So I went for a transfer after 3/4 of the FIFO is
> full.

Reasonable.

> I don't know how 42 is computed.

It is _the_
"Answer to the Ultimate Question of Life, the Universe, and Everything"

>> - Why TX FIFO threshold is set to 1? Why not 48 (or 42)?
> 
> So you can DMA an arbitrarily number of bytes. Otherwise you would be
> forced to program a multiple of 48 (or 42) and push the remaining bytes
> manually.

You could calculate the best TX_THRESHOLD runtime based on the transfer you
are just starting if you want place to optimize.

>> - according to the documentation, the UART_IER register's bits are different
>> in different modes, in DMA mode the UART_IER_MSI, UART_IER_RLSI, UART_IER_RDI,
>> etc are not applicable when the FIFO is enabled. If I read it right.
> 
> I would have to look those up.

Nevermind, I misinterpreted the TRM.

>> I got the impression from the documentation that it is best to use RX FIFO
>> threshold 1 so we receive all bytes into the memory one-by-one.
>> Or I think we could use higher threshold and we need to respond to drain the
>> FIFO with CPU by responding to EOF interrupt (enabled by bit 7 in IER register
>> when the FIFO is enabled)
> 
> How is threshold 1 applicable? Wouldn't you get an interrupt after each
> byte?

No, with threshold 1 you will have DMA request after each byte and you will
have one interrupt after the transfer is done. But I see that it is a bit more
complicated than this.


>>>> if that is what it has been configured. But AFAIK we use bursts from
>>>> UART, so we configure that the FIFO should have 40(?) bytes and only then the
>>>> DMA request should be asserted. DMA will read the 40(?) bytes out, so again it
>>>> does not matter if we had 1 byte in the FIFO when the DMA started.
>>>
>>> In general: burst size 48, program transfer with 16 bytes in the FIFO. The
>>> transfer should start (DMA asserted by the UART) once the remaining 32
>>> bytes have arrived.
>>
>> I have hard time to follow this...
>> The IP's threshold and the DMA burst size must be configured in sync. If you
>> say in the IP to generate the DMA request when the FIFO have 48 bytes, then
>> you need to program the DMA to read 48 bytes.
> correct.
> 
>> If you set the UART FIFO
>> threshold to 16 bytes, then you need to configure the DMA burst size to 16
>> bytes as well:
>> "This request (RX DMA request) is deasserted when the number of bytes defined
>> by the threshold level is read by the device DMA controllers."
> 
> I intended to follow this :)
> 
>>> Before having the 48 bytes as burst I had 1 byte. At this point the DMA
>>> engine transferred one byte at a time but something else was not perfect
>>> so I went for 48.
>>
>> Hrm, my bet would be that Enabled FIFO + 1 byte threshold should be the safest
>> and working mode for UART.
>>
>>> Nobody at TI could answer my question why the RX-DMA is not triggered by
>>> the UART if the RX transfer was not programmed prio the reception. I
>>> received even bare metal code where, according to the code, the RX
>>> transfer was programmed _after_ the first byte has been received. I
>>> tried to run this in Linux (as I was not able to run this bare metal)
>>> and I could not confirm that this works.
>>
>> I'm not sure if I get this right, but are you saying that if you program UART
>> first, enable UART RX then enable the DMA it will not work at all?
> - program the UART (baud rate, etc)
> - send from the remote side 48 bytes (just 48). The data will stay in
>   UART's FIFO
> - UART will generate RX interrupt will
> - program DMA engine to transfer 48 bytes (at this point the UART has
>   probably 4 byte in its FIFO while the remaining data is still dropping
>   in).
> - UART will continue generate RX interrupts
> - UART will generate a TIMEOUT interrupt

Looks OK as sequence. The only thing which could make this fail if the DMA
does not evaluate the already asserted DMA request line. Other then that it
should work as similar (bug - in case of TX) was working with sDMA and McBSP.

> the mode that is currently used:
> 
> - program the UART (baud rate, etc)
> - program DMA engine to transfer 48 bytes.
> - send from the remote side 48 bytes (just 48)
> - DMA engine will transfer 48 bytes once 48 bytes are UART's FIFO and
>   generate a transfer-complete interrupts
> - UART will generate an interrupt. The interrupt-status register will
>   read "nothing" because it was a RX interrupt which was cleared by the
>   DMA engine (usually you won't notice this but at 2Mbaud you will
>   likely see "nobody cared" and the core will disable the UART
>   interrupt).

you should have this interrupt disabled when using DMA. If it is possible.

>> That is really strange indeed. One thing might be that you quickly overrun in
>> UART and that causes things to fail?
> 
> no overrun. I used [0] so send stuff in simplex / duplex mode or just a
> specific amount of data.
> 
>> But as I have said: I'm not an expert on the UART side, I don't even know how
>> to properly test the UART DMA,a nd to be honest I do keep it disabled most of
>> the time as it interfere with my DMA driver work.
>> I was planning to propose to have a way to disable the UART DMA for console
>> UARTs as there is no real point of having DMA for that.
> 
> By the time I worked on it I had it enabled on my am335x and dra7. I had
> the test tool [0] the check for large transfers. For console uarts it
> makes no sense since you usually get like 2 characters a second. On RX
> side what happens here is _usually_ a timeout interrupt and the FIFO is
> drained in PIO mode. This is something you *don't* notice. On the TX
> side you get larger transfers for instance during "dmesg" output.

Yep, I agree that TX can be a good for console.

> 
> [0] https://git.breakpoint.cc/cgit/bigeasy/serialcheck.git/
> 
> Sebastian
> 


-- 
Péter
--
To unsubscribe from this list: send the line "unsubscribe linux-serial" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Index of Archives]     [Kernel Newbies]     [Security]     [Netfilter]     [Bugtraq]     [Linux PPP]     [Linux FS]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Samba]     [Video 4 Linux]     [Linmodem]     [Device Mapper]     [Linux Kernel for ARM]

  Powered by Linux