Skip to content
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

[prodc-integration] Normal Sleep Power Consumption High #22241

Open
jettr opened this issue Mar 25, 2024 · 18 comments
Open

[prodc-integration] Normal Sleep Power Consumption High #22241

jettr opened this issue Mar 25, 2024 · 18 comments
Assignees
Labels
Component:RTL prodc-integration ProdC Integration Issues

Comments

@jettr
Copy link
Contributor

jettr commented Mar 25, 2024

Description

We are noticing that the power draw while the chip is in normal sleep is around 13mW (3.95mA @ 3.3V). We are hoping to target the 6 - 8 mW range or better for normal sleep.

By normal sleep, I mean a sleep that retains SRAM contents and will wake up and start executing code from where it left off. Normal sleep is like a deeper WFI where there is no pending interrupt to process. We still want to wake up from normal sleep in a reasonable amount of time to handle incoming TPM communication from the AP (either on I2C or SPI bus).

What we are doing for normal sleep:

  • Following programmers guide to enter low power mode
    • We configure the control to have only MAIN_PD_N set (this gives us 3.95mA draw)
    • If we set MAIN_PD_N + USB_CLK_EN_LP + IO_CLK_EN + CORE_CLK_EN we get 7.8mA as a point of reference.
      • What do we lose by allowing USB_CLK_EN_LP, IO_CLK, and CORE_CLK to shutdown during sleep?

What else can we try to get the power consumption of normal sleep down to the 6-8 mW range or better?


For another data point: "deep sleep," i.e. sleep that must resume execution from ROM/ROM_EXT, power consumption looks good. It is around 600uW (0.20mA @ 3.33V).

@jettr jettr added the prodc-integration ProdC Integration Issues label Mar 25, 2024
@johngt
Copy link

johngt commented Mar 26, 2024

@andreaskurth / @vogelpi - for power utilisation discussions

@andreaskurth
Copy link
Contributor

Potentially related: #22223

@moidx moidx added this to the Earlgrey-PROD.M4 milestone Mar 26, 2024
@moidx
Copy link
Contributor

moidx commented Mar 26, 2024

AI @jettr to disable entropy complex and measure power consumption to triage #22223. See reference:

