低功耗设计(1)【转载学习】

芯片设计进阶之路——低功耗深入理解(一) - 知乎 (zhihu.com)

低功耗产品设计=低功耗硬件设计+低功耗软件设计

一 . 需求分析阶段

1.1 引入

我们做不到 让马儿跑,又让马儿不吃草,但是可以合理的规划它跑的路线和时间段。

随着近几年电子产品的高速发展,出现了各式各样的便携式产品,他们的发展趋势必将是更小、更轻,功能更强大。那么在产品的开发过程中,需要在满足需求中性能指标后,尽可能的优化产品功耗。

1.2 需求分析举例

老板偶然看到别人带了个智能手环挺好,然后回来就决定自己也要做手环,吩咐产品经理去调研市面上的手环(竞品分析),产品经理通过调研发现小米的手环功能最多,待机最长,价格最便宜。然后就开始根据市面总体情况编写需求文档啦,我要求成本200块以内,待机20天,有记步等功能,外形多高多宽。然后交给工程师小李了。

小李一看,我擦,成本200,待机还要这么长,还要这么多功能,外形大小还限制了。要求真多,但也没办法,接下来就要根据需求进行软硬件的设计,首先我们先分析下小米手环的设计。

小米手环的硬件设计方面:

低功耗OLED显示屏(相对TFT LCD 数码管等功耗更低)

快速稳定的蓝牙4.0主控芯片(低功耗主控)

大电量,长续航(高能量高密度,锂聚合物电池)

传感器,采用功耗低,精度高的传感器芯片

硬件方面,器件的选型属于硬标准,为你低功耗的产品设计提供可能。

小米手环的软件设计方面:

软件上主要在使用方式上进行优化,例如检测不到运动芯片进入低功耗,屏幕熄灭,当运动的时候才进行触发等。

通过上面的例子我们也都发现,低功耗产品设计=低功耗硬件设计+低功耗软件设计(策略,使用方式)

二. 低功耗的硬件上设计


一个产品的设计,在硬件方面我们主要考虑哪些方面?

(1)说到主控芯片:我们以前接触过的MSP430,好多公司选它大都是因为它的低功耗特性。

但是仅几年stm32 L系列发展的势头更猛,我们下面说的低功耗都是基于stm32L系列进行讲解

(2)电源管理:LDO(低静态电流,输出可关断)DC/DC(高转化率,输出可关断)

注:静态电流就是不工作的时候不耗电,输出可关断就是可以cpu控制(用cpu管脚进行控制关掉)在我们选择电源管理芯片的时候一定要特别注意,有的芯片负载能力强,但是功耗高,有的功耗低,但是负载能力差,需要根据需求进行选定。可适当配合cpu进行关断处理。

(3)外设模块(休眠模式可配置,超低休眠电流,超低待机电流,中断唤醒功能) 

(4)外部接口

输入:超低功耗外围器件

输出:MOS管控制输出,避免长期供电。

注:低功耗外围器件选型可参考之前的功耗PPT

电容,按键,LED,存储器,模拟电路等。

三. stm32选型


1.stm32产品线

stm32的各个系列都有在低功耗方面做处理,但是想要更低的功耗,肯定是优先选择L系列。

手册内容:

STM32L4系列MCU可以根据微处理器运行时不同的应用需求来适时调整电压从而实现功耗的动态平衡。该功能适用于STOP模式下的低功耗外设(LP UART、LP定时器)、安全和保密特性、大量智能外设,以及诸如运算放大器、比较器、LCD、12位DAC和16位ADC(硬件过采样)等先进的低功耗模拟外设。

功耗方面,L系列到底在哪些方面优于F系列?

stm32F1 和stm32L系列模式对比

1>低功耗模式更多

2>低功耗模式下提供了更多 功能选择

3>低功耗模式下支持更多的唤醒源

4>实测,L4的漏电流确实比F1系列要小很多

等,不详细展开说明。

更为灵活的设计也必然会让我们在软件设计上更为灵活。

四 . stm32低功耗处理关键点


