Skip to content

Commit

Permalink
Add support for Nicla Vision
Browse files Browse the repository at this point in the history
  • Loading branch information
sebromero committed Nov 25, 2024
1 parent b215570 commit f703173
Show file tree
Hide file tree
Showing 6 changed files with 96 additions and 11 deletions.
4 changes: 2 additions & 2 deletions examples/Standby_WakeFromPin/Standby_WakeFromPin.ino
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ Board board;

void setup() {
// When uploading this sketch to the M4 core, it just goes to standby mode.
#if defined(ARDUINO_GENERIC_STM32H747_M4)
#if defined(CORE_CM4)
board.standByUntilWakeupEvent();
return;
#endif
Expand All @@ -69,7 +69,7 @@ void setup() {
// On Portenta C33, you can specify which pin to use to wake up the device from sleep mode
// Please read the documentation to understand which pins can be used to wake up the device.
board.enableWakeupFromPin(PORTENTA_C33_WAKEUP_PIN, FALLING);
#elif defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_GENERIC_STM32H747_M4) || defined(ARDUINO_NICLA_VISION)
#elif defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_GENERIC_STM32H747_M4)
// On Portenta only pin GPIO0 can be used to wake up the device from sleep mode
board.enableWakeupFromPin();
#endif
Expand Down
2 changes: 1 addition & 1 deletion examples/Standby_WakeFromRTC_H7/Standby_WakeFromRTC_H7.ino
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ void blinkLed(int ledPin, int delayTime = 1000){

void setup() {
// When uploading this sketch to the M4 core, it just goes to standby mode.
#if defined(ARDUINO_GENERIC_STM32H747_M4)
#if defined(CORE_CM4)
board.standByUntilWakeupEvent();
return;
#endif
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
/*
Standby Wake from RTC Demo for Nicla Vision
This example demonstrates how to wake up the Nicla Vision from standby mode using the included RTC (Real Time Clock).
The device will stay awake for ~5 seconds, then go to sleep for 10 second. When the device is awake you will see the board's blue LED turned on.
Effectively, you will get the same effect as with blink.
The example also turns off the peripherals before going to sleep and turns them back on after waking up.
Usage:
- Make sure you are running the latest version of the Nicla Vision core.
- Select the Nicla Vision board from the Tools menu
- Select the Nicla Vision USB port from the Tools menu
- Upload the code to your Nicla Vision
Note: You need to upload this sketch to both cores, the M7 and the M4 for it to work.
You can do so by selecting the M7 core and then the M4 core from the Tools menu in the "Target core" section.
Initial authors:
Sebastian Romero ([email protected])
*/

#include "Arduino_PowerManagement.h"

Board board;

void blinkLed(int ledPin, int delayTime = 1000){
digitalWrite(ledPin, LOW);
delay(delayTime);
digitalWrite(ledPin, HIGH);
delay(delayTime);
}

void setup() {
// When uploading this sketch to the M4 core, it just goes to standby mode.
#if defined(CORE_CM4)
board.standByUntilWakeupEvent();
return;
#endif

pinMode(LEDR, OUTPUT); // Used to indicate errors
digitalWrite(LEDR, HIGH); // Turn off the red LED
pinMode(LED_BUILTIN, OUTPUT);
digitalWrite(LED_BUILTIN, LOW); // Turn on the built-in LED to show that the board is awake

if(!board.begin()){
// If the board fails to initialize, it will blink the red LED
while (true){
blinkLed(LEDR);
}
}

delay(10000); // keep the board awake for 10 seconds, so we can se it working
board.shutDownFuelGauge();

// The LED should go off when the board goes to sleep
board.setAllPeripheralsPower(false);

board.enableWakeupFromRTC(0, 0, 10); // Go to standby for 10 seconds
board.standByUntilWakeupEvent();
}

void loop() {}
2 changes: 1 addition & 1 deletion library.properties
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,4 @@ category=Device Control
url=https://github.com/arduino-libraries/Arduino_PowerManagement
architectures=renesas_portenta, mbed_portenta, mbed_nicla
includes=Arduino_PowerManagement.h
depends=Arduino_PF1550,Arduino_LowPowerPortentaC33,Arduino_LowPowerPortentaH7
depends=Arduino_PF1550,Arduino_LowPowerPortentaC33,Arduino_LowPowerPortentaH7,Arduino_LowPowerNiclaVision
32 changes: 26 additions & 6 deletions src/Board.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ Board::~Board() {
}

bool Board::begin() {
#if defined(ARDUINO_PORTENTA_H7_M7)
#if defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_NICLA_VISION)
if (CM7_CPUID == HAL_GetCurrentCPUID()){
if (LowPowerReturnCode::success != LowPower.checkOptionBytes()){
LowPower.prepareOptionBytes();
Expand Down Expand Up @@ -146,7 +146,7 @@ bool Board::enableWakeupFromRTC(uint32_t hours, uint32_t minutes, uint32_t secon

#endif

#if defined(ARDUINO_PORTENTA_H7)
#if defined(ARDUINO_PORTENTA_H7) || defined(ARDUINO_NICLA_VISION)
bool Board::enableWakeupFromRTC(uint32_t hours, uint32_t minutes, uint32_t seconds){
standbyType |= StandbyType::untilTimeElapsed;
wakeupDelayHours = hours;
Expand All @@ -165,16 +165,19 @@ void Board::sleepUntilWakeupEvent(){
void Board::standByUntilWakeupEvent(){
#if defined(ARDUINO_PORTENTA_C33)
lowPower -> deepSleep();
#elif defined(ARDUINO_GENERIC_STM32H747_M4)
#elif defined(CORE_CM4)
LowPower.standbyM4();
#elif defined(ARDUINO_PORTENTA_H7_M7)
#elif defined(ARDUINO_PORTENTA_H7_M7)
RTCWakeupDelay rtcWakeupDelay = RTCWakeupDelay(wakeupDelayHours, wakeupDelayMinutes, wakeupDelaySeconds);
if(standbyType == StandbyType::untilEither)
LowPower.standbyM7(LowPowerStandbyType::untilPinActivity | LowPowerStandbyType::untilTimeElapsed, rtcWakeupDelay);
else if (standbyType == StandbyType::untilPinActivity)
LowPower.standbyM7(LowPowerStandbyType::untilPinActivity);
else if (standbyType == StandbyType::untilTimeElapsed)
LowPower.standbyM7(LowPowerStandbyType::untilTimeElapsed, rtcWakeupDelay);
#elif defined(ARDUINO_NICLA_VISION) && defined(CORE_CM7)
RTCWakeupDelay rtcWakeupDelay = RTCWakeupDelay(wakeupDelayHours, wakeupDelayMinutes, wakeupDelaySeconds);
LowPower.standbyM7(rtcWakeupDelay);
#endif
}

Expand All @@ -185,7 +188,7 @@ void Board::setAllPeripheralsPower(bool on){
this -> setCommunicationPeripheralsPower(on);
this -> setExternalPowerEnabled(on);
this -> setAnalogDigitalConverterPower(on);
#else if defined(ARDUINO_PORTENTA_H7)
#elif defined(ARDUINO_PORTENTA_H7)
// On the H7 several chips need different voltages, so we cannot turn the lanes that are dependent on each other separately.
// This should only be used when going into standby mode, as turning off the USB-C PHY, Ethernet or Video bridge might cause undefined behaviour.
if(on){
Expand All @@ -199,6 +202,23 @@ void Board::setAllPeripheralsPower(bool on){
PMIC.getControl() -> turnLDO3Off(Ldo3Mode::Normal);
PMIC.getControl() -> turnSw1Off(Sw1Mode::Normal);
}

#elif defined(ARDUINO_NICLA_VISION)
if(on){
PMIC.getControl() -> turnLDO2On(Ldo2Mode::Normal); // Camera
PMIC.getControl() -> turnLDO1On(Ldo1Mode::Normal); // ToF sensor / Camera
PMIC.getControl() -> turnLDO3On(Ldo3Mode::Normal); // VDDA - Analog components, e.g. ADC
PMIC.getControl() -> turnSw2On(Sw2Mode::Normal); // USB, 25 MHz crystal, 32 kHz crystal
// TODO: Not supported yet by PMIC library
// PMIC.getControl() -> turnSw3On(Sw3Mode::Normal); // External power VDDIO_EXT
} else {
PMIC.getControl() -> turnLDO2Off(Ldo2Mode::Normal); // Camera
PMIC.getControl() -> turnLDO1Off(Ldo1Mode::Normal); // ToF sensor / Camera
PMIC.getControl() -> turnLDO3Off(Ldo3Mode::Normal); // VDDA - Analog components, e.g. ADC
PMIC.getControl() -> turnSw2Off(Sw2Mode::Normal); // USB, 25 MHz crystal, 32 kHz crystal
// TODO: Not supported yet by PMIC library
// PMIC.getControl() -> turnSw3Off(Sw3Mode::Normal); // External power VDDIO_EXT
}
#endif
}
//
Expand Down Expand Up @@ -270,7 +290,7 @@ bool Board::setReferenceVoltage(float voltage) {
void Board::shutDownFuelGauge() {
#if defined(ARDUINO_PORTENTA_C33)
MAX1726Driver fuelGauge(&Wire3);
#elif defined(ARDUINO_PORTENTA_H7_M7) || defined(ARDUINO_GENERIC_STM32H747_M4)
#elif defined(ARDUINO_PORTENTA_H7)
MAX1726Driver fuelGauge(&Wire1);
#elif defined(ARDUINO_NICLA_VISION)
MAX1726Driver fuelGauge(&Wire1);
Expand Down
6 changes: 5 additions & 1 deletion src/Board.h
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@
// but in this library we can turn of the Ethernet interface using the PMIC, so we set the NO_ETHERNET_TURN_OFF flag to avoid turning off the Ethernet interface from both sides.
#define NO_ETHERNET_TURN_OFF
#include "Arduino_LowPowerPortentaH7.h"
#elif defined(ARDUINO_NICLA_VISION)
#include "Arduino_LowPowerNiclaVision.h"
#endif

#define CONTEXT_LDO2 2 // LDO regulator: 1.8 V to 3.3 V, 400 mA
Expand Down Expand Up @@ -110,7 +112,9 @@ class Board {
* The pin is only accessible via high-density connectors.
*/
void enableWakeupFromPin();
#endif

#if defined(ARDUINO_PORTENTA_H7) || defined(ARDUINO_NICLA_VISION)
/**
* Enables sleep mode when the board is idle.
*/
Expand Down Expand Up @@ -153,7 +157,7 @@ class Board {
bool enableWakeupFromRTC(uint32_t hours, uint32_t minutes, uint32_t seconds, RTClock * rtc = &RTC);
#endif

#if defined(ARDUINO_PORTENTA_H7)
#if defined(ARDUINO_PORTENTA_H7) || defined(ARDUINO_NICLA_VISION)
/**
* Enables wake-up of the device from the RTC.
* @param hours The number of hours to sleep.
Expand Down

0 comments on commit f703173

Please sign in to comment.