status_t entropy_testutils_stop_all(void) {
.

This will turn off the TRNG request interface and should yield lower power consumption numbers.

@vogelpi
Copy link
Contributor

vogelpi commented Mar 26, 2024

When becoming active again, you should be able to just switch the MODULE_ENABLE fields in the main control registers of the EDNs, CSRNG and ENTROPY_SRC back on and don't need to undergo the full reconfiguration process. Currently, we don't provide a function in the testutils for that though.

In terms of latency, re-enabling ENTROPY_SRC and the TRNG will mean to repeat the startup health tests again and fill up the entropy buffer. This will take in the order of 5 - 10ms. To be sure it should maybe be experimentally verified (I can provide instructions for that). While waiting for the ENTROPY_SRC / TRNG to become online again, the processor can still run. It's just that crypto accelerators requiring randomness may be stalled for a while.

@jettr
Copy link
Contributor Author

jettr commented Mar 28, 2024

Disabling the entropy complex did reduce power consumption in normal sleep! The power consumption drops to 9mW (2.71mA @ 3.3V). I didn't try re-enabling the entropy sources or do crypto in my tests.

I performed

EDN0.stop();
EDN1.stop();
csrng_stop();
entropy_src_stop();

before the normal sleep where those resolve to

    impl Edn {
        pub fn stop(&self) {
            self.register
                .ctrl
                .modify(CTRL::CMD_FIFO_RST.val(multibit::size_4bit::TRUE));
            self.register.ctrl.set(0x9999);
        }
    }

    pub unsafe fn csrng_stop() {
        StaticRef::new(CSRNG_BASE_ADDR as *const CsrngRegisters).ctrl.set(0x0999);
    }

    pub unsafe fn entropy_src_stop() {
        let register = StaticRef::new(ENTROPY_SRC_BASE_ADDR as *const EntropySrcRegisters);
        register.module_enable.set(0x9);
        register.entropy_control.set(0x99);
        register.conf.set(0x2649999);
        register.health_test_windows.set(0x600200);
        register.alert_threshold.set(0xfffd0002);
    }

This is good new and seems like something we can use. Is there any other IP block we can disable to get another 2 - 3 mW savings?

@vogelpi
Copy link
Contributor

vogelpi commented Mar 28, 2024

Thanks for the feedback @jettr ! This is good news. Could please try to only disable the ENTROPY_SRC, i.e., just do a entropy_src_stop()? My expectation would be that this alone should be sufficient to reach 9mA. If you use the function dif_entropy_src_set_enabled() instead of entropy_src_stop() you also re-enable the ENTROPY_SRC with the same settings in an attempt to resume. In contrast, the stop function clears some of the settings.

As for further things to try out: Reading the documentation of the register you referenced above. I would suggest to use the following:

Apart from that, you also have the option to disable individual clocks via clkmgr. However, I don't know how this interacts with above settings.

  • CLK_ENABLES allows you to explicitly enable/disable the USB, and the 3 peripheral clocks.
  • CLK_HINTS allows you to explicitly enable/disable the clocks of the big crypto accelerators.

Another analog part you may want to disable is the ADC, see adc_en_ctl.

This was referenced Mar 29, 2024
@jettr
Copy link
Contributor Author

jettr commented Mar 29, 2024

Could please try to only disable the ENTROPY_SRC, i.e., just do a entropy_src_stop()? My expectation would be that this alone should be sufficient to reach 9mW.

You are correct. It appears that the only entropy_src_stop() reduces the power consumption.

If you use the function dif_entropy_src_set_enabled() instead of entropy_src_stop() you also re-enable the ENTROPY_SRC with the same settings in an attempt to resume.

When I only use entropy_src_set_enabled and none of the other methods we have been experimenting with in the following way:

entropy_src_set_enabled(false);
rv32i::support::wfi();
entropy_src_set_enabled(true);

I actually get even lower normal sleep power: 8.8mW (2.66mA * 3.3V), but not by that much. This also seems like it is a better choice we as don't have to go through health checks etc again on normal sleep resume.

As for the PMU Control register: I am already using MAIN_PD_N as the only bit that is set when entering normal sleep. And if I remove even that, then the chips goes into deep sleep (which is desirable in different sleep scenarios).

Apart from that, you also have the option to disable individual clocks via clkmgr

We haven't done too much of that yet. That is something we will explore too. Thank you.

Another analog part you may want to disable is the ADC

We do need to ADC to be monitoring for a cable insertion during normal/deep sleep so we can't fully disable it, but I do hope that we can make full use of the lower power mode that it offers.

This was referenced Mar 29, 2024
@andreaskurth
Copy link
Contributor

Related to high entropy consumption

@vogelpi
Copy link
Contributor

vogelpi commented Apr 29, 2024

@jettr We've found out today that keymgr doesn't behave ideally in terms of entropy consumption (see #22819). We're now discussing a hardware fix for that. In the meantime, and in particular for the engineering sample, software should set the reseed interval register to the maximum value. It's a 16-bit register, so the max reseed interval is something like 65535. It's not ideal but should already be much better than the default 256. You may want to try this out on the chip and re-measure power.

@jettr
Copy link
Contributor Author

jettr commented May 2, 2024

Thanks for the heads up! We will want to re-measure power for A1, but it should have this change.

@andreaskurth
Copy link
Contributor

@jettr: With the relaxed keymgr reseed configuration, does the power consumption of ES match the expectation / requirements?

@jettr
Copy link
Contributor Author

jettr commented May 13, 2024

I saw a small power different when I set reseed interval register to 0xFFFF. The normal sleep current for this round of testing started at ~4.26mA and dropped to ~4.07mA with the change. Looks like only about 630uW of power savings.

@vogelpi
Copy link
Contributor

vogelpi commented May 14, 2024

Thanks @jettr for getting back with additional results. It's less than I expected but on the other hand, keymgr is still triggering a reseed (CSRNG operation) every 0.5ms with this new setting. I think there is not much more that can be done for ES on the entropy complex front.

@jettr
Copy link
Contributor Author

jettr commented May 14, 2024

That's okay, we will just need to re-measure power with the A1 silicon :)

@andreaskurth
Copy link
Contributor

Disabling input for unused pins should help as well with reducing power consumption. That will be supported for most pins in A1

@andreaskurth andreaskurth added the Triage Priority Issue to be discussed with priority in the next triage meeting label May 24, 2024
@andreaskurth andreaskurth removed this from the Earlgrey-PROD.M4 milestone May 24, 2024
@andreaskurth
Copy link
Contributor

@johngt Please add this to PROD SiVal

@johngt johngt added this to the Earlgrey-SiVal milestone May 24, 2024
@andreaskurth andreaskurth removed the Triage Priority Issue to be discussed with priority in the next triage meeting label May 24, 2024
@matutem
Copy link
Contributor

matutem commented Aug 15, 2024

@jettr did you try disabling the various CONTROL.*CLK_EN?

@jettr
Copy link
Contributor Author

jettr commented Aug 16, 2024

@jettr did you try disabling the various CONTROL.*CLK_EN?

Yes, I performed all of this normal sleep testing with all of the CONTROL.*CLK_EN bits set to 0. The only enabled bits on the CONTROL register are CONTROL::LOW_POWER_HINT + CONTROL::MAIN_PD_N

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Component:RTL prodc-integration ProdC Integration Issues
Projects
None yet
Development

No branches or pull requests

6 participants