以stm32L476为例,决定 STM32L476 系统功耗的主要是三个因素稳压器(voltage regulator)、CPU 工作频率、芯片自身低功耗的处理,下面分别对三个因素进行阐述。

1.稳压器

L4 使用两个嵌入式线性稳压器为所有数字电路、待机电路以及备份时钟域供电,分别是主稳压器(main regulator,下文简称 MR)和低功耗稳压器(low-power regulator,下文简称 LPR)。稳压器在复位后处于使能状态,根据应用模式,选择不同的稳压器对 Vcore 域供电。其中,MR 的输出电压可以由软件配置为不同的范围(Range 1 和 Rnage 2)。

稳压器

应用场合

MR(Range 1)Vcore = 1.2V,用于运行模式、睡眠模式和停止模式0,MR 为 Vcore 域提供全功率
MR(Range 2)Vcore = 1.0V,使用的场景同上
LPR用于低功耗运行模式、低功耗休眠模式、停止模式 1、停止模式2
OFFStandby 和 Shutdown 模式下,MR 和 LPR 都被关闭

注:不同的供电范围,外设应用上会有限制(ADC USB)

2.CPU 工作频率

通过降低 CPU 的主频达到降低功耗的目的:
MR 工作在 Range 1 正常模式时,SYSCLK 最高可以工作在 80M;
MR 工作在 Range 2 时,SYSCLK 最高不能超过 26 M;
低功耗运行模式和低功耗休眠模式,即 Vcore 域由 LPR 供电,SYSCLK 必须小于 2M。

注:在频率修改的时候一定要注意供电范围,及外设的限制。

3.芯片本身的低功耗处理

芯片本身定义了一系列的休眠模式,如 Sleeep、Stop、Standby 和 Shutdown,前面的四种模式功耗逐渐降低,实质是芯片内部通过关闭外设和时钟来实现。

参考:低功耗管理系统从设计上分运行模式休眠模式,独立管理,运行模式用于变频和变电压,休眠调用芯片的休眠特性。对于多数芯片和开发来说,可能并不需要考虑变频和变电压,仅需关注休眠模式。 

五.stm32L 低功耗模式

我们下面主要讲解sleep模式和stop模式,其他模式作为了解。

5.1 低功耗运行模式(RUN LP)

内核和外设都可以保持运行状态 

进入低功耗运行模式必须: 

配置内部电源变换器工作在低功耗模式下(设置LPRUN和LPSDSR 位)
系统时钟必须设置在128KHz以下,可以使用MSI作为系统时钟
内核供电VCORE必须选择供电范围2(1.5V),并且关闭动态电压调节功能

进入低功耗运行模式可选: 

通过RCC_APBxENR和RCC_AHBENR关闭不使用的外设时钟
选择从SRAM执行代码,并配置Flash模块进入低功耗模式
关闭VREFINT
 

内核逻辑由低功耗稳压器供电,以降低静态电流;

在低功耗睡眠模式下,可关闭闪存(掉电模式和时钟门控)。当处理器从SRAM1或SRAM2

执行时,它还可在低功耗运行模式下关闭;

系统时钟频率最大限于2 MHz。可选择MSI内部RC振荡器,因为它支持多种频率范围,低

功耗睡眠闪存关闭时MCU总消耗很小,在100 kHz可低至18 µA

5.2 睡眠模式(SLEEP)

内核停止运行,外设保持运行

5.2.1、需要通过特殊的指令进入睡眠模式
WFI (由中断唤醒)

退出:任意的NVIC识别到的外设中断都可以唤醒内核

WFE (由事件唤醒)

事件是指在没有在NVIC中使能的外设中断,或被配置为事件模式的EXTI中断。

退出:一旦事件产生,即可唤醒内核,不会有进入/退出中断而产生的延迟

5.2.2、 选择进入睡眠模式的机制(SLEEPONEXIT位)
Sleep Now: SLEEPONEXIT=0:MCU在WFI或WFE指令后立即进入SLEEP模式。

Sleep on Exit: SLEEPONEXIT=1:MCU在退出某个低优先级的ISR之后进入 SLEEP模式

