qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* Emulation of 'System OFF' mode in ARM nRF51 SoCs
@ 2023-06-14  2:27 Chris Laplante
  2023-06-19 11:01 ` Philippe Mathieu-Daudé
  2023-06-19 12:03 ` Peter Maydell
  0 siblings, 2 replies; 7+ messages in thread
From: Chris Laplante @ 2023-06-14  2:27 UTC (permalink / raw)
  To: qemu-devel@nongnu.org

Hi all,

I am working on improving nRF51 emulation. Specifically I want to implement the special "System OFF" mode. System OFF is a power saving mode. In this mode, the system can only be woken up by a reset or a handful of peripherals (most notably, GPIO via high/low level detection on configured pins). System reset is triggered upon wakeup.

I've been digging into the QEMU mailing list and source code and have come to the conclusion that deep sleep and low power modes are not implemented. There seems to be support for turning off ARM CPU cores, e.g. as used by imx6_src.c. But that doesn't apply here because I only have one CPU. 

So ultimately what I think I will try to implement is what the nRF51 reference manual calls "Emulated System OFF mode". From the reference manual:

    If the device is in debug interface mode, System OFF will be emulated to secure 
    that all required resources needed for debugging are available during System OFF... 
    Since the CPU is kept on in emulated System OFF mode, it is recommended 
    to add an infinite loop directly after entering System OFF, to prevent the CPU from 
    executing code that normally should not be executed.

Does anyone have any guidance on how to implement this? I don't particularly care about fidelity. As long as a GPIO level trigger can break the CPU out of the infinite loop (which the reference manual tells users to add) and jump into the reset vector, it will be good enough for my use. I don't really care about masking out other interrupt sources, for example.

Thanks,
Chris


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-06-14  2:27 Emulation of 'System OFF' mode in ARM nRF51 SoCs Chris Laplante
@ 2023-06-19 11:01 ` Philippe Mathieu-Daudé
  2023-07-01 19:29   ` Chris Laplante
  2023-06-19 12:03 ` Peter Maydell
  1 sibling, 1 reply; 7+ messages in thread
From: Philippe Mathieu-Daudé @ 2023-06-19 11:01 UTC (permalink / raw)
  To: Chris Laplante, qemu-arm; +Cc: qemu-devel@nongnu.org

Hi Chris,

On 14/6/23 04:27, Chris Laplante wrote:
> Hi all,
> 
> I am working on improving nRF51 emulation. Specifically I want to implement the special "System OFF" mode. System OFF is a power saving mode. In this mode, the system can only be woken up by a reset or a handful of peripherals (most notably, GPIO via high/low level detection on configured pins). System reset is triggered upon wakeup.
> 
> I've been digging into the QEMU mailing list and source code and have come to the conclusion that deep sleep and low power modes are not implemented. There seems to be support for turning off ARM CPU cores, e.g. as used by imx6_src.c. But that doesn't apply here because I only have one CPU.

What problem are you getting with a single CPU?
The "arm/arm-powerctl.h" API should work well.
If you scheduled a timer, I expect it to awake
your CPU on expiration. You can also use a QMP
command to toggle a GPIO and trigger an IRQ.

You can use the qtest API to test your code,
see some tests in tests/qtest/ using:
- qtest_set_irq_in()
- qtest_qom_set_bool() for GPIO

Regards,

Phil.

> So ultimately what I think I will try to implement is what the nRF51 reference manual calls "Emulated System OFF mode". From the reference manual:
> 
>      If the device is in debug interface mode, System OFF will be emulated to secure
>      that all required resources needed for debugging are available during System OFF...
>      Since the CPU is kept on in emulated System OFF mode, it is recommended
>      to add an infinite loop directly after entering System OFF, to prevent the CPU from
>      executing code that normally should not be executed.
> 
> Does anyone have any guidance on how to implement this? I don't particularly care about fidelity. As long as a GPIO level trigger can break the CPU out of the infinite loop (which the reference manual tells users to add) and jump into the reset vector, it will be good enough for my use. I don't really care about masking out other interrupt sources, for example.
> 
> Thanks,
> Chris
> 



^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-06-14  2:27 Emulation of 'System OFF' mode in ARM nRF51 SoCs Chris Laplante
  2023-06-19 11:01 ` Philippe Mathieu-Daudé
@ 2023-06-19 12:03 ` Peter Maydell
  2023-07-01 19:29   ` Chris Laplante
  1 sibling, 1 reply; 7+ messages in thread
From: Peter Maydell @ 2023-06-19 12:03 UTC (permalink / raw)
  To: Chris Laplante; +Cc: qemu-devel@nongnu.org

