2016-10-27 158 views
3

NUCLEO-L053R8開發板上的STM32L053R8開發板。HAL_RCC_OscConfig時間太長(appx 170μS),從STOP喚醒時需要<50μS

我們有一個每200微秒左右從睡眠中「醒來」的系統,然後再進入少量工作(睡眠模式)。 理想情況下,我想在50μS以內從STOP喚醒。 HAL_RCC_OscConfig()函數花費大約170μS,這使得這種努力毫無意義。

從我所看到的大部分時間都花費在PLL配置上,特別是跟隨PLL重新啓用(約98μS)的while循環(「等到PLL準備就緒」)。

/* Configure the main PLL clock source, multiplication and division factors. */ 
__HAL_RCC_PLL_CONFIG(RCC_OscInitStruct->PLL.PLLSource, 
        RCC_OscInitStruct->PLL.PLLMUL, 
        RCC_OscInitStruct->PLL.PLLDIV); 
/* Enable the main PLL. */ 
__HAL_RCC_PLL_ENABLE(); 

/* Get timeout */ 
tickstart = HAL_GetTick(); 

/* Wait till PLL is ready */ 
while(__HAL_RCC_GET_FLAG(RCC_FLAG_PLLRDY) == RESET) 
{ 
    if((HAL_GetTick() - tickstart) > RCC_PLL_TIMEOUT_VALUE) 
    { 
    return HAL_TIMEOUT; 
    }  
} 

是否有任何方法可以從STOP模式中喚醒並在50μS以下恢復到全速HSI? 什麼是從STOP喚醒時設置時鐘的最有效方法?

目前我使用在PWR_STOP例子是如下規定的方法:其構成的時鐘,幷包括在此HAL_RCC_OscConfig(&RCC_OscInitStruct)長延遲

/* Enter Stop Mode */ 
HAL_PWR_EnterSTOPMode(PWR_LOWPOWERREGULATOR_ON, PWR_STOPENTRY_WFI); 

/* Stop interrupt that woke us up */ 
int ret = HAL_LPTIM_TimeOut_Stop_IT(&LptimHandle); 
SystemDisableWakeupCounter(); 

/* Configures system clock after wake-up from STOP: enable HSI, PLL and select 
PLL as system clock source (HSI and PLL are disabled automatically in STOP mode) */ 
SystemClockConfig_STOP(); 

依次SystemClockConfig_STOP()調用調用SystemClock_Config()。

非常感謝您提供任何援助。

+0

你是什麼PLL的來源? –

+0

PLLSource是RCC_PLLSOURCE_HSI – PsyUk

回答

1

我不知道你的PLL信號源是什麼,但推薦使用HSI16。全部來自reference manual

HSI16時鐘信號由內部16 MHz RC振盪器產生。它可以直接用作系統時鐘或PLL輸入。

HSI16時鐘可以在從低功耗模式 模式喚醒後使用,這可以確保比使用MSI 時鐘喚醒更短的喚醒時間。


如果你能允許稍微高消費,不禁止內部穩壓器。這是一個妥協:更快的喚醒與更高的消費或更慢,同時節省更多的能源,決定哪一個更重要。

當通過發出一箇中斷或喚醒事件退出停機方式, MSI或HSI16 RC振盪器被選作根據在RCC_CFGR寄存器中的位 STOPWUCK系統時鐘。

當電壓調節器 以低功耗模式工作時,從停止模式喚醒時會產生額外的啓動延遲 。通過在停止模式期間保持內部穩壓器開啓 ,儘管啓動時間 減少,但消耗量更高。


現在我想使用PLL是必須的,但後來恐怕除了上面提到的,你不能做的確實不多的啓動時間。 PLL需要一定的時間來鎖定輸入參考時鐘頻率。但首先輸入頻率必須穩定(這就是爲什麼建議使用HSI16)。

而不是阻塞等待(while循環),您可以使用中斷。

如果在RCC_CIER寄存器 (參見第7.3.5節)中使能PLL,則PLL可以生成中斷。

雖然PLL鎖定,您可以在16 MHz上執行一些任務,並且在接收到中斷(在ISR中完成時鐘配置)時可以啓動需要全速的任務。

+1

感謝您的詳細信息。 我已經設置了RCC_CFGR_STOPWUCK,但是我修改了喚醒功能,沒有設置PLL: RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI; RCC_OscInitStruct.HSEState = RCC_HSE_OFF; RCC_OscInitStruct.HSIState = RCC_HSI_ON; RCC_OscInitStruct.PLL.PLLState = RCC_PLL_NONE; RCC_OscInitStruct.HSICalibrationValue = 0x10; 這在〜6uS醒了。 然後,我可以設置所需的GPIO,然後完全喚醒(約160uS)並繼續執行核心任務。 – PsyUk

+0

re:「如果在RCC_CIER寄存器中使能了PLL,就可以產生中斷」 您是否有這方面的一個方便的例子? 我啓用了中斷,然後在systick關閉的情況下進入睡眠模式。 __HAL_RCC_ENABLE_IT(RCC_IT_PLLRDY); SysTick-> CTRL = 0; HAL_PWR_EnterSLEEPMode(PWR_MAINREGULATOR_ON,PWR_STOPENTRY_WFI); 但我沒有看到觸發的事件。 它是否必須以某種方式與EXTI鏈接? 如果我添加一個循環檢查PLLRDY,而不是在睡眠中等待,那麼我可以看到該標誌已設置。 \t \t 我錯過了什麼? – PsyUk

+0

@PsyUk我還沒有使用過這個功能,只是從我引用的參考手冊中知道它。我現在無法查看它,但稍後會檢查它。 –

2

好吧,datasheet表示PLL鎖定可能需要160μs,所以只要您嘗試使用PLL,延遲就會在那裏。

enter image description here

你需要PLL呢?

您可以將RCC配置爲在已經以16 MHz運行的HSI中喚醒(請參閱RCC_CFGR_STOPWUCK位)。你只有一半的速度,但它已經開始並且在6點運行。

+0

感謝您的參考。我確實需要PLL,RCC_CFGR_STOPWUCK已經設置好了。將PLLState設置爲無可提供更快的喚醒,並在完成必要的任務後,將PLL狀態設置爲開。 – PsyUk