5.2.3、进一步降低功耗
在SLEEP模式下,所有的I/O口和外设都保持和运行时一致的状态,因

此可以关闭不使用的外设的时钟,以降低功耗

5.3低功耗睡眠模式

内核停止运行,外设保持运行

进入低功耗睡眠模式必须: 

配置内部电源变换器工作在低功耗模式下(设置LPSDSR位),并执 行WFI或WFE指令
Flash模块进入低功耗模式(设置SLEEP_PD位),RAM内容保持
系统时钟必须设置在128KHz以下

内核供电VCORE必须选择供电范围2(1.5V)
选择进入低功耗睡眠模式的机制 (SLEEPONEXIT位),选择SLEEP NOW或者SLEEP ON EXIT
进入低功耗睡眠模式可选: 

关闭不使用的外设和GPIO口的时钟
关闭VREFINT
 

5.4停止模式

内核停止,VCORE范围内的时钟都停止,PLL, MSI, HSI和HSE都被禁止,SRAM和寄存器的内容保留

进入停止模式必须: 

选择进入低功耗睡眠模式的机制 (SLEEPONEXIT位),设置SLEEPDEEP位,清除PDDS位,执行WFI或WFE指令。

清除所有的EXTI,RTC警报,RTC唤醒,RTC侵入检测,RTC时间戳的未处理标志位。

从停止模式唤醒时,MSI将自动作为系统时钟,唤醒所需时间的典型值为7.9us。

进入停止模式可选: 

内部电源变换器可以工作在正常模式或者低功耗模式,为了降低功耗,推荐设置电源变换器工作在低功耗模式(LPSDSR位)

禁止Flash的供电,关闭VREFINT,BOR,PVD和侵入检测功能可以单独使能IWDG,RTC,LSI和LSE功能可以使用ADC,DAC和LCD的功能
       STM32L4系列产品实现了三个停止模式,具有完全SRAM和外设保持能力,并且由于使用了高

达48 MHz的MSI,能够在1 µs内唤醒。

在这些停止模式下,所有高速振荡器(HSE,MSI,HSI)都停止,而低速振荡器(LSE,

LSI)可保持活动。外设可设置为活动的,需要时可使用HSI时钟,能够在一些特定事件

(如UART字符重复或I2C地址识别)下唤醒设备。

Stop2模式可实现专门机制,使保持电流尽可能低,同时允许非常快速的唤醒,从SRAM唤醒

需要5 µs,或从闪存唤醒需要8 µs。

5.5待机模式

内部电源变换器关闭,VCORE范围内全部断电, PLL, MSI, HSI和HSE都被禁止,SRAM和寄存器内容不保留,RTC寄存器,RTC备份寄存器和待机电路保持原状

待机模式下所有I/O口都保持高阻状态,除了:

Reset引脚
配置为侵入检测/时间戳/报警A输出/报警B输出/RTC唤醒/校准 输出的RTC_AF1引脚
使能的WKUP1/ WKUP2/ WKUP3引脚


进入待机模式必须: 

设置SLEEPDEEP位,设置PDDS位,清除WUF位,执行WFI或WFE指令。
清除配置为唤醒源的RTC标志位,如RTC警报,RTC唤醒,RTC侵入检测,RTC时间戳标志。

进入待机模式可选: 

待机模式时可以使用IWDG,RTC,LSI和LSE功能。
 

每个模式都有自己特点,根据自己的需求,进行模式的适配。

在上面的模式中也不断的提到,在什么模式下,什么外设可用,什么时钟不可用,要用什么中断源唤醒,无非都是ST在芯片设计的时候将电源的管理部分进行更为灵活的设计,才能为我们提供这么多的动态接口。那么ST的内部电源管理还是需要进行了解的。

六.stm32L freertos 下低功耗模式

1.sleep模式