On Wed, 14 Jun 2023 at 14:02, Chris Laplante <chris@laplante.io> wrote:
>
> Hi all,
>
> I am working on improving nRF51 emulation. Specifically I want to implement the special "System OFF" mode. System OFF is a power saving mode. In this mode, the system can only be woken up by a reset or a handful of peripherals (most notably, GPIO via high/low level detection on configured pins). System reset is triggered upon wakeup.
>
> I've been digging into the QEMU mailing list and source code and have come to the conclusion that deep sleep and low power modes are not implemented. There seems to be support for turning off ARM CPU cores, e.g. as used by imx6_src.c. But that doesn't apply here because I only have one CPU.

For QEMU, "power saving" is pretty irrelevant. We have a
couple of different modes:
 * CPU is executing instructions (i.e. it is powered on)
 * CPU is not executing instructions because of some sort of
   "halt" or "wfi" type instruction that means we should pause
   until the next incoming interrupt
 * CPU is not executing instructions because it is powered
   off. When some external device in the system powers it on,
   it will start up from reset.

The powerctl APIs work fine for single CPUs. Of course
the external power controller device in the system which
is calling the "power off" APIs needs to arrange to also call
"power on" again later.

> So ultimately what I think I will try to implement is what the nRF51 reference manual calls "Emulated System OFF mode". From the reference manual:
>
>     If the device is in debug interface mode, System OFF will be emulated to secure
>     that all required resources needed for debugging are available during System OFF...
>     Since the CPU is kept on in emulated System OFF mode, it is recommended
>     to add an infinite loop directly after entering System OFF, to prevent the CPU from
>     executing code that normally should not be executed.

The reference manual is very unclear about what this "emulated
system off" mode actually does. I think that implementing
real "system off" is probably simpler. For that you should be able
to implement it something like this:

 (1) the power management device implements the SYSTEMOFF register
     to call arm_set_cpu_off() when a 1 is written
 (2) make sure the GPIO device implements DETECT as a GPIO output
     signal, ie an outbound qemu_irq (if we don't do this already
     the functionality will need to be added to the device model)
 (3) similarly for ANADETECT from the LPCOMP device
 (4) Wire those qemu_irq GPIO outputs up to inputs on the
     power management device. When the power management device
     sees those signals go high and the CPU is in system off mode,
     it should trigger the reset of the CPU by calling
     arm_set_cpu_on_and_reset().

NB: this doesn't exactly model the defined system-off behaviour,
but it's probably close enough. Specifically, it will only reset
the CPU itself -- all other devices in the SoC will retain their
state across the power down. If you needed to implement the
hw exact behaviour (only "retained registers" keep their state,
others are reset, watchdog gets disabled, etc) you'd need to have
the power management device tell the other devices to do a
system-off reset in addition to dealing with powering the CPU
off and on. It's probably not worth looking at this extra
complication unless you really need it.

thanks
-- PMM


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-06-19 12:03 ` Peter Maydell
@ 2023-07-01 19:29   ` Chris Laplante
  2023-07-03 11:20     ` Peter Maydell
  0 siblings, 1 reply; 7+ messages in thread
From: Chris Laplante @ 2023-07-01 19:29 UTC (permalink / raw)
  To: Peter Maydell; +Cc: qemu-devel@nongnu.org

Hi Peter,

> The reference manual is very unclear about what this "emulated
> system off" mode actually does. I think that implementing
> real "system off" is probably simpler. For that you should be able
> to implement it something like this:
> 
> (1) the power management device implements the SYSTEMOFF register
> to call arm_set_cpu_off() when a 1 is written
> (2) make sure the GPIO device implements DETECT as a GPIO output
> signal, ie an outbound qemu_irq (if we don't do this already
> the functionality will need to be added to the device model)

Working on adding this now. One question - if the CPU is off (via arm_set_cpu_off), will the 'DETECT' IRQ I add to nrf51_gpio.c still fire? 

> (3) similarly for ANADETECT from the LPCOMP device
> (4) Wire those qemu_irq GPIO outputs up to inputs on the
> power management device. When the power management device
> sees those signals go high and the CPU is in system off mode,
> it should trigger the reset of the CPU by calling
> arm_set_cpu_on_and_reset().
>

There is no power management IC or device in this system. Is it something I can implement in nrf51 directly, or will I need to do it in machine context? I guess what I'm asking is, if the CPU is off, can it still wake itself up?

Thanks,
Chris


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-06-19 11:01 ` Philippe Mathieu-Daudé
@ 2023-07-01 19:29   ` Chris Laplante
  0 siblings, 0 replies; 7+ messages in thread
From: Chris Laplante @ 2023-07-01 19:29 UTC (permalink / raw)
  To: Philippe Mathieu-Daudé; +Cc: qemu-arm, qemu-devel@nongnu.org

Hi Phil,

> What problem are you getting with a single CPU?
> The "arm/arm-powerctl.h" API should work well.
> If you scheduled a timer, I expect it to awake
> your CPU on expiration. You can also use a QMP
> command to toggle a GPIO and trigger an IRQ.
> 
> You can use the qtest API to test your code,
> see some tests in tests/qtest/ using:
> - qtest_set_irq_in()
> - qtest_qom_set_bool() for GPIO

Thanks for the tips - I am working on implementing this now!

Chris


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-07-01 19:29   ` Chris Laplante
@ 2023-07-03 11:20     ` Peter Maydell
  2023-07-06 22:13       ` Chris Laplante
  0 siblings, 1 reply; 7+ messages in thread
