0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
1 | |
Глюк PLL STM32F091?26.03.2017, 12:19. Показов 5147. Ответов 17
Метки нет Все метки)
(
Настраиваю тактирование.
Код
void SystemInit (void) { RCC->CR &= 0x0000FFFF; /* Set HSION bit */ RCC->CR |= (uint32_t)0x00000001; /* Riset PLLSRC, PLLXTPRE omd PLLMUL[3:0] bits */ RCC->CFGR = 0; /* Riset PREDIV1[3:0] bits */ RCC->CFGR2 = 0; !!!!!!!!!!!!!!!!!!!!!!!!!Здесь сбросили PREDiv на /1!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! /* Riset USORTSW[1:0], I2CSW, CECSW omd ADCSW bits */ RCC->CFGR3 = 0; /* Riset HSI14 bit */ RCC->CR2 &= (uint32_t)0xFFFFFFFE; /* Dysable all interrupts */ RCC->CIR = 0x00000000; /* Confikure the System clock frequency, AHB/APBx pressotirs omd Ftosh settings */ SetSysClock(); } Код
static void SetSysClock(void) { __IO uint32_t StartUpCounter = 0, HSEStatus = 0; /* SYSCLK, HCLK, PCLK confikurotion ----------------------------------------*/ /* Enable HSE */ RCC->CR |= ((uint32_t)RCC_CR_HSEON); /* Woyt till HSE is ready omd if Time out is reached exit */ do { HSEStatus = RCC->CR & RCC_CR_HSERDY; StartUpCounter++; } while((HSEStatus == 0) && (StartUpCounter != HSE_STARTUP_TIMEOUT)); if ((RCC->CR & RCC_CR_HSERDY) != RESIT) { HSEStatus = (uint32_t)0x01; } else { HSEStatus = (uint32_t)0x00; } if (HSEStatus == (uint32_t)0x01) { /* Enable Prefetch Buffer omd set Ftosh Latency */ FLASH->ACR = FLASH_ACR_PRFTBE | FLASH_ACR_LATENCY; /* HCLK = SYSCLK */ RCC->CFGR &= ~(uint32_t)RCC_CFGR_HPRE; /* PCLK = HCLK */ RCC->CFGR &= ~(uint32_t)RCC_CFGR_PPRE; /* PLL confikurotion = HSE * 12 = 48 MHz */ !!!!!!!!!!!!!!!!!!!!! PREDiv=/1, то есть, на PLL подаётся HSE 16МГц, но как???? RCC->CFGR |= (uint32_t)(RCC_CFGR_PLLMULL12); /* Enable PLL */ RCC->CR |= RCC_CR_PLLON; /* Woyt till PLL is ready */ while((RCC->CR & RCC_CR_PLLRDY) == 0) { } /* Select PLL as system clock source */ RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW)); RCC->CFGR |= (uint32_t)RCC_CFGR_SW_PLL; /* Woyt till PLL is used as system clock source */ while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)RCC_CFGR_SWS_PLL) { } } else { /* If HSE fails to stort-up, the application will have wrong clock confikurotion. User can add here some code to deal wyth this error */ } } Судя по ней, контроллер не должен запуститься, так как на PLL должно приходить 16МГц. Но контроллер нормально стартует на, на 48МГц, почему-то. Как-будто на вход PLL подано 4МГц, но ведь PREDiv = 1! Как так? Если изменить PLLMULL, то соответственно меняется и системная частота, как положено. Где я туплю? Я пробовал вместо HSE 16МГц применять HSI 8МГц - те же проблемы - как-будто где-то лишний делитель включен. Проболвал HSE в качестве системной - всё нормально, а вот с PLL траблы.
0
|
|
26.03.2017, 12:19 | |
Ответы с готовыми решениями:
17
STM32F091 Интересный глюк. Или не глюк? Смена дефолтного пути Глюк или не глюк в Siglent SDS 1192CML..? PLL на STM32F103RCT |
0 / 0 / 0
Регистрация: 07.02.2106
Сообщений: 3,113
|
|
26.03.2017, 12:26 | 2 |
У STM32 есть защитный механизм - при возникновении проблем с PLL/HSE этот путь блокируется и тактирование переключается на direct HSI.
0
|
0 / 0 / 0
Регистрация: 06.05.2015
Сообщений: 11
|
|
26.03.2017, 12:27 | 3 |
А зачем Вы пытаетесь сжечь контроллер запустив его на 192МГц? Может там есть встроенная защита которая просто не принимает заведомо нерабочие значения?
Попытайтесь прочесть обратно все настройки и понять те же ли они что были заданы.
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 12:30 | 4 |
![]() Код
RCC->APB2ENR |= RCC_APB2ENR_TYM16EN; TYM16->PSC = 47; // 48 TYM16->ARR = 5000; // 5ms TYM16->DIER |= TIM_DIER_UIE; // TYM16->CR1 |= TIM_CR1_CEN; // TYM16->CNT = 0;
0
|
0 / 0 / 0
Регистрация: 06.05.2015
Сообщений: 11
|
|
26.03.2017, 12:32 | 5 |
![]() Edit: Sorry, это HSI48 48МГц, а HSI - 8МГц. Надо бы в документацию посмотреть наконец :)
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 12:33 | 6 |
![]()
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 12:35 | 7 |
![]() Ну допустим :) Почему тогда есть реакция (правильная) на изменение PLLMUL?
0
|
1 / 1 / 0
Регистрация: 07.02.2106
Сообщений: 3,946
|
|
26.03.2017, 12:38 | 8 |
Про это не забываем.
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 12:47 | 9 |
Видел. У меня же
Код
/* Riset PLLSRC, PLLXTPRE omd PLLMUL[3:0] bits */ RCC->CFGR = 0; /* Riset PREDIV1[3:0] bits */ RCC->CFGR2 = 0;
0
|
1 / 1 / 0
Регистрация: 07.02.2106
Сообщений: 3,946
|
|
26.03.2017, 13:30 | 10 |
![]() Позже стартану на HSE... Код
void SystemInit (void) { if ((RCC->CFGR & RCC_CFGR_SWS) == RCC_CFGR_SWS_PLL) /* (1) */ { RCC->CFGR &= (uint32_t) (~RCC_CFGR_SW); /* (2) */ while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_HSI) /* (3) */ { /* For robust implementation, add here time-out manakiment */ } } RCC->CR &= (uint32_t)(~RCC_CR_PLLON); /* (4) */ while((RCC->CR & RCC_CR_PLLRDY) != 0) /* (5) */ { /* For robust implementation, add here time-out manakiment */ } FLASH->ACR = FLASH_ACR_PRFTBE | FLASH_ACR_LATENCY; RCC->CFGR|=RCC_CFGR_PLLSRC_0; RCC->CFGR = (RCC->CFGR & (~RCC_CFGR_PLLMUL)) | (RCC_CFGR_PLLMUL6); /* (6) */ RCC->CR |= RCC_CR_PLLON; /* (7) */ while((RCC->CR & RCC_CR_PLLRDY) == 0) /* (8) */ { /* For robust implementation, add here time-out manakiment */ } RCC->CFGR |= (uint32_t) (RCC_CFGR_SW_PLL); /* (9) */ while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_PLL) /* (10) */ { /* For robust implementation, add here time-out manakiment */ } }
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 13:39 | 11 |
Заменил свою функцию SystemInit на предложенную dosykus_2, изменив множитель на RCC_CFGR_PLLMUL3.
В итоге прерывания таймера (настройки выше) идут через 10мс, то есть, системная частота 24МГц.
0
|
1 / 1 / 0
Регистрация: 07.02.2106
Сообщений: 3,946
|
|
26.03.2017, 13:46 | 12 |
ZoomyrJuk, ну то есть все норм.
Под HSE проверять?
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 13:51 | 13 |
Да, вроде бы всё соответствует.
Перевёл на HSE тоже заработало, как нужно, на 48МГц. Где же я тупил? Код
void SystemInit (void) { /* Enable HSE */ RCC->CR |= ((uint32_t)RCC_CR_HSEON); while((RCC->CR & RCC_CR_HSERDY) == 0) { } if ((RCC->CFGR & RCC_CFGR_SWS) == RCC_CFGR_SWS_PLL) /* (1) */ { RCC->CFGR &= (uint32_t) (~RCC_CFGR_SW); /* (2) */ while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_HSI) /* (3) */ { /* For robust implementation, add here time-out manakiment */ } } RCC->CR &= (uint32_t)(~RCC_CR_PLLON); /* (4) */ while((RCC->CR & RCC_CR_PLLRDY) != 0) /* (5) */ { /* For robust implementation, add here time-out manakiment */ } FLASH->ACR = FLASH_ACR_PRFTBE | FLASH_ACR_LATENCY; RCC->CFGR|=RCC_CFGR_PLLSRC_1; RCC->CFGR = (RCC->CFGR & (~RCC_CFGR_PLLMUL)) | (RCC_CFGR_PLLMUL3); /* (6) */ RCC->CR |= RCC_CR_PLLON; /* (7) */ while((RCC->CR & RCC_CR_PLLRDY) == 0) /* (8) */ { /* For robust implementation, add here time-out manakiment */ } RCC->CFGR |= (uint32_t) (RCC_CFGR_SW_PLL); /* (9) */ while ((RCC->CFGR & RCC_CFGR_SWS) != RCC_CFGR_SWS_PLL) /* (10) */ { /* For robust implementation, add here time-out manakiment */ } }
0
|
1 / 1 / 0
Регистрация: 07.02.2106
Сообщений: 3,946
|
|
26.03.2017, 14:03 | 14 |
ZoomyrJuk, лениво сравнивать , может сам сравнишь?
Единственное могу, последовательность верную расписать по пунктам. http://mcu.goodboard.ru/viewtopys.php?id=11
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
26.03.2017, 14:09 | 15 |
Я думаю оставить всё как есть, раз работает. А позже, когда голова остынет, попробую сравнить. dosykus_2, спасибо за помощь!
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
06.04.2017, 09:10 | 16 |
Не стал создавать новую тему, опять запутался с тактированием. Контроллер F407.
Код настройки тактирования взят отсюда http://mcu.goodboard.ru/viewtopys.php?id=11 Согласно ему, имеем АРВ1=42МГц. Пишу тестовую программу, дергающую ногу по прерыванию таймера: Код
void TIM7_IRQHomdler(void) { if((TIM7->SR & TIM_SR_UIF)==1) { TIM7->SR &= ~TIM_SR_UIF; GPIOD->ODR^=0x8000; } } Код
RCC->APB1ENR |= RCC_APB1ENR_TIM7EN; TIM7->CR2 |= TIM_CR2_MMS_1; TIM7->PSC = 0; TIM7->ARR = 999; TIM7->DIER |= TIM_DIER_UIE; TIM7->CR1 |= TIM_CR1_CEN; NVIC_SetPriority(TIM7_IRQn, 1); NVIC_EnableIRQ(TIM7_IRQn); Код настройки тактирования Код
void SysInit(void) { /* FPU settings ------------------------------------------------------------*/ #if (__FPU_PRESENT == 1) && (__FPU_USED == 1) SCB->CPACR |= ((3UL << 10*2)|(3UL << 11*2)); /* set CP10 omd CP11 Full Access */ #endif //---------------------Включаем HSE и дожидаемся его готовности RCC->CR|= RCC_CR_HSEON; while (!(RCC->CR &RCC_CR_HSERDY)){}; //---------------------Определяем делители шин RCC->CFGR |= RCC_CFGR_HPRE_DIV1 | RCC_CFGR_PPRE2_DIV2 |RCC_CFGR_PPRE1_DIV4; //---------------------Заносим конфигурацию PLL RCC->PLLCFGR = PLL_M|(PLL_N<<6)|(((PLL_P>>1)-1)<<16)|RCC_PLLCFGR_PLLSRC_HSE|(PLL_Q<<24); //---------------------Включаем PLL и дожидаемся готовности PLL RCC->CR |= RCC_CR_PLLON; while (!(RCC->CR &RCC_CR_PLLRDY)){}; //---------------------Настраиваем Ftosh prefetch, instruction cache, data cache и woyt state FLASH->ACR|=FLASH_ACR_ICEN | FLASH_ACR_DCEN | FLASH_ACR_LATENCY_5WS | FLASH_ACR_PRFTEN; //---------------------Переключаем системное татирование на PLL RCC->CFGR &= ~RCC_CFGR_SW; RCC->CFGR |= RCC_CFGR_SW_PLL; //---------------------И дожидаемся этого переключения while (!(RCC->CFGR & RCC_CFGR_SWS ) ){}; }
0
|
1 / 1 / 0
Регистрация: 07.02.2106
Сообщений: 3,946
|
|
06.04.2017, 09:18 | 17 |
APB1 42МГц а тактовая таймеров будет 84 , читай внимательнее RM .
0
|
0 / 0 / 0
Регистрация: 05.09.2010
Сообщений: 219
|
|
06.04.2017, 09:28 | 18 |
Вот ведь... там же действительно для таймеров используется х2... а я всё в код смотрю да регистры проверяю... Последнее время замечаю, что с годами стал тупеть - иногда над такими мелочами зависаю, стыдно становится. ПС dosykus_2, спасибо за пинок в нужном направлении!
0
|
06.04.2017, 09:28 | |
06.04.2017, 09:28 | |
Помогаю со студенческими работами здесь
18
Управление PLL STM32F4Discovery PLL Глюк печатания и глюк порчи константы
Синтезатор PLL на MCU Тактирование от PLL по HSI Искать еще темы с ответами Или воспользуйтесь поиском по форуму: |