freertos 进入空闲后,进入sleep模式,sleep模式下任何中断都会导致退出sleep模式,滴答定时器也会导致唤醒,这肯定不是我们想要的,但是freertos的系统调度依赖于滴答时钟,那么我们的系统就会崩溃,那么对这段时间进行下补偿就好了,我们可以使用LPtime进行时间补偿,freertos使用滴答时钟完成了这个功能,我们通过系统函数得到下个任务到来的时间,然后设置滴答定时器在那个时候来中断唤醒系统,当然也会存在其他中断唤醒的情况,滴答时钟进行计时,之后的时间减去睡眠之前记录的时间,就可以轻松得到补偿时间。

这个操作,依赖于我们最先就配置好了时钟,滴答时钟进行精准的计时,那假如我在整个系统运行中想要把整个主频降低该怎么办?

我们在动态改变整个系统的时钟的时候肯定要先把整个任务调度和中断停掉,这个时候再更换时钟,就神不知鬼不觉了,当然这种方式肯定要快而且不能频繁操作,不然我们的整个系统的调度时间都要被延后了。

2.freertos 下stop模式

模仿tickless进行的实现。串口唤醒,中断唤醒及lptime进行时间补偿的计时。

重要的是时钟的恢复,不然整个系统会跑乱。

配合RTC进行唤醒

关键点1:时钟的选择(配置和恢复)

时钟设置:

stop模式是会停掉时钟的,唤醒后要进行时钟的恢复,这样freertos才能正常的进行调度。(恢复的时钟要和设置的前后保持一致)

关键点2:设置串口中断唤醒及RTC唤醒

我们知道,低功耗模式的操作是在空闲时间进行的,我们肯定不能睡过,不然就错过了下一任务的执行,我们通过

RTC唤醒中断,当下一个任务到来的时候进行周期唤醒,也就是获得最大的stop时间,这个时间我们可以通过freertos的接口进行获取到。

但是我们的串口数据不是规律到来的,所以还要配置下串口中断唤醒,但是最为麻烦的是,从stop开始,到串口唤醒,这段时间是不知道的,freertos是通过滴答定时器进行计时的,但是我们stop模式下只有LSE和LSI时钟可用。一种方法就是将滴答时钟改为以上时钟,这样stop的时候就不会影响计时了,还有就是通过LPtime进行定时。

大致流程如下:

配置串口唤醒中断,RTC中断
lptime进行计时
开始进入stop模式
唤醒后,停止计时,得到睡眠时间。
区分是中断唤醒还是RTC周期唤醒,之后进行不同的补偿方式到freertos
恢复时钟
 

注:LPtime的定时时间要精准,不然整个调度过程就会出错。

关键点三:滴答时钟寄存器

在时间补偿的过程中,我们要停掉滴答时钟,滴答定时器重装载,恢复时钟等操作,滴答定时器的寄存器需要理解。

了解sysTick定时器:

Systick(系统节拍)定时器,它属于NVIC的一部分,且可以产生SysTick异常。Systick为简单的向下计数的24位计数器,可以使用处理器内部时钟或者外部参考时钟。

在操作系统中,需要一个周期性的中断来定期触发OS内核。如用于任务管理和上下文切换,处理器也可以在不同时间片内处理不同任务。处理器设计还需要确保运行在非特权等级的应用任务无法禁止该定时器,否则任务可能会禁止SysTick定时器并锁定整个系统。

systick中存在4个寄存器:

如何停止定时器,如果重装载值,这里不过多说明,查看相应的寄存器

补偿步骤:

停止滴答定时器
计算重装载值(补偿的值增加上去)
重新启动定时器

 

附件:

LPuart stop下唤醒中断配置:

