PROGCONT.RU

Форма входа







Регистрация Вход/

Пример Пример Пример


STM8S Clock (тактирование).

 Что такое генератор тактовых импульсов(clock)?
 Это своего рода сердце любого контролера, которое заставляет работать CPU(ядро) и периферию(вспомогательные модули) и конечно скорость работы контролера зависит от частоты генератора, чем больше частота тем быстрей работает контролер. В данных контролерах, можно использовать три вида генератора: внешний HSE(высокочастотный) и два внутренних HSI(высокочастотный), LSI(низкочастотный). Ниже схема как устроено тактирование CPU и периферии.

нет рисунка

 Выбор и подключение к источнику тактирования.

 Изначально как мы знаем(если не знаем, смотрите ниже в HSI) тактирование происходит от внутреннего генератора для того что бы переключить наш контролер на другой источник тактирования мы будем использовать следующую функцию.


CLK_ClockSwitchConfig( CLK_SwitchMode, CLK_NewClock, ITState, CLK_CurrentClockState);

CLK_SwitchMode-как мы собираемся переключаться на другой генератор, в автоматическом(контролер сам после стабилизации нового генератора переходит на него) или ручном(по идее мы должны проверить флаг стабилизации нового генератора или в прерывании сами перейти на новый источник но это не хрена не работает, функция ожидает перехода и только потом продолжается выполнятся программный код) режиме.
Варианты:
   CLK_SWITCHMODE_AUTO-автоматический
   CLK_SWITCHMODE_MANUAL-ручной
CLK_NewClock-Источники тактирования.
   CLK_SOURCE_HSE-внешний
   CLK_SOURCE_HSI-встроенный высокочастотный
   CLK_SOURCE_LSI-встроенный низкочастотный
ITState-включаем или не включаем прерывание от стабилизации частоты
   ENABLE- включаем
   DISABLE-не включаем
CLK_CurrentClockState-включить или не включать новый генератор
   CLK_CURRENTCLOCKSTATE_ENABLE-сразу включить
   CLK_CURRENTCLOCKSTATE_DISABLE-включить потом


 Пример использования этой функции, переключаемся на внешний генератор.

   CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSE, DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
//Отключаем HSI экономим питание.
   CLK_HSICmd(DISABLE);

  Чтобы отловить переключение нужно немного изменить функцию, включить прерывание и вставить свой обработчик в файле(stm8s_it.c) векторов прерывания, как на примере ниже с HSE.

//С сбрасываем флаг прерывания на всякий случай.
   CLK_ClearITPendingBit(CLK_IT_SWIF);
//Включаем прерывание.
   enableInterrupts();
//Меняем DISABLE на ENABLE.
   CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSE, ENABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
//Отключаем HSI экономим питание.
   CLK_HSICmd(DISABLE);

  В файле(stm8s_it.c) векторов прерывания вписываем наш обработчик.

нет рисунка

 Пример с миганием светодиода, обращаю внимание на LSI что бы заработал нужно изменить LSI_EN OPT BIT(Как? Читайте ниже LSI (Low Speed Internal)-Встроенный низкочастотный генератор.).

 #include "stm8s.h"
 void pause(uint32_t p);
