This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Linux/AM3352: Simultaneous RS-485 and RS-422 communication

Part Number: AM3352

Tool/software: Linux

Hello,

I want to get following configuration:

UART0: disabled
UART1: disabled
UART2: RS422
UART3: RS485
UART4: debug
UART5: RS422

My problem is that while using SERIAL_8250 driver RS422 works fine, but RS485 is only receiving, not transmiting.
On the other hand, when I use SERIAL_OMAP driver RS485 works like a charm, but I can't establish connection on RS422 (I have pppd TCP/IP over RS422).
Debug works always.

Whichever driver I use, I'm not changing device tree (maybe that's a mistake?). Device tree looks as follows:

uart2: serial@48024000 {                // RS422 ppp 
      pinctrl-names = "default";
      pinctrl-0 = <&uart2_pins>;
      status = "okay";
};

uart3: serial@481a6000 {                // RS485
      pinctrl-names = "default";
      pinctrl-0 = <&uart3_pins>;
      status = "okay";
      rs485-rts-delay = <0 0>;
      linux,rs485-enabled-at-boot-time;
      rts-gpio = <&gpio2 17 0>;
      rs485-rts-active-high;
};

uart4: serial@481a8000 {                // debug
      pinctrl-names = "default";
      pinctrl-0 = <&uart4_pins>;
      status = "okay";
};

uart5: serial@481aa000 {                // RS422 ppp
      pinctrl-names = "default";
      pinctrl-0 = <&uart5_pins>;
      status = "okay";
};
uart2_pins: pinmux_uart2_pins {
        pinctrl-single,pins = <
                0x150 ( PIN_INPUT_PULLUP | MUX_MODE1 )          /* (A17) spi0_sclk.uart2_rxd */
                0x154 ( PIN_OUTPUT_PULLDOWN | MUX_MODE1 )       /* (B17) spi0_d0.uart2_txd */
        >;
};

uart3_pins: pinmux_uart3_pins {
        pinctrl-single,pins = <
                0x160 (PIN_INPUT_PULLUP | MUX_MODE1)            /* (C15) spi0_cs1.uart3_rxd */
                0x164 (PIN_OUTPUT_PULLDOWN | MUX_MODE1)         /* (C18) ecap0_in_pwm0_out.uart3_txd */
                0xcc ( PIN_OUTPUT_PULLDOWN | MUX_MODE7 )        /* (U4)  lcd_data11.uart3_rtsn */
        >;
};

uart4_pins: pinmux_uart4_pins {
        pinctrl-single,pins = <
                0x70 (PIN_INPUT_PULLUP | MUX_MODE6)             /* (T17) gpmc_wait0.uart4_rxd */
                0x74 (PIN_OUTPUT_PULLDOWN | MUX_MODE6)          /* (U17) gpmc_wpn.uart4_txd */
        >;
};

uart5_pins: pinmux_uart5_pins {
        pinctrl-single,pins = <
                0x108 ( PIN_INPUT_PULLUP | MUX_MODE3 )          /* (H16) gmii1_col.uart5_rxd */
                0x144 ( PIN_OUTPUT_PULLDOWN | MUX_MODE3 )       /* (H18) rmii1_refclk.uart5_txd */
        >;
};

Kernel configuration fragment for SERIAL_8250 with working RS422:

CONFIG_SERIAL_EARLYCON=y
CONFIG_SERIAL_8250=y
CONFIG_SERIAL_8250_CONSOLE=y
CONFIG_SERIAL_8250_NR_UARTS=10
CONFIG_SERIAL_8250_RUNTIME_UARTS=10
CONFIG_SERIAL_8250_EXTENDED=y
CONFIG_SERIAL_8250_MANY_PORTS=y
CONFIG_SERIAL_8250_SHARE_IRQ=y
CONFIG_SERIAL_8250_FSL=y
CONFIG_SERIAL_8250_OMAP=y
CONFIG_SERIAL_8250_OMAP_TTYO_FIXUP=y
CONFIG_SERIAL_OF_PLATFORM=y

CONFIG_SERIAL_CORE=y
CONFIG_SERIAL_CORE_CONSOLE=y
CONFIG_HW_RANDOM=m
CONFIG_HW_RANDOM_OMAP=m
CONFIG_DEVPORT=y

And for the second case (SERIAL_OMAP with working RS485):

CONFIG_SERIAL_CORE=y
CONFIG_SERIAL_CORE_CONSOLE=y
CONFIG_SERIAL_OMAP=y
CONFIG_SERIAL_OMAP_CONSOLE=y
CONFIG_HW_RANDOM=m
CONFIG_HW_RANDOM_OMAP=m
CONFIG_DEVPORT=y

configs not listed are not set.

Please help me figure it out. As everything is working (unfortunately not in same time...) I think HW is fine so I don't think posting schematics will be necessary.

Kind regars,

Marek Słomiany

  • What Linux version is this?
  • ti-rt-linux-4.9.y
    commit: 4ad5dcaca7428dd2bc1a6a40c948e3799c1e27ae
    from: git://git.ti.com/ti-linux-kernel/ti-linux-kernel.git
  • Hi,

    In the original or default driver setup. So to understand are you seeing the tx enable being set when trying to transmit?

    Is this a custom board that you are working with?

    The question you are asking about changing the device tree maybe a clue. The tx enable on your board is it same pin for both drivers?

    Did you check out a release tag with the TI tree when building the kernel?

    Best Regards,
    Schuyler
  • Yes, it's a custom board.
    If you mean rtsn pin, it's wired to CPU only in UART3, I am not sure if it's pulled up/down in other UARTs (I am not designer of this board) but it's uncontrollable from cpu - that's for sure.
    About release tag, I'm not sure which tag you have in mind? (sorry if it's obvious - I'm not a pro, just self-learner)
    Maybe it's possible to use both drivers, but to distinguish them somehow between those devices?

  • Hi,
    Yes the RTS pin is what I am meaning. After looking at the DTS pin mux definitions, as a quick check of the mux modes for the RTS signal on UART3, the mux mode is 7 for the RTS signal which is gpio mode. Have you tried mux mode 6 for this pin?

    You also will want to use the 8250 omap serial driver, the other is now considered legacy code.

    Best Regards,
    Schuyler
  • >> Yes the RTS pin is what I am meaning. After looking at the DTS pin mux definitions, as a quick check of the mux modes for the RTS signal on UART3, the mux mode is 7 for the RTS signal which is gpio mode. Have you tried mux mode 6 for this pin? 

    I have just checked it on both muxmodes (6 and 7) and it doesn't change anything. UART3 is set in device tree with "rts-gpio = <&gpio2 17 0>;" so I think it should be in gpio mode (muxmode 7)

    >> You also will want to use the 8250 omap serial driver, the other is now considered legacy code.

    Ok, so I'm using the first configuration with 8250.

    I have tried to probe with external device if there is any 3.3V signal on RTS pin and there is nothing. For comparison I have once more used the legacy driver and there is 3.3V (blinking diode on my tool) when transferring data (either direction).

    I am wondering if in device tree node property compatible = "ti,am3352-uart", "ti,omap3-uart"; is set correctly... in Documentation/devicetree/bindings/serial/rs485.txt there is example for atmel at91. Loooks similar but there is no list of compatible values.

  • Hi,
    Looking in driver code for each driver the rts-gpio is only used in omap serial driver, you could probably remove this property from the node.

    The serial core driver is going to use the UART IP RTS signal so I think we need to debug this with mux mode set to 6. For this field why is it set to 0 rs485-rts-delay = <0 0>; Can you try changing the value to something greater than 0? Perhaps try 200 or greater, if I am understanding the driver correctly the value looks to be clamped at 100mS.

    Both of those compatible definitions are defined in the 8250 omap driver, are you asking if you need both?

    Best Regards,
    Schuyler
  • Sorry for such long delay in checking this, but I finally had possibility to check this out.

    Now my device tree for this node looks like this:

    uart3_pins: pinmux_uart3_pins {
        pinctrl-single,pins = <
        0x160 (PIN_INPUT_PULLUP | MUX_MODE1)            /* (C15) spi0_cs1.uart3_rxd */
        0x164 (PIN_OUTPUT_PULLDOWN | MUX_MODE1)         /* (C18) ecap0_in_pwm0_out.uart3_txd */
        0xcc ( PIN_OUTPUT_PULLDOWN | MUX_MODE6 )        /* (U4)  lcd_data11.uart3_rtsn */
    
    
    uart3: serial@481a6000 {                // RS485
        pinctrl-names = "default";
        pinctrl-0 = <&uart3_pins>;
        status = "okay";
        rs485-rts-delay = <200 200>;
        linux,rs485-enabled-at-boot-time;
        /* rts-gpio = <&gpio2 17 0>; */
        rs485-rts-active-high;
    };

    But it behaves exactly the same as earlier.

    here is decompiled device tree fragment (to include things that came from am33xx.dtsi)

    serial@481a6000 {
        compatible = "ti,am3352-uart", "ti,omap3-uart";
        ti,hwmods = "uart4";
        clock-frequency = <0x2dc6c00>;
        reg = <0x481a6000 0x2000>;
        interrupts = <0x2c>;
        status = "okay";
        pinctrl-names = "default";
        pinctrl-0 = <0x2d>;
        rs485-rts-delay = <0xc8 0xc8>;
        linux,rs485-enabled-at-boot-time;
        rs485-rts-active-high;
    };

    Everything seems to be fine, but still rts is not working.

  • Hi,
    I know the CTS signal is not used in RS-485 but I would like to see it, can you provide a schematic snippet of how the RS-485 is setup on your board?

    Also is the tx line sending out any data? I would to see like if the tx is sending the data even the RTS is not enabling the transceiver.

    Best Regards,
    Schuyler
  • here is the schematic:

    I have connected Logic analyzer to pins Tx, Rx, rts and cts.

    only result I got is here:

    CTS and RTS didn't move even a bit. For comparison (and testing if i connected it properly) I have recompiled kernel with legacy driver (SERIAL_OMAP), I have high signal on RTS during send but still nothing on CTS.

    Here is my device tree for this node with CTS pin:

    uart3: serial@481a6000 {                //user RS485
                   pinctrl-names = "default";
                   pinctrl-0 = <&uart3_pins>;
                   status = "okay";
                   rs485-rts-delay = <200 200>;
                   /* linux,rs485-enabled-at-boot-time; */
                   rts-gpio = <&gpio2 17 0>;
                   rs485-rts-active-high;
           };
    
    uart3_pins: pinmux_uart3_pins {
                        pinctrl-single,pins = <
                                0x160 (PIN_INPUT_PULLUP | MUX_MODE1)            /* (C15) spi0_cs1.uart3_rxd */
                                0x164 (PIN_OUTPUT_PULLDOWN | MUX_MODE1)         /* (C18) ecap0_in_pwm0_out.uart3_txd */
                                0xcc ( PIN_OUTPUT_PULLDOWN | MUX_MODE6 )        /* (U4)  lcd_data11.uart3_rtsn */
                                0xc8 ( PIN_OUTPUT_PULLDOWN | MUX_MODE6 )        /* (U3)  lcd_data10.uart3_ctsn */
                                >;
                };
    

  • Just to refresh topic... Does anyone have a clue what can I be doing wrong?
  • Hi,
    We are trying an experiment here to see if we can replicate the issue.
    Best Regards,
    Schuyler
  • Marek,

    I helped Schuyler recreate this using a BBB. I used UART1 as the pins are available on the P9 header (P9-19 and P9-24 to be exact). 

    Here are the DTS changes I made:

    diff --git a/arch/arm/boot/dts/am335x-boneblack.dts b/arch/arm/boot/dts/am335x-boneblack.dts
    index 1230fd0..27df4e7 100644
    --- a/arch/arm/boot/dts/am335x-boneblack.dts
    +++ b/arch/arm/boot/dts/am335x-boneblack.dts
    @@ -86,6 +86,24 @@
     			AM33XX_IOPAD(0x86c, PIN_OUTPUT_PULLDOWN | MUX_MODE7) /* gpmc_a11.GPIO1_27 */
     		>;
     	};
    +
    +	uart1_pins_default: uart1_pins_default {
    +		pinctrl-single,pins = <
    +			0x180 ( PIN_INPUT | MUX_MODE0 ) /* (D16) uart1_rxd.uart1_rxd */
    +			0x184 ( PIN_OUTPUT | MUX_MODE0 ) /* (D15) uart1_txd.uart1_txd */
    +			0x178 ( PIN_INPUT | MUX_MODE0 ) /* (D18) uart1_ctsn.uart1_ctsn */
    +			0x17c ( PIN_OUTPUT | MUX_MODE0 ) /* (D17) uart1_rtsn.uart1_rtsn */
    +		>;
    +	};
    +};
    +
    +&uart1 {                // RS485
    +    pinctrl-names = "default";
    +    pinctrl-0 = <&uart1_pins_default>;
    +    status = "okay";
    +    rs485-rts-delay = <200 200>;
    +    linux,rs485-enabled-at-boot-time;
    +    rs485-rts-active-high;
     };
     
     &lcdc {

    Here's what we captured:

    As you can see, we see RTS strobing as we would expect.

    It seems that something must be different in your set up. If you have a Beaglebone Black, you should be able to recreate the test above easily enough.

    We hope this is helpful.

  • I have checked your configuration on my BBB and it seems to be working fine on logic analyser. But...
    Lately, for most of time, to observe pins I was sending some strings to appropriate ttySx using echo - I used two grouped terminals, to send in both directions in about 100ms interval (first Tx than Rx).
    When it seemed (by the logic analyser plot) to be working fine, I have moved to connecting to terminal myself using screen. This worked perfectly on old SERIAL_OMAP module, but now when I start screen, I noticed, the RTS pin is pulled down permanently. RTS will be back in high state only after reboot. Earlier (when I posted this topic) I was mainly using screen for this, but the RTS must have been reverted - that was why I was able to read but I was unable to send anything, now after some changes it's oposite - after I launch screen, RTS will be permanently down so only sending will be possible. 

    I think my main question of this topic will now change a bit: Is this normal what happens? is it screen's fault? Is there a way to 'unlock' RTS without reboot?

    I really appreciate your help,
    Kind regards,
    Marek

    PS: We have made some minor changes in HW, but as it's working when echoing to each other I won't get into details of changes.

  • Hi,

    Are you still seeing this as an issue?

    Best Regards,
    Schuyler
  • Yes, it's still working as I described it first... But currently I am using the legacy driver for this one RS485 serial and the 8250 for all others. 
    I don't want to waste any more of your time as it could be something on my side (considering it's working fine on your end).

    Only one last question: If you take two BBBs, connect them with RS and open tty using screen: is the RTSn pin behaving properly?

  • Hi,

    The screen capture provided earlier in the thread is how we expect the interface to work. The RTS signal is attached to the transmit enable on the transceiver, not to another BBB. In the screen capture above is the correct behaviour which is the RTS going low on the start bit of the byte being transmitted and going high after the transmission completes.

    Best Regards,
    Schuyler