void LPUART_PrepareToStopMode(void)
{
	uint8_t ubReceivedChar;
 
	/* Empty RX Fifo before entering Stop mode 2 (Otherwise, characters already present in FIFO
	will lead to immediate wake up */
	while (LL_LPUART_IsActiveFlag_RXNE(LPUART1))
	{
		/* Read Received character. RXNE flag is cleared by reading of RDR register */
		ubReceivedChar = LL_LPUART_ReceiveData8(LPUART1);
	}
 
	ubReceivedChar = ubReceivedChar;
 
	/* Clear OVERRUN flag */
	LL_LPUART_ClearFlag_ORE(LPUART1);
 
	/* Make sure that no LPUART transfer is on-going */
	while(LL_LPUART_IsActiveFlag_BUSY(LPUART1) == 1)
	{
	}
	/* Make sure that LPUART is ready to receive */
	while(LL_LPUART_IsActiveFlag_REACK(LPUART1) == 0)
	{
	}
 
	/* Configure LPUART1 transfer interrupts : */
	/* Clear WUF flag and enable the UART Wake Up from stop mode Interrupt */
	LL_LPUART_ClearFlag_WKUP(LPUART1);
	LL_LPUART_EnableIT_WKUP(LPUART1);
 
	/*STOP2模式下使能时钟*/
	LL_LPUART_EnableClockInStopMode(LPUART1);
 
	/* Enable Wake Up From Stop */
	LL_LPUART_EnableInStopMode(LPUART1);
}

stop唤醒后,时钟恢复:

void SYSCLKConfig_STOP(void)
{
	RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};
	RCC_OscInitTypeDef RCC_OscInitStruct = {0};
	uint32_t pFLatency = 0;
 
	/* Enable Power Control clock */
	__HAL_RCC_PWR_CLK_ENABLE();
 
	/* Get the Oscillators configuration according to the internal RCC registers */
	HAL_RCC_GetOscConfig(&RCC_OscInitStruct);
 
	/* Enable PLL */
	RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_NONE;
	RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON;
	if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK)
	{
 
	}
 
	/* Get the Clocks configuration according to the internal RCC registers */
	HAL_RCC_GetClockConfig(&RCC_ClkInitStruct, &pFLatency);
 
	/* Select PLL as system clock source and keep HCLK, PCLK1 and PCLK2 clocks dividers as before */
	RCC_ClkInitStruct.ClockType     = RCC_CLOCKTYPE_SYSCLK;
	RCC_ClkInitStruct.SYSCLKSource  = RCC_SYSCLKSOURCE_PLLCLK;
	if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, pFLatency) != HAL_OK)
	{
 
	}
}

睡眠前第一个函数及唤醒后第一个函数

void OS_PreSleepProcessing(uint32_t xExpectedIdleTime)
{
	tick_sleep = xExpectedIdleTime;
	LPUART_PrepareToStopMode();											//配置串口唤醒
	HAL_RTCEx_DeactivateWakeUpTimer(&RTCHandle);						//配置RTC唤醒
	HAL_RTCEx_SetWakeUpTimer_IT(&RTCHandle, (uint32_t)((tick_sleep)*2.048), RTC_WAKEUPCLOCK_RTCCLK_DIV16);	// Wakeup Time Base = 16 /(~32.000KHz) = ~0.5 ms
	count_start(); 														//重置计数
	HAL_PWREx_EnterSTOP1Mode(PWR_STOPENTRY_WFI);						//进入低功耗
	uart_wkp = 0;
}
void OS_PostSleepProcessing(uint32_t ulExpectedIdleTime)
{
	time_count_sys =  LL_LPTIM_GetCounter(LPTIM2)+4;
	count_stop();
	if(uart_wkp != 1)
	{
		//表示为RTC唤醒
		rtc_wakeup_flag =1;
	}
	else
	{
	  	rtc_wakeup_flag =0;
		uart_wkp = 0;
	}
	SYSCLKConfig_STOP();
	LL_RCC_SetLPTIMClockSource(LL_RCC_LPTIM1_CLKSOURCE_LSI);
	LL_LPTIM_Enable(LPTIM1);
	LL_LPTIM_SetAutoReload(LPTIM1, 65535);
	LL_LPTIM_StartCounter(LPTIM1, LL_LPTIM_OPERATING_MODE_CONTINUOUS);//恢复时钟
}

主要的时钟补偿函数:

__weak void vPortSuppressTicksAndSleep( TickType_t xExpectedIdleTime )
	{
		uint32_t ulReloadValue, ulCompleteTickPeriods, ulSysTickCTRL;
		/* 确保滴答定时器的重装值不会溢出(不超过最大计数值) */
		if( xExpectedIdleTime > xMaximumPossibleSuppressedTicks )
		{
			xExpectedIdleTime = xMaximumPossibleSuppressedTicks;
		}
 
		/* 停止滴答定时器*/
		portNVIC_SYSTICK_CTRL_REG &= ~portNVIC_SYSTICK_ENABLE_BIT;
 
		/* 根据参数xExpectedIdleTime来计算滴答定时器的重装载值 */
		ulReloadValue = portNVIC_SYSTICK_CURRENT_VALUE_REG + ( ulTimerCountsForOneTick * ( xExpectedIdleTime - 1UL ) );
 
		/* Enter a critical section but don't use the taskENTER_CRITICAL()
		method as that will mask interrupts that should exit sleep mode. */
		__DSB();
		__ISB();
 
		/* If a context switch is pending or a task is waiting for the scheduler
		to be unsuspended then abandon the low power entry. */
		if( eTaskConfirmSleepModeStatus() == eAbortSleep ) //再次判断是否能够进入低功耗
		{
			/* Restart from whatever is left in the count register to complete
			this tick period. */
			portNVIC_SYSTICK_LOAD_REG = portNVIC_SYSTICK_CURRENT_VALUE_REG;
 
			/* Restart SysTick. */
			portNVIC_SYSTICK_CTRL_REG |= portNVIC_SYSTICK_ENABLE_BIT;
 
			/* Reset the reload register to the value required for normal tick
			periods. */
			portNVIC_SYSTICK_LOAD_REG = ulTimerCountsForOneTick - 1UL;
 
			/* Re-enable interrupts - see comments above __disable_interrupt()
			call above. */
		}
		else
		{
		      /* Set the new reload value. */
		      portNVIC_SYSTICK_LOAD_REG = ulReloadValue;
 
		      /* Clear the SysTick count flag and set the count value back to
		      zero. */
		      portNVIC_SYSTICK_CURRENT_VALUE_REG = 0UL;
 
		      /* Restart SysTick. */
		      portNVIC_SYSTICK_CTRL_REG |= portNVIC_SYSTICK_ENABLE_BIT;
 
		      /* Sleep until something happens.  configPRE_SLEEP_PROCESSING() can
		      set its parameter to 0 to indicate that its implementation contains
		      its own wait for interrupt or wait for event instruction, and so wfi
		      should not be executed again.  However, the original expected idle
		      time variable must remain unmodified, so a copy is taken. */
		      configPRE_SLEEP_PROCESSING(xExpectedIdleTime);
 
		      configPOST_SLEEP_PROCESSING( xExpectedIdleTime );
 
		      /* 停止滴答定时器 */
		      ulSysTickCTRL = portNVIC_SYSTICK_CTRL_REG;
		      portNVIC_SYSTICK_CTRL_REG = ( ulSysTickCTRL & ~portNVIC_SYSTICK_ENABLE_BIT );
 
		      /* Re-enable interrupts - see comments above __disable_interrupt()
		      call above. */
 
		      if(rtc_wakeup_flag ==1)
		      {
			      rtc_wakeup_flag = 0;
			      ulCompleteTickPeriods = tick_sleep; //rtc正常周期的时钟补偿
		      }
		      else
		      {
			      if(time_count_sys > xExpectedIdleTime)
			      {
			      	time_count_sys = xExpectedIdleTime;
			      }
			      ulCompleteTickPeriods = time_count_sys;//串口中断的时钟补偿
 
		      }
 
		      /* 重新启动滴答定时器,滴答定时器的重装载值设置为正常值*/
		      portNVIC_SYSTICK_CURRENT_VALUE_REG = 0UL;
		      portENTER_CRITICAL();
		      {
			      portNVIC_SYSTICK_CTRL_REG |= portNVIC_SYSTICK_ENABLE_BIT;
			      vTaskStepTick( ulCompleteTickPeriods );
			      portNVIC_SYSTICK_LOAD_REG = ulTimerCountsForOneTick - 1UL;
		      }
		      portEXIT_CRITICAL();
	      }
	}

rtc初始化:(唤醒+时钟功能)