int main( void )
 {
 //Частота по умолчанию
   GPIO_Init(GPIOD, GPIO_PIN_0, GPIO_MODE_OUT_OD_LOW_FAST);
   for( uint32_t q=0; q<5;q++){
      GPIO_WriteHigh(GPIOD, GPIO_PIN_0);
      pause(10000);
      GPIO_WriteLow(GPIOD, GPIO_PIN_0);
      pause(10000);
   }
while(1){
 //Тактируемся от LSI
 CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_LSI, DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
 CLK_HSECmd(DISABLE);
 CLK_HSICmd(DISABLE);
    for( uint32_t q=0; q<5;q++){
      GPIO_WriteHigh(GPIOD, GPIO_PIN_0);
      pause(10000);
      GPIO_WriteLow(GPIOD, GPIO_PIN_0);
      pause(10000);
   }
 //Тактируемся от HSI делитель 4
 CLK_HSIPrescalerConfig(CLK_PRESCALER_HSIDIV4);
 CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSI, DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
 CLK_HSECmd(DISABLE);
 CLK_LSICmd(DISABLE);
   for( uint32_t q=0; q<5;q++){
      GPIO_WriteHigh(GPIOD, GPIO_PIN_0);
      pause(10000);
      GPIO_WriteLow(GPIOD, GPIO_PIN_0);
      pause(10000);
   }
 //Тактируемся от HSE
CLK_ClockSwitchConfig(CLK_SWITCHMODE_AUTO, CLK_SOURCE_HSE, DISABLE, CLK_CURRENTCLOCKSTATE_ENABLE);
 CLK_HSICmd(DISABLE);
 CLK_LSICmd(DISABLE);
   for( uint32_t q=0; q<5;q++){
      GPIO_WriteHigh(GPIOD, GPIO_PIN_0);
      pause(10000);
      GPIO_WriteLow(GPIOD, GPIO_PIN_0);
      pause(10000);
   }
}
return 0;
}
void pause(uint32_t p){
for(uint32_t i=0; i<p; i++){}
}
#ifdef USE_FULL_ASSERT
void assert_failed(uint8_t* file, uint32_t line)
{
while (1){}
}
#endif

 Давайте посмотрим, что из себя представляют эти HSI, HSE, LSI и для чего они:


 HSI (High Speed Internal)-Встроенный высокочастотный или главный генератор.

 Разработчики что бы упростить нам жизнь встроили в контролер HSI генератор 16Мгерц, контролер всегда начинает работать на нем да, кстати, только у этого генератора есть свой пост делитель(HSIDIV[1:0]) в который установлено значение 8 контролер по умолчанию будет работать на частоте 2Мгерц.
 Что бы перенастроить частоту на 16Мгерц нужно выполнить не сложную операцию.

 CLK_HSIPrescalerConfig(CLK_PRESCALER_HSIDIV1);

Все значения:
   CLK_PRESCALER_HSIDIV1
   CLK_PRESCALER_HSIDIV2
   CLK_PRESCALER_HSIDIV4
   CLK_PRESCALER_HSIDIV8

 Зразу о этом генераторе, он довольно не плохой, рекомендую его использовать постоянно если нет необходимости точных измерений и передачи информации на больших скоростях например UART 115200(иногда из за температуры плавает частота и теряются данные), для этих целей используйте внешний кварцевый резонатор или понижайте скорость передачи.
 Можно калибровать этот генератор следующий функцией, как оно будет влиять на работу, наверное, на увеличение частоты точно не знаю, пробуйте, после сброса значение будет CLK_HSITRIMVALUE_0.

 CLK_AdjustHSICalibrationValue( CLK_HSICalibrationValue);

 CLK_HSICalibrationValue-все значения:
   CLK_HSITRIMVALUE_0
   CLK_HSITRIMVALUE_1
   CLK_HSITRIMVALUE_2
   CLK_HSITRIMVALUE_3
   CLK_HSITRIMVALUE_4
   CLK_HSITRIMVALUE_5
   CLK_HSITRIMVALUE_6
   CLK_HSITRIMVALUE_7

 HSE (High Speed Extrenal)-Внешний высокочастотный или кварцевый генератор.

 Схема подключения.

нет рисунка

 Более точный и стабильный чем остальные, используйте кварц на 16Мгерц или придется править файл #include "stm8s.h". Переключатся на него нужно в самом начале вашей программы, потому что если вы например выполните сначала настройку UART а потом переключите на внешний генератор то компилятор не правильно рассчитает параметры для настройки скорости соединения.

 В случае поломки или повреждения соединения с генератором тактирование прекращается и контролер зависает, для таких ситуаций у контролера есть защита называется она CSS. Работает она следующим образом, когда модуль обнаруживает проблемы с тактированием он переключает контролер на внутренний генератор HSI и устанавливает его стартовые настройки, то есть пред делитель 8, повторно переключится на внешний генератор уже не получится, только после сброса. Что бы её включить используйте функцию, выключается только после сброса.

   CLK_ClockSecuritySystemEnable();

 Если ещё необходимо отловить момент отказа HSE, просто включаем прерывание от модуля CSS следующим образом:

//С сбрасываем флаг прерывания на всякий случай.
   CLK_ClearITPendingBit(CLK_IT_CSSD);
//Бодключаем прерывание от CSS.
   CLK_ITConfig(CLK_IT_CSSD, ENABLE);
//Включаем прерывание.
   enableInterrupts();

 В файле(stm8s_it.c) векторов прерывания вписываем наш обработчик.

нет рисунка


 LSI (Low Speed Internal)-Встроенный низкочастотный генератор.

 В основном он используется для тактирования watchdog, некоторой периферии или для энергосберегающего режима, так как частота его 128kHz.Что бы его подключить для тактирования CPU мало использовать выше упомянутую функцию, еще необходимо установить бит- LSI_EN OPT BIT(или по старому править фьюзы), в IAR нажимаем на ST-LINK(вверху компилятора) выбираем Options Bytes… правим LSI_EN на Enable. Используется редко поэтому не будем заострять на нем внимание.


 PERIPHERAL CLOCK-Включение тактирование периферии.

 Тактирование скорей надо будет отключать ради экономии, потому что у контролеров STM8S по умолчанию тактирование всей периферии включено. Выберите нужную периферию в зависимости от вашего контролера, включить вставьте ENABLE или отключить DISABLE как в примере ниже UART1.

 CLK_PeripheralClockConfig( CLK_PERIPHERAL_UART1, ENABLE);

 Список периферии, зависит от вашего контролера(смотрите Datasheet).
   CLK_PERIPHERAL_I2C
   CLK_PERIPHERAL_SPI
   CLK_PERIPHERAL_UART1
   CLK_PERIPHERAL_UART1
   CLK_PERIPHERAL_UART2
   CLK_PERIPHERAL_UART3
   CLK_PERIPHERAL_TIMER6
   CLK_PERIPHERAL_TIMER4
   CLK_PERIPHERAL_TIMER5
   CLK_PERIPHERAL_TIMER2
   CLK_PERIPHERAL_TIMER3
   CLK_PERIPHERAL_TIMER1
   CLK_PERIPHERAL_AWU
   CLK_PERIPHERAL_ADC
   CLK_PERIPHERAL_CAN


 CPU DIV-пред делитель CPU.

 Замедляет контролер(CPU), реальная частота будет fMASTER деленый на значение, ниже пример и список всех значений.

 CLK_SYSCLKConfig( CLK_Prescaler);

 CLK_Prescaler-все значения:
   CLK_PRESCALER_CPUDIV1
   CLK_PRESCALER_CPUDIV2
   CLK_PRESCALER_CPUDIV4
   CLK_PRESCALER_CPUDIV8
   CLK_PRESCALER_CPUDIV16
   CLK_PRESCALER_CPUDIV32
   CLK_PRESCALER_CPUDIV64
   CLK_PRESCALER_CPUDIV128


 CCO-Тактирование дополнительных устройств.

 Данный выход (Pin) предназначен для тактирования внешних устройств (например, дополнительную микросхему) от нашего контролера, источником может быть, например HSI, ниже пример подключения и список всех источников.

 CLK_CCOConfig( CLK_CCO);

 CLK_CCO-все значения:
   CLK_OUTPUT_HSI
   CLK_OUTPUT_LSI
   CLK_OUTPUT_HSE
   CLK_OUTPUT_CPU
   CLK_OUTPUT_CPUDIV2
   CLK_OUTPUT_CPUDIV4
   CLK_OUTPUT_CPUDIV8
   CLK_OUTPUT_CPUDIV16
   CLK_OUTPUT_CPUDIV32
   CLK_OUTPUT_CPUDIV64
   CLK_OUTPUT_HSIRC
   CLK_OUTPUT_MASTER
   CLK_OUTPUT_OTHERS

 После выполнения функции, выбранный источник нельзя будет отключить.


Комментариев нет  Только зарегистрированные пользователи могут оставлять комментарии!