@@ -347,12 +347,33 @@ pub mod config {
347347 pub struct DcdcConfig {
348348 /// Config for the high voltage stage, if disabled LDO will be used.
349349 pub regh : bool ,
350+ /// Configure the voltage of the high voltage stage. It is stored in non-volatile memory (UICR.VREGHVOUT register); pass None to not touch it.
351+ #[ cfg( feature = "nrf5340-app-s" ) ]
352+ pub regh_voltage : Option < ReghVoltage > ,
350353 /// Config for the main rail, if disabled LDO will be used.
351354 pub regmain : bool ,
352355 /// Config for the radio rail, if disabled LDO will be used.
353356 pub regradio : bool ,
354357 }
355358
359+ /// Output voltage setting for VREGH regulator stage.
360+ #[ cfg( feature = "nrf5340-app-s" ) ]
361+ pub enum ReghVoltage {
362+ /// 1.8 V
363+ _1V8 = 0 ,
364+ /// 2.1 V
365+ _2V1 = 1 ,
366+ /// 2.4 V
367+ _2V4 = 2 ,
368+ /// 2.7 V
369+ _2V7 = 3 ,
370+ /// 3.0 V
371+ _3V0 = 4 ,
372+ /// 3.3 V
373+ _3v3 = 5 ,
374+ //ERASED = 7, means 1.8V
375+ }
376+
356377 /// Settings for enabling the built in DCDC converter.
357378 #[ cfg( feature = "_nrf91" ) ]
358379 pub struct DcdcConfig {
@@ -399,6 +420,8 @@ pub mod config {
399420 #[ cfg( feature = "_nrf5340-app" ) ]
400421 dcdc : DcdcConfig {
401422 regh : false ,
423+ #[ cfg( feature = "nrf5340-app-s" ) ]
424+ regh_voltage : None ,
402425 regmain : false ,
403426 regradio : false ,
404427 } ,
@@ -431,6 +454,7 @@ mod consts {
431454#[ allow( unused) ]
432455mod consts {
433456 pub const UICR_APPROTECT : * mut u32 = 0x00FF8000 as * mut u32 ;
457+ pub const UICR_VREGHVOUT : * mut u32 = 0x00FF8010 as * mut u32 ;
434458 pub const UICR_SECUREAPPROTECT : * mut u32 = 0x00FF801C as * mut u32 ;
435459 pub const UICR_NFCPINS : * mut u32 = 0x00FF8028 as * mut u32 ;
436460 pub const APPROTECT_ENABLED : u32 = 0x0000_0000 ;
@@ -683,6 +707,21 @@ pub fn init(config: config::Config) -> Peripherals {
683707 }
684708 }
685709
710+ #[ cfg( feature = "nrf5340-app-s" ) ]
711+ unsafe {
712+ if let Some ( value) = config. dcdc . regh_voltage {
713+ let value = value as u32 ;
714+ let res = uicr_write_masked ( consts:: UICR_VREGHVOUT , value, 0b00000000_00000000_00000000_00000111 ) ;
715+ needs_reset |= res == WriteResult :: Written ;
716+ if res == WriteResult :: Failed {
717+ warn ! (
718+ "Failed to set regulator voltage, as UICR is already programmed to some other setting, and can't be changed without erasing it.\n \
719+ To fix this, erase UICR manually, for example using `probe-rs erase` or `nrfjprog --eraseuicr`."
720+ ) ;
721+ }
722+ }
723+ }
724+
686725 if needs_reset {
687726 cortex_m:: peripheral:: SCB :: sys_reset ( ) ;
688727 }
0 commit comments