From: Peter Maydell @ 2023-07-03 11:20 UTC (permalink / raw)
  To: Chris Laplante; +Cc: qemu-devel@nongnu.org

On Sat, 1 Jul 2023 at 20:29, Chris Laplante <chris@laplante.io> wrote:
>
> Hi Peter,
>
> > The reference manual is very unclear about what this "emulated
> > system off" mode actually does. I think that implementing
> > real "system off" is probably simpler. For that you should be able
> > to implement it something like this:
> >
> > (1) the power management device implements the SYSTEMOFF register
> > to call arm_set_cpu_off() when a 1 is written
> > (2) make sure the GPIO device implements DETECT as a GPIO output
> > signal, ie an outbound qemu_irq (if we don't do this already
> > the functionality will need to be added to the device model)
>
> Working on adding this now. One question - if the CPU is off (via arm_set_cpu_off), will the 'DETECT' IRQ I add to nrf51_gpio.c still fire?

Yes. The only thing that turning the CPU off affects is
the CPU -- all the rest of the devices in the system
continue to behave as normal.

> > (3) similarly for ANADETECT from the LPCOMP device
> > (4) Wire those qemu_irq GPIO outputs up to inputs on the
> > power management device. When the power management device
> > sees those signals go high and the CPU is in system off mode,
> > it should trigger the reset of the CPU by calling
> > arm_set_cpu_on_and_reset().
> >
>
> There is no power management IC or device in this system.

The manual says there is: chapter 12 describes the
power management and the registers involved, which are
in the POWER peripheral part of the SoC, starting at
0x4000_0000. QEMU just doesn't model that yet.

thanks
-- PMM


^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: Emulation of 'System OFF' mode in ARM nRF51 SoCs
  2023-07-03 11:20     ` Peter Maydell
@ 2023-07-06 22:13       ` Chris Laplante
  0 siblings, 0 replies; 7+ messages in thread
From: Chris Laplante @ 2023-07-06 22:13 UTC (permalink / raw)
  To: Peter Maydell; +Cc: qemu-devel@nongnu.org

Hi Peter,

> > 
> > Working on adding this now. One question - if the CPU is off (via arm_set_cpu_off), will the 'DETECT' IRQ I add to nrf51_gpio.c still fire?
> 
> 
> Yes. The only thing that turning the CPU off affects is
> the CPU -- all the rest of the devices in the system
> continue to behave as normal.
> 

Excellent, thanks.

> > There is no power management IC or device in this system.
> 
> 
> The manual says there is: chapter 12 describes the
> power management and the registers involved, which are
> in the POWER peripheral part of the SoC, starting at
> 0x4000_0000. QEMU just doesn't model that yet.
>

Ah yes, my mistake. I am working on implementing the POWER peripheral (along with CLOCK and MPU, since they are overlapped at 0x4000_0000). It will be called nrf51_cpm.

I have modified the GPIO peripheral to support the DETECT mechanism, and so far it seems to work. I have also locally implemented a version of qtest_irq_intercept_out which supports named GPIO out interrupts, and I have a qtest that confirms that basic functionality of DETECT is working. 

Hoping to have patches to send in the next couple weeks.

Thanks,
Chris


^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2023-07-06 22:14 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-06-14  2:27 Emulation of 'System OFF' mode in ARM nRF51 SoCs Chris Laplante
2023-06-19 11:01 ` Philippe Mathieu-Daudé
2023-07-01 19:29   ` Chris Laplante
2023-06-19 12:03 ` Peter Maydell
2023-07-01 19:29   ` Chris Laplante
2023-07-03 11:20     ` Peter Maydell
2023-07-06 22:13       ` Chris Laplante

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).