static void MX_RTC_Init(void)
{
 
	/* USER CODE BEGIN RTC_Init 0 */
	LL_EXTI_InitTypeDef EXIT_InitStructure;
	/* USER CODE END RTC_Init 0 */
 
	LL_RTC_TimeTypeDef RTC_TimeStruct = {0};
	LL_RTC_DateTypeDef RTC_DateStruct = {0};
 
	/* Peripheral clock enable */
	LL_RCC_EnableRTC();
 
	/* RTC interrupt Init */
	NVIC_SetPriority(RTC_WKUP_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),0, 0));
	NVIC_EnableIRQ(RTC_WKUP_IRQn);
 
	/* USER CODE BEGIN RTC_Init 1 */
	LL_RTC_DisableWriteProtection(RTC);
	LL_RTC_WAKEUP_Disable(RTC);
	/* Wait until it is allow to modify wake up reload value */
	while (LL_RTC_IsActiveFlag_WUTW(RTC) != 1)
	{
	}
	LL_RTC_WAKEUP_SetAutoReload(RTC, 0);
	LL_RTC_WAKEUP_SetClock(RTC, LL_RTC_WAKEUPCLOCK_DIV_16);
 
	/* Enable wake up counter and wake up interrupt */
	LL_RTC_EnableIT_WUT(RTC);
	LL_RTC_WAKEUP_Enable(RTC);
 
	LL_RTC_EnableWriteProtection(RTC);
 
	/* Reset Internal Wake up flag */
	LL_RTC_ClearFlag_WUT(RTC);
 
	/*初始化RTC唤醒对应的EXIT_LINE_20*/
	LL_EXTI_ClearFlag_0_31(LL_EXTI_LINE_20);
 
	EXIT_InitStructure.Line_0_31 = LL_EXTI_LINE_20;
	EXIT_InitStructure.LineCommand = ENABLE;
	EXIT_InitStructure.Mode = LL_EXTI_MODE_IT ;
	EXIT_InitStructure.Trigger = LL_EXTI_TRIGGER_RISING;
	LL_EXTI_Init(&EXIT_InitStructure);
 
	/* USER CODE END RTC_Init 1 */
	/** Initialize RTC and set the Time and Date
	*/
	RTCHandle.Instance = RTC;
 
	RTCHandle.Init.HourFormat = RTC_HOURFORMAT_24;
	RTCHandle.Init.AsynchPrediv = RTC_ASYNCH_PREDIV;
	RTCHandle.Init.SynchPrediv = RTC_SYNCH_PREDIV;
	RTCHandle.Init.OutPut = RTC_OUTPUT_DISABLE;
	RTCHandle.Init.OutPutPolarity = RTC_OUTPUT_POLARITY_HIGH;
	RTCHandle.Init.OutPutType = RTC_OUTPUT_TYPE_OPENDRAIN;
 
	if( HAL_RTC_Init(&RTCHandle) != HAL_OK)
	{
		/* Initialization Error */
	}
	/** Initialize RTC and set the Time and Date
	*/
	if(LL_RTC_BAK_GetRegister(RTC, LL_RTC_BKP_DR0) != 0x32F2){
 
		RTC_TimeStruct.Hours = 10;
		RTC_TimeStruct.Minutes = 0;
		RTC_TimeStruct.Seconds = 0;
		LL_RTC_TIME_Init(RTC, LL_RTC_FORMAT_BCD, &RTC_TimeStruct);
		RTC_DateStruct.WeekDay = LL_RTC_WEEKDAY_TUESDAY;
		RTC_DateStruct.Month = 10;
		RTC_DateStruct.Day = 1;
		RTC_DateStruct.Year = 19;
		LL_RTC_DATE_Init(RTC, LL_RTC_FORMAT_BCD, &RTC_DateStruct);
		LL_RTC_BAK_SetRegister(RTC,LL_RTC_BKP_DR0,0x32F2);
	}
	/** Initialize RTC and set the Time and Date
	*/
	/* USER CODE BEGIN RTC_Init 2 */
 
	/* USER CODE END RTC_Init 2 */
 
}


————————————————
原文链接:6.stm32 低功耗设计--总结_stm32低功耗系列-CSDN博客

  • 2
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
### 回答1: Renesas是指日本Renesas电子公司的产品和解决方案具有较特性。作为一家领先的半导体解决方案供应商,Renesas致力于提供高性能、的产品来满足客户的需求。 首先,Renesas的产品在设计上具有优化的电源管理,提供更高的能源效率。通过有效的电源控制和管理,Renesas设备可以减少能源的消,延长电池寿命,提供更长的使用时间。这对于诸如智能手机、可穿戴设备和工业应用等需要长时间使用的设备特别重要。 其次,Renesas的产品在工作模式和待机模式之间自动切换,以最大限度地减少率的消。当设备不需要工作时,Renesas的解决方案将自动进入模式,从而最大限度地减少能源的浪费。 此外,Renesas通过采用先进的制造工艺和节能技术,进一步降了产品的。通过微小尺寸的晶体管和电源设计,Renesas能够提供高性能的处理能力,同时保持。 最后,Renesas的解决方案还具有良好的系统集成能力。通过整合不同的能单元和外围设备,Renesas可以减少设备的,并提高系统的整体性能。 总而言之,Renesas的产品和解决方案通过优化的电源管理、智能的切换模式、先进的制造工艺和系统集成能力,实现了高性能和长时间使用的平衡,为各种应用领域提供了可靠、高效的解决方案。这使得Renesas成为了全球领先的半导体供应商之一。 ### 回答2: Renesas技术是指Renesas电子公司在芯片设计和制造方面所采用的一系列技术,旨在降芯片的,从而提高设备的电池续航时间,并促进电子产品的智能化和便携性。 首先,Renesas采用了先进的工艺技术,如互补金属氧化物半导体(CMOS)工艺,该工艺具有、高效能的特点。这种工艺可减少电流泄漏和,提高集成电路的性能,从而降整体。 其次,Renesas优化了芯片架构和设计,采用了设计原则。通过精确控制电源电压和频率,使用高效的电源管理电路,最大限度地降。此外,Renesas还采用了率管理技术,如可变电压和频率技术,根据芯片的实际工作负载动态调整电压和频率,以降不必要的。 另外,为了进一步降,Renesas还优化了晶体管的设计和布局,采用了阻抗和电压操作的技术。这些技术可以降晶体管的开关和静态,提高芯片的效率。 最后,Renesas还提供了开发和优化工具,帮助客户在设计阶段准确评估芯片的,并进行优化。通过提供参考设计和示例代码等资源,Renesas帮助客户快速开发产品,加快上市时间。 总之,Renesas技术通过采用先进的工艺、优化芯片设计率管理和优化工具等手段,实现了芯片的开发和制造。这种技术不仅提高了电子设备的能效和续航时间,也促进了电子产品的智能化和便携性。 ### 回答3: Renesas 是指日本电子公司瑞萨电子(Renesas Electronics Corporation)所开发的技术。作为全球领先的半导体解决方案供应商之一,Renesas Electronics致力于开发能够提供高性能和的半导体产品。 Renesas技术有以下几个方面的特点和优势: 首先,Renesas采用了先进的设计技术和制造工艺,使得其半导体产品在工作时能够最大程度地降。这种技术可以有效地延长电池的续航时间,提高设备的使用效率。 其次,Renesas技术注重在休眠时的管理。在设备不工作时,Renesas的芯片能够进入模式,降待机,从而延长电池寿命。 另外,Renesas技术还包括对优化的软件算法和工具支持。通过使用这些算法和工具,开发人员能够更好地优化系统设计,最大限度地减少,提高系统性能。 最重要的是,Renesas技术广泛应用于各个领域,如智能手机、电子消费品、汽车电子、工业自动化等。通过在这些领域的广泛应用,Renesas技术已经在市场上得到了良好的反馈和认可。 总之,Renesas技术在降、延长电池寿命和提高系统性能方面具有显著优势。通过其先进的设计技术和制造工艺,Renesas Electronics已经成为解决方案的领先供应商之一。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值