ArduinoCore-stm32l0 icon indicating copy to clipboard operation
ArduinoCore-stm32l0 copied to clipboard

Doesn't go to low power mode

Open kungfupizza opened this issue 4 years ago • 15 comments

Hi, I am using a custom board with nothing but LoRa murata IC and two relays. I made a small program to test the stop and sleep function.

I cannot see the controller going in the sleep/stop mode. When awake, the current consumption is at 4.6mA and when in sleep, it goes to 4.3mA. Not a drop at all. While my test codes look like below, #include"STM32L0.h"

void setup() { Serial1.begin(115200); //I need to use Serial1 not Serial

}

void loop() { Serial1.println("I am awake"); delay(5000); //Awake time.. 4.6mA Serial1.println("Going in stop mode"); STM32L0.stop(5000); //Stop time.. 4.3mA //Also used sleep, but it comes to same 4.3mA. }

My board doesn't have any LEDs or other peripherals. Just two relays, which I don't use at all here. What is it that I am doing wrong?

kungfupizza avatar Sep 28 '19 14:09 kungfupizza

Answering without schematic of what is wired on your board will be difficult. For sure there is an issue because calling stop put the device approx 2uA consumption, got lot of boards like that.

hallard avatar Oct 01 '19 07:10 hallard

@kungfupizza please check how the TCXO pin is wired, by default it should be connected to PA12 which turns it off, should that be your issue. Here is an example project you could use to help you out: https://github.com/IRNAS/smartparks-rhino-tracker-hardware

SloMusti avatar Oct 10 '19 11:10 SloMusti

The TCXO should be about 1mA. Without some schematics it's impossible to tell.

GrumpyOldPizza avatar Oct 10 '19 12:10 GrumpyOldPizza

image

Note that the LEDs have been removed before testing.

kungfupizza avatar Oct 10 '19 15:10 kungfupizza

Looks like you did not connect PA8 to USB_VBUS. So I suspect that the USB code goes crazy and this is why it refuses to go into low power modes.

GrumpyOldPizza avatar Oct 10 '19 16:10 GrumpyOldPizza

Is there some way to not let the controller get into the USB code?

kungfupizza avatar Oct 11 '19 15:10 kungfupizza

From where do you measure your current? Between 5V and the DC/DC input? Because if so, you've got a LED on 3V3 rail that should also consume about 2mA plus the DC/DC consumption

hallard avatar Oct 11 '19 20:10 hallard

No, I measure it after 3.3V conversion. Also like I had mentioned, the LEDs have been removed while testing.

kungfupizza avatar Oct 12 '19 07:10 kungfupizza

Two suggestions from my recent experience:

  • In my testing (with STM32L072 and core versoin 0.0.10), keeping Serial1 enabled keeps some clocks running, and power usage is about 3mA. Doing a Serial1.end() before sleeping and Serial1.begin(...) after sleeping should fix this. The same holds for SPI and Wire.
  • As for USB, I've seen that explicitly calling USBDevice.detach() removes the device from the bus, leaving only 300μA or so for the HSI64 that is still kept enabled. Only if you compile without USB support (select in the IDE Tools menu), power usage really drops (to 18μA in my case, most of which I suspect is components on my board). AFAICS, the current git master has improved this, by completely disabling the USB peripheral on USBDevice.detach(), or automatically when no VBUS is present. See also #125 for some additional discussion of this.

matthijskooijman avatar Dec 02 '20 10:12 matthijskooijman

Interesting. Serial1 / SPI / Wire should have all clocks shut down they use (HSI16), unless there is something else going on. N.b. that the system will stay in SLEEP mode if a background activity is still going on (or wakeup of Serial1 is selected with a baudrate higher than 19200). There might be a bug in 0.0.10, but in the current repository this is working correctly.

For USB HSI48 is turned off on USBDevice.detach(). There is no HSI64. If you are in a debugger (which will draw more power, enabled via STM32L0.swdEnable()). you can print out stm32l0_system_device and see what should be enabled.

GrumpyOldPizza avatar Dec 02 '20 13:12 GrumpyOldPizza

In my testing (with STM32L072 and core versoin 0.0.10), keeping Serial1 enabled keeps some clocks running, and power usage is about 3mA. Doing a Serial1.end() before sleeping and Serial1.begin(...) after sleeping should fix this. The same holds for SPI and Wire.

I wanted to see if this still happened with the master version, but I could no longer reproduce this (with either the master version or 0.0.10). Not sure what happened there, but now I also get a low power usage (I've seen 18-30μA for my whole board) in stop mode, even after calling SPI.begin(), Wire.begin() and Serial1.begin(). Maybe I was using SWD before and that added power usage, dunno exactly.

There is no HSI64

Oh, I meant HSI48 there, w00ps.

For USB HSI48 is turned off on USBDevice.detach().

Yeah, I see that HSI48 is now turned off, but I'm still seeing significant power usage (3mA or so) in stop after calling USBDevice.detach(). Also, the detach doesn't actually seem to work, the USB device does not show up as disconnected in dmesg (but opening the serial port does show failed to set dtr/rts, so I suspect the USB stack is shut down, but the pullup is still active maybe). I'll have to investigate this a bit closer later.

matthijskooijman avatar Dec 04 '20 19:12 matthijskooijman

Not sure what happened there, but now I also get a low power usage (I've seen 18-30μA for my whole board) in stop

but I'm still seeing significant power usage (3mA or so) in stop after calling USBDevice.detach().

There was another component on my board that was not always properly put to sleep during some of my tests, so that explains the extra power usage I was sometimes seeing. This explains the earlier higher measurements and the 3mA USB current as well. With that extra component disabled, I see 20-ish μA in stop mode with USB disabled at compiletime, but still 300-ish μA with USB enabled but detached.

Also, the detach doesn't actually seem to work, the USB device does not show up as disconnected in dmesg

This seems to be the pullup indeed, explicitly unsetting the DPPU bit before USBDevice.detach() makes the device disconnect properly and removes the 300μA current. So I guess that shutting down the USB peripheral doesn't disable the pullup, so it must be manually disabled. I'll open a separate issue (or probably a PR with a fix if I can figure out where to best fix this) for this. Update: Reported #171 for this

matthijskooijman avatar Dec 05 '20 11:12 matthijskooijman

Hello !

I'm facing an issue to put my device in sleep mode. It's working properly if the USB_VBUS pin is down (consumption = ~1,5uA) but the device doesn't sleep if the USB_VBUS pin is high (consumption = ~3mA).

Is there a way to "accept" the sleep even if the USB_VBUS is high (something like an uC register to set during the initialization) ? I need it because I have a bad protection diode how let pass a high state on my USB_VBUS pin and it's not possible to change the diode.

(This is the same diode problem as explained at the end of this topic -> #63 )

Sistrum avatar Feb 19 '21 17:02 Sistrum

@Sistrum Did you try USBDevice.detach() to disable the USB core? Also see #171 for a problem where the USB pullup is not correctly disabled, but that should only cause less current (some 300μA in my setup).

matthijskooijman avatar Feb 19 '21 18:02 matthijskooijman

Yes, it's working with USBDevice.detach(), thanks a lot !

Sistrum avatar Feb 22 '21 10:02 Sistrum