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.

AM625: GPIO Output State In Deep Sleep

Part Number: AM625
Other Parts Discussed in Thread: SK-AM62B-P1

Hello,

we have an issue with GPIO output state not being preserved while in Deep Sleep mode.

This is related to previous questions on the topic:

 - https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1360238/am625-peripherals-goes-into-reset-state-when-processor-goes-into-deepsleep-mode/5189677#5189677

 - https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1207903/am625-sdk-08-06-00-42-kernel-5-10-gpio-state-on-deep-sleep/4571452#4571452

Our current need and expectation is that any GPIO configured as output is going to keep its state when the system goes into suspend and afterward resume without any glitches.

We are running the latest TI SDK SW 09.02.01.09 on a custom HW.

We are currently measuring GPIO GPMC0_AD2 (as an example), this pin has a 2.2kOhm pull-down on the board (-> it's a strap option).

What is happening is that the Linux software is driving this pin as high, and the pin goes to low as soon as the board gets into suspend (not sure if this is because the pin gets configured as input, because of the pull-down, of if this is actively driven as output). The expectation and the need is that the pin stays to a stable state and that this state is high in suspend.

We did check the pad configuration and everything seems as expected:

# devmem2 0xF4044 w
/dev/mem opened.
Memory mapped at address 0xffff838c2000.
Read at address 0x000F4044 (0xffff838c2044): 0x00050007

Any suggestion?

  • Hello,

    I'll try to replicate the behavior on our end.

    I will reply to this thread when I have an update within the next few days. Feel free to update this thread with any findings you have in the meantime.

    Best Regards,

    Anshu

  • Hi ,

    I did a quick test on SK-AM62B-P1 board to check the state of the GPIO in deepsleep. More details below.

    Software images:

    Latest prebuilt SDK images (https://dr-download.ti.com/software-development/software-development-kit-sdk/MD-PvdSyIiioq/09.02.01.09/tisdk-default-image-am62xx-evm.wic.xz)

    Version: 09.02.01.09, Release date: 29 Mar 2024


    Test steps:

    1. Load the above software images on SK board.

    2. Set user-led LD1 (SOC_GPIO1_49) trigger to 'default-on '

    root@am62xx-evm:/sys/class/leds/am62-sk:green:heartbeat# echo default-on > trigger

    3. Enter to suspend-to-ram (deepsleep) state.

    root@am62xx-evm:/sys/class/leds/am62-sk:green:heartbeat# rtcwake -s 10 -m mem -d rtc0

    Real observations on AM62-SK HW:

    I observed that LD1 goes off when the device is in deepsleep. In other words, GPIO1_49 is not persisting it's state across deepsleep and goes low for the time of device deeplseep. This is not expected.

    Expectations for SOC GPIOs in deepsleep:

    While device stays in the deepsleep mode, I expect that SOC GPIOs must retain it's last configured state.

    In this specific test, I expect that after executing test step#3, LD1 should be 'ON' (GPIO1_49 should be high) as it was before entering into deepsleep.

    Why AM62 GPIOs are not retaining it's state during suspend-to-ram cycle ?

    Full logs:

    root@am62xx-evm:/sys/class/leds/am62-sk:green:heartbeat# echo default-on > trigger                                                                                                                                                                                                                                                                                                     
    root@am62xx-evm:/sys/class/leds/am62-sk:green:heartbeat# rtcwake -s 10 -m mem -d rtc0
    rtcwake: wakeup from "mem" using rtc0 at Wed May 15 10:49:33 2024
    [10968.298504] PM: suspend entry (deep)
    [10968.302350] Filesystems sync: 0.000 seconds
    [10968.330896] remoteproc remoteproc0: stopped remote processor 5000000.m4fss
    [10968.338428] Freezing user space processes
    [10968.344862] Freezing user space processes completed (elapsed 0.002 seconds)
    [10968.351927] OOM killer disabled.
    [10968.355157] Freezing remaining freezable tasks
    [10968.361202] Freezing remaining freezable tasks completed (elapsed 0.001 seconds)
    [10968.368610] printk: Suspending console(s) (use no_console_suspend to debug)
    [10968.377677] wlcore: down
    [10968.421515] am65-cpsw-nuss 8000000.ethernet eth0: Link is Down
    [10968.422167] am65-cpsw-nuss 8000000.ethernet eth1: Link is Down
    [10968.433648] Disabling non-boot CPUs ...
    [10968.435927] psci: CPU1 killed (polled 0 ms)
    [10968.438599] psci: CPU2 killed (polled 4 ms)
    [10968.441260] psci: CPU3 killed (polled 0 ms)
    [10968.442907] Enabling non-boot CPUs ...
    [10968.443314] Detected VIPT I-cache on CPU1
    [10968.443406] GICv3: CPU1: found redistributor 1 region 0:0x00000000018a0000
    [10968.443474] CPU1: Booted secondary processor 0x0000000001 [0x410fd034]
    [10968.444394] CPU1 is up
    [10968.444658] Detected VIPT I-cache on CPU2
    [10968.444702] GICv3: CPU2: found redistributor 2 region 0:0x00000000018c0000
    [10968.444738] CPU2: Booted secondary processor 0x0000000002 [0x410fd034]
    [10968.445396] CPU2 is up
    [10968.445668] Detected VIPT I-cache on CPU3
    [10968.445717] GICv3: CPU3: found redistributor 3 region 0:0x00000000018e0000
    [10968.445758] CPU3: Booted secondary processor 0x0000000003 [0x410fd034]
    [10968.446451] CPU3 is up
    [10968.447088] ti-sci 44043000.system-controller: ti_sci_resume: wakeup source: 0x50
    [10968.558706] am65-cpsw-nuss 8000000.ethernet: set new flow-id-base 19
    [10968.567825] am65-cpsw-nuss 8000000.ethernet eth0: PHY [8000f00.mdio:00] driver [TI DP83867] (irq=POLL)
    [10968.567857] am65-cpsw-nuss 8000000.ethernet eth0: configuring for phy/rgmii-rxid link mode
    [10968.574643] am65-cpsw-nuss 8000000.ethernet eth1: PHY [8000f00.mdio:01] driver [TI DP83867] (irq=POLL)
    [10968.574656] am65-cpsw-nuss 8000000.ethernet eth1: configuring for phy/rgmii-rxid link mode
    [10969.220221] wlcore: PHY firmware version: Rev 8.2.0.0.245
    [10969.313032] wlcore: firmware booted (Rev 8.9.0.0.86)
    [10969.475567] OOM killer enabled.
    [10969.478715] Restarting tasks ... done.
    [10969.486914] random: crng reseeded on system resumption
    [10969.492189] remoteproc remoteproc0: powering up 5000000.m4fss
    [10969.498052] remoteproc remoteproc0: Booting fw image am62-mcu-m4f0_0-fw, size 55016
    [10969.507419] rproc-virtio rproc-virtio.0.auto: assigned reserved memory node m4f-dma-memory@9cb00000
    [10969.517669] virtio_rpmsg_bus virtio0: rpmsg host is online
    [10969.518451] virtio_rpmsg_bus virtio0: creating channel ti.ipc4.ping-pong addr 0xd
    [10969.523376] rproc-virtio rproc-virtio.0.auto: registered virtio0 (type 7)
    [10969.534095] virtio_rpmsg_bus virtio0: creating channel rpmsg_chrdev addr 0xe
    [10969.537596] remoteproc remoteproc0: remote processor 5000000.m4fss is now up
    [10969.537637] PM: suspend exit

    Thank you.

    Regards,

    Parth P

  • Hi ,

    Just realized that above test with a user LED might not be as relevant, considering the fact that LED subsystem might turn LEDs off in low-power mode. Requesting to kindly ignore my above response and consider below test and findings instead.

    I retested the SOC GPIO behavior with a EXP_GPIO0_42 present on 'User Expansion Connector (J3)' with all the latest SW images as mentioned in above response on AM62-SK board across deepsleep cycle.

    Configured EXP_GPIO0_42 as GPIO with pull-up enabled using devmem and could see GPIO toggle on oscilloscope with a simple commands below.

    root@am62xx-evm:~# gpioset gpiochip0 42=1
    root@am62xx-evm:~# gpioset gpiochip0 42=0
    root@am62xx-evm:~# gpioset gpiochip0 42=1

    For the test, I set GPIO0_42 high and try to keep device in deepsleep. I expect GPIO0_42 to remain high for a complete deepsleep cycle persisting it's last configured state throughout .

    I observe the similar behavior where GPIO0_42 goes low/down for the time of the device deeplseep and goes high again as soon as device wakes up from a deepsleep. This is not expected.

    Please see the below logs.

    root@am62xx-evm:~# devmem2 0xF40AC w
    /dev/mem opened.
    Memory mapped at address 0xffffb6241000.
    Read at address  0x000F40AC (0xffffb62410ac): 0x08214007
    
    root@am62xx-evm:~# devmem2 0xF40AC w 18234007 
    /dev/mem opened.
    Memory mapped at address 0xffffbe288000.
    Read at address  0x000F40AC (0xffffbe2880ac): 0x08234007
    Write at address 0x000F40AC (0xffffbe2880ac): 0x01163A97, readback 0x01163A97
    
    root@am62xx-evm:~# gpioset gpiochip0 42=0
    root@am62xx-evm:~# gpioset gpiochip0 42=1
    root@am62xx-evm:~# rtcwake -s 10 -m mem -d rtc0
    rtcwake: wakeup from "mem" using rtc0 at Wed May 15 11:52:51 2024
    [14793.959706] PM: suspend entry (deep)
    [14793.963535] Filesystems sync: 0.000 seconds
    [14793.984404] remoteproc remoteproc0: stopped remote processor 5000000.m4fss
    [14793.992216] Freezing user space processes
    [14793.998574] Freezing user space processes completed (elapsed 0.002 seconds)
    [14794.005644] OOM killer disabled.
    [14794.008953] Freezing remaining freezable tasks
    [14794.014983] Freezing remaining freezable tasks completed (elapsed 0.001 seconds)
    [14794.022433] printk: Suspending console(s) (use no_console_suspend to debug)
    [14794.030889] wlcore: down
    [14794.075046] am65-cpsw-nuss 8000000.ethernet eth0: Link is Down
    [14794.075692] am65-cpsw-nuss 8000000.ethernet eth1: Link is Down
    [14794.087222] Disabling non-boot CPUs ...
    [14794.089465] psci: CPU1 killed (polled 0 ms)
    [14794.092185] psci: CPU2 killed (polled 4 ms)
    [14794.095310] psci: CPU3 killed (polled 0 ms)
    [14794.096803] Enabling non-boot CPUs ...
    [14794.097211] Detected VIPT I-cache on CPU1
    [14794.097299] GICv3: CPU1: found redistributor 1 region 0:0x00000000018a0000
    [14794.097367] CPU1: Booted secondary processor 0x0000000001 [0x410fd034]
    [14794.098288] CPU1 is up
    [14794.098553] Detected VIPT I-cache on CPU2
    [14794.098595] GICv3: CPU2: found redistributor 2 region 0:0x00000000018c0000
    [14794.098634] CPU2: Booted secondary processor 0x0000000002 [0x410fd034]
    [14794.099249] CPU2 is up
    [14794.099510] Detected VIPT I-cache on CPU3
    [14794.099556] GICv3: CPU3: found redistributor 3 region 0:0x00000000018e0000
    [14794.099594] CPU3: Booted secondary processor 0x0000000003 [0x410fd034]
    [14794.100332] CPU3 is up
    [14794.100784] ti-sci 44043000.system-controller: ti_sci_resume: wakeup source: 0x50
    [14794.211977] am65-cpsw-nuss 8000000.ethernet: set new flow-id-base 19
    [14794.221079] am65-cpsw-nuss 8000000.ethernet eth0: PHY [8000f00.mdio:00] driver [TI DP83867] (irq=POLL)
    [14794.221111] am65-cpsw-nuss 8000000.ethernet eth0: configuring for phy/rgmii-rxid link mode
    [14794.227876] am65-cpsw-nuss 8000000.ethernet eth1: PHY [8000f00.mdio:01] driver [TI DP83867] (irq=POLL)
    [14794.227888] am65-cpsw-nuss 8000000.ethernet eth1: configuring for phy/rgmii-rxid link mode
    [14794.881829] wlcore: PHY firmware version: Rev 8.2.0.0.245
    [14794.974604] wlcore: firmware booted (Rev 8.9.0.0.86)
    [14795.137653] OOM killer enabled.
    [14795.140798] Restarting tasks ... done.
    [14795.147954] random: crng reseeded on system resumption
    [14795.153614] remoteproc remoteproc0: powering up 5000000.m4fss
    [14795.159566] remoteproc remoteproc0: Booting fw image am62-mcu-m4f0_0-fw, size 55016
    [14795.168800] rproc-virtio rproc-virtio.0.auto: assigned reserved memory node m4f-dma-memory@9cb00000
    [14795.179306] virtio_rpmsg_bus virtio0: rpmsg host is online
    [14795.185035] virtio_rpmsg_bus virtio0: creating channel ti.ipc4.ping-pong addr 0xd
    [14795.186428] rproc-virtio rproc-virtio.0.auto: registered virtio0 (type 7)
    [14795.192979] virtio_rpmsg_bus virtio0: creating channel rpmsg_chrdev addr 0xe
    [14795.199528] remoteproc remoteproc0: remote processor 5000000.m4fss is now up
    [14795.213684] PM: suspend exit
    root@am62xx-evm:~# [14797.303814] am65-cpsw-nuss 8000000.ethernet eth0: Link is Up - 1Gbps/Full - flow control off
    [14797.304535] am65-cpsw-nuss 8000000.ethernet eth1: Link is Up - 1Gbps/Full - flow control off

    Why AM62 GPIOs are not retaining it's state during suspend-to-ram cycle ?

    Thanks.

    Regards,

    Parth P

  • Hi Parth,

    I observe the similar behavior where GPIO0_42 goes low/down for the time of the device deeplseep

    Do you have a measured voltage for low? From my tests so far, it will drop slightly (3.3V -> 3.27V). Have you seen the same behavior on MCU GPIO pins?

    Thanks,

    Anshu

  • Hi ,

    Thank you for response.

    Do you have a measured voltage for low? From my tests so far, it will drop slightly (3.3V -> 3.27V). Have you seen the same behavior on MCU GPIO pins?

    Yes, I have measured the voltage at GPIO0_42 and I see voltage drops to '0V' for the time device is in deepsleep.

    I did not test MCU GPIO. This is not much relevant for us. We want all the GPIOs (Main/MCU) to persist it's state for a complete suspend-to-ram cycle.

    Could you please confirm if there's known limitation/sw-bug around GPIO not persisting it's configured state across deepsleep cycle. Furthermore, what could be the solution for this issue (if it exists) and what would be the expected time of arrival for this solution ?

    Thank you.

    Regards,

    Parth P

  • A little bit more context on this. In our design GPIOs are used to control power enable signals (e.g. enable signal of some LDO) or peripherals reset.

    If a device gets reset or its power is removed while in standby (even for a very short amount of time), the hardware just misbehaves and the suspend/resume functionality is not usable. 

  • Hello Parth and fd,

    Thank you for your patience. I was able to replicate a test on GPIO0_42 as well, but I did not get the same results that you tests.

    • TI EVM: SK-AM62B-P1 PROC142A.
    • SDK Version: Linux SDK 9.2
    • Image: Default Image, updated the device tree to add GPIO0_42

    root@am62xx-evm:~# uname -a
    Linux am62xx-evm 6.1.80-ti-g2e423244f8c0 #1 SMP PREEMPT Wed Mar 20 14:43:33 UTC 2024 aarch64 aarch64 aarch64 GNU/Linux
    root@am62xx-evm:~# gpiodetect
    gpiochip0 [4201000.gpio] (24 lines)
    gpiochip1 [600000.gpio] (92 lines)
    gpiochip2 [601000.gpio] (52 lines)
    gpiochip3 [1-0022] (24 lines)
    root@am62xx-evm:~# gpioset 1 42=1
    root@am62xx-evm:~# devmem2 0xF40AC
    /dev/mem opened.
    Memory mapped at address 0xffff7f887000.
    Read at address  0x000F40AC (0xffff7f8870ac): 0x00050007
    root@am62xx-evm:~# echo mem > /sys/power/state

    For Main Domain GPIO0_42:

    Active Power Entering Deep Sleep At Deep Sleep Exiting Deep Sleep after Wakeup Trigger Active Power after Wakeup
    3.3V 3.27V 3.27V less than 10mV (?)

    3.3V

    The voltage drop during the wakeup sequence is unexpected.

    I discussed internally about the PADCONFIG behavior. If bit24 is set to zero, then the IO states will carry over from Active state into Deep Sleep. If bit24 is set to one, then the IO states will use what was defined in bits 25-30. This might be a variable to review.

    I don't have a solution at this moment, but will continue working on it.

    Best Regards,

    Anshu

  • Hello,

    After some recent experiments with setting Bit24=1 & toggling Bit26 of the PADCONFIG, we noticed that there a drop in voltage when we tried to resume as seen below:

    Changing the internal pullup/down resistor didn't seem to impact much.

    We're currently checking with the Software Development team to see which steps in the resume sequence may cause this. We'll continue experimenting and will update this thread by next week. 

    Best Regards,

    Anshu

  • Hello,

    After some further experimenting, we were able to point to the IO Isolation step in the Resume Sequence to cause the issue I noted in the previous post. We are now working on a possible solution to this.

    Thanks,

    Anshu

  • Hello,

    Can you provide a schematic that includes the GPIO that you are using? We're interested in the external pull resistors that in being used.

    Thanks,

    Anshu

  • The issue is not specific to a unique pin.

    One important example we have been looking at is GPMC0_AD2 (bootmode 02), we have a 2.2kOhm pull-down and after that, this is connected to the RESET_N of a TI DP83867 ethernet phy.

  • Thanks fd. Can you confirm the PADCONFIG register output you are getting? I'm assuming it is 0x00050007.

    Best Regards,

    Anshu

  • Can you confirm the PADCONFIG register output you are getting? I'm assuming it is 0x00050007.

    Correct

  • Can you please comment on this statement from ?

    The output buffer in each IO cells is disabled when the device enters Deep Sleep.

    from https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1369205/am625-gpio-s-impedance-change-in-deepsleep-mode 

  • I have requested Paul to clarify as needed. 

    In general in Deep Sleep mode, you will need to make sure that the pins that need to retain status , do not have an opposing pull up. 

    I think on your USBDRV issue the 100K helped, as the pin has default pull down (during and after reset) as listed in the datasheet Table 6-1 

  • In general in Deep Sleep mode, you will need to make sure that the pins that need to retain status , do not have an opposing pull up. 

    I read this as "the pins cannot retains the state in deep sleep mode".

    The requirement you are writing here is not generally possible to achieve in our use case. We have a situation in which a pin needs to be low when the board is reset, therefore we have a pull-down and need to be high in deep sleep.

    It would be helpful to understand if there is a way to at least partially workaround this issue. 

  • I do not read it as that, USB DRVBUS is somewhat specific, so will need Paul to comment. The IO state of DRVVBUS during deepsleep which is a weak high is conflicting with a strong external pull-down on the board, was how i read the issue. 

    The pins do retain their state in deep sleep with appropriate pad config handling etc

  • USB DRVBUS is somewhat specific

    Thanks for this clarification, this is important. For DRVVBUS we can find an ad-hoc solution.

    The pins do retain their state in deep sleep with appropriate pad config handling etc

    Thanks, looking forward to figuring out what is going on since this is not working for us as of now (I think you know, but I wanted to write it here to be sure that it is clear that this is still an open point from our point of view)

  • So now is the pin in question the following 

    One important example we have been looking at is GPMC0_AD2 (bootmode 02), we have a 2.2kOhm pull-down and after that, this is connected to the RESET_N of a TI DP83867 ethernet phy.

  • So now is the pin in question the following 

    One important example we have been looking at is GPMC0_AD2 (bootmode 02), we have a 2.2kOhm pull-down and after that, this is connected to the RESET_N of a TI DP83867 ethernet phy.

    This is not correct. This is just an example.

    Quoting myself and Parth:

    The issue is not specific to a unique pin.

    A little bit more context on this. In our design GPIOs are used to control power enable signals (e.g. enable signal of some LDO) or peripherals reset.

    If a device gets reset or its power is removed while in standby (even for a very short amount of time), the hardware just misbehaves and the suspend/resume functionality is not usable. 

    and

    We want all the GPIOs (Main/MCU) to persist it's state for a complete suspend-to-ram cycle.
  • Hi Francesco, Parth

    Attaching the presentation to summarize our discussion (this has the relevant sections in the TRM that will need to be referred to)

    High level summary 

    • During Deepsleep IOs are configured to Isolation state. During IO isolation, Receiver is kept ON for wake-up event propagation. Transmitter is turned OFF. IO can hold a value of ‘1’ or ‘0’ through an internal pull (~20K). Before entering into deeplseep mode, IO must be configured by programming the PADCFG MMRs to hold the value during deepsleep (bits 24, 27, 28). System designers must ensure that there is no opposing pulls or driver values on these pins on the board. Failure to do so will lead to indeterminate IO level.
    • Behavior of IOs on Main domain: Based on few SOC architecture considerations for key modules that exist in main domain, main domain is put in PORz state during deepsleep. Since the Main PADCFG is also located in Main domain, it is put into PORz state causing MMR context to be lost. Hence the only option for Main domain IOs is IO isolation as described above (IO holds the pre-programmed state).
    • Behavior of IOs in MCU/WKUP domain: MCU PADCFG is located in always ON WKUP domain. PADCFG MMR context is still preserved during deeplseep. Hence, MCU/WKUP domain IOs can have more options during deeplseep. For example, desired IOs can be removed from IO Isolation (ISO bypass – bit23). The Transmitter can be kept ON and can drive a value of ‘1’ or ‘0’ (bits 23-26).

    You can evaluate other low power modes, potentially MCU only or OS IDLE to see if they can help you retain the use-case where both MCU and Main domain IOs need to drive a value during a low power mode and cannot be guaranteed to have an opposing pull. 

    typical power consumption can be found in the following application note 

    AM62x Power Consumption

    The SDK documentation on power management below

    https://software-dl.ti.com/processor-sdk-linux/esd/AM62X/09_02_01_10/exports/docs/linux/Foundational_Components/Kernel/Kernel_Drivers/Power_Management/pm_low_power_modes.html

    AM62 Deep Sleep IO Considerations.pdf

    Please let us know if you have any follow up questions 

  • thanks for the update here.

    In addition to this  mentioned an unexpected "glitch" on the voltage during resume, is this something you are going to take care of? This seems more of a bug, and not a SOC architecture decision.

  • Yes there is some fine tuning going on the resume sequence on GPIO /PADCFG restore vs IO isolation. Some more experiments to run to ensure the glitch was not due to any noise in instrumentation and/or opposing pulls. Will keep you posted. 

  • Hi fd,

    Here is the most recent experiment.

    For a GPIO without an external pull resistor, we were able to reduce the voltage drop by changing the PADCONFIG register for the GPIO. We set Bit16=0, Bit17=1 of the PADCONFIG register so the internal, non-DeepSleep resistor is pulled high. There were no other changes to the bit fields.

    Here is the O-Scope measurement.


    We tested this using the default SDK 9.2 image and used RTCWake with a 10 second interval. The only change is to the device tree to add the pinmuxing for the GPIO.

    Best Regards,

    Anshu