|
|
  |
STM32F407IG6 и Keil, При создании проекта keil тянет за собой startup_stm32f4xx.s |
|
|
|
Jul 5 2012, 17:34
|
Профессионал
    
Группа: Свой
Сообщений: 1 719
Регистрация: 13-09-05
Из: Novosibirsk
Пользователь №: 8 528

|
.s лучше не трогать, там ничего править не нужно. Лучше скопируйте system_stm32f4xx.c к себе в папку с прочими исходниками, да и поправьте под свои нужды. У семейства f1xx можно было дефайнами выбрать разные варианты инициализации, видимо для f4xx это сложнее сделать, индусы не осилили  .
--------------------
Russia est omnis divisa in partes octo.
|
|
|
|
|
Jul 5 2012, 18:42
|
Знающий
   
Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725

|
Цитата(sidy @ Jul 5 2012, 16:39)  Если не подключать к проекту файл startup_stm32f4xx.s то keil ругается следующим образом: main.axf: Error: L6320W: Ignoring --entry command. Cannot find argument 'Reset_Handler'. main.axf: Warning: L6320W: Ignoring --first command. Cannot find argument '__Vectors'. Итак вопрос: поскольку я только начинаю пробовать STM32F407IG6 как мне произвести инициализацию системы тактирования. Т.е. я сперва хочу использовать только HSE - внешний кварц частотой 25 МГц, без PLL, затем в другом проекте или в этом же задействовать PLL и сконфигурировать его по своему усмотрению. Как уже ответили коллеги, не стОит отказываться от уже вылизанного startup*.s, который делает не что иное, как создает таблицу векторов, а самое главное - заполняет первые два слова начальным значением стека и стартовым адресом. Упомянутая ругня компоновщика об этом и говорит, как только startup*.s был выведен из проекта. Писать программы можно как угодно, но просто разумнее придерживаться стандартов. Например, CMSIS, который и описывает, как рекомендуется построить по крайней мере начальный код, чтобы добраться до main(). Если хочется сделать все своими руками, напишите свою функцию void Reset_Handler(void) и на нее будет передано управление сразу же после старта процессора (почему - смотрите, что такое слабое определение WEAK). Хотите остаться в рамках стандарта, но переопределить тактирование - прислушатесь к тому, что SSerge ответил.
Сообщение отредактировал KnightIgor - Jul 5 2012, 18:44
|
|
|
|
|
Jul 6 2012, 04:27
|
Частый гость
 
Группа: Свой
Сообщений: 152
Регистрация: 21-12-05
Из: Москва
Пользователь №: 12 476

|
Не вижу в чем проблема. Для F4 серии ST выложил специальный инструмент - эксель файл, который генерит system_stm32f4xx.c для любой частоты автоматически по указанным вами параметрам. Для работы с ним разрешите макросы в вашем экселе. Сгенерите необходимую вам частоту, скопируйте оттуда и разбирайтесь, если нужно менять частоту в программе. ИМХО, с примерами разбираться гораздо проще. Или сразу создайте файл который вам нужен и подцепите его в проект. Ссылка, смотрите AN3988
|
|
|
|
|
Jul 6 2012, 06:06
|

Гуру
     
Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095

|
QUOTE (topkin @ Jul 6 2012, 07:27)  Для F4 серии ST выложил специальный инструмент - эксель файл, Если бы ST еще догадался эксель для этого файла выложить... Там работы на два часа - прочитать описание PLL в руководстве пользователя и прямо по этому руководству прописать десяток регистров. Заодно будет понимание - как оно работает и как, в случае необходимости, перенастроить на лету. Что все носятся с этими стартапами как со священной коровой? Файл-то элементарный.
--------------------
На любой вопрос даю любой ответ"Write code that is guaranteed to work, not code that doesn’t seem to break" ( C++ FAQ)
|
|
|
|
|
Jul 10 2012, 12:53
|
Местный
  
Группа: Участник
Сообщений: 280
Регистрация: 2-11-08
Пользователь №: 41 333

|
Большое спасибо всем за рекомендации. Я продолжаю пробовать STM407IG6, а в частности на данный момент остановился на таймере Basic Timer TIM7, данный таймер имеет генерацию прерываний по переполнению. Я создал файл stm32f4xx_it.c в котором описал обработчик прерывания: Код void TIM7_IRQHandler (void) { unsigned int flag=0; if (flag==0) flag=1; }; В функции main я разрешил тактирование TIM7, разрешил update interrupt, разрешил счет, в регистре TIM7->ARR=0xFFFF. Но в обработчик прерывания по переполнению я не попадаю. Я предполагаю, что возможно нужно разрешить глобально все прерывания, но в многочисленной документации не нашел как это сделать.
|
|
|
|
|
Jul 10 2012, 20:08
|
Знающий
   
Группа: Участник
Сообщений: 643
Регистрация: 29-05-09
Из: Германия
Пользователь №: 49 725

|
Цитата(sidy @ Jul 10 2012, 14:53)  Большое спасибо всем за рекомендации. В функции main я разрешил тактирование TIM7, разрешил update interrupt, разрешил счет, в регистре TIM7->ARR=0xFFFF. Но в обработчик прерывания по переполнению я не попадаю. Я предполагаю, что возможно нужно разрешить глобально все прерывания, но в многочисленной документации не нашел как это сделать. Еще надо разрешить прерывание в NVIC: NVIC_EnableIRQ (TIM7_IRQn); Опционально: NVIC_SetPriority (TIM7_IRQn, myTIM7Priority); То есть, четыре пункта: - правильное имя обработчика прерывания (свериться с startup файлом) - разрешение соответствующих прерываний в самом устройстве TIM7 - разрешение прерывания по вектору в NVIC - глобальное разрешение прерывания P.S. только заметил в твоем коде: Код void TIM7_IRQHandler (void) { unsigned int flag=0; if (flag==0) flag=1; }; Переменная flag - локальная, не "видна" снаружи и исчезнет с выходом из прерывания. Уж если, то правильней: Код static unsigned int flag = 0; void TIM7_IRQHandler (void) {... если она должна быть видна лишь в рамках текущего модуля (файла *.c), либо: Код volatile unsigned int flag = 0; void TIM7_IRQHandler (void) {... и соответственно Код extern volatile unsigned int flag; в заголовочном файле, предоставляемом другим модулям.
Сообщение отредактировал KnightIgor - Jul 11 2012, 08:26
|
|
|
|
|
Jul 13 2012, 12:32
|
Местный
  
Группа: Участник
Сообщений: 280
Регистрация: 2-11-08
Пользователь №: 41 333

|
Спасибо, разобрался. На данный момент пробую периферийный модуль USART3. Привожу пример кода: Код int main (void) { RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE); //Разрешаем тактирование порта G GPIOG->MODER|=GPIO_MODER_MODER6_0; //PG6 output mode GPIO_WriteBit(GPIOG, GPIO_Pin_6, Bit_SET); //Зажигаем PG6 /****************************Инициализаций USART***************************/ RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3, ENABLE); //Разрешаем тактирование USART3 RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE); //Разрешаем тактирование порта С GPIO_PinAFConfig(GPIOC, GPIO_PinSource10, GPIO_AF_USART3); //Выбираем альтернативную функцию для USART3 TX PC10 GPIO_PinAFConfig(GPIOC, GPIO_PinSource11, GPIO_AF_USART3); //Выбираем альтернативную функцию для USART3 RX PC11 USART3->BRR=25000000/153600; //Скорость передачи USART3->CR2|=USART_CR2_STOP_1; //2 Стоп-бита USART3->CR1|=USART_CR1_RE | USART_CR1_TE | USART_CR1_UE; while(1){ USART3->DR=170; while((USART3->SR&USART_SR_TXE)==0){}; USART3->SR&=~USART_SR_TC; }; } Проблема заключается в следующем: смотрю в отладчике значение регистра USART3->DR, данное значение всегда=0 и на ножке USART3 tx всегда единица, т.е. передачи нет. И еще вопрос по поводу отладчика в Keil когда я ставлю точку останова в прерывании от TIM7 после строки i1=TIM7->CNT; То значение i1 в окне Watch1 i1=0; а значение TIM->CNT в View->System Viewer -> TIM7 совершенно произвольное - не совсем понятно с чем это связанно.
|
|
|
|
|
Jul 17 2012, 06:51
|
Частый гость
 
Группа: Свой
Сообщений: 112
Регистрация: 1-05-09
Из: Ростов-на-Дону
Пользователь №: 48 518

|
Цитата(sidy @ Jul 13 2012, 16:32)  Код int main (void) { while(1){ USART3->DR=170; while((USART3->SR&USART_SR_TXE)==0){}; USART3->SR&=~USART_SR_TC; }; } По идее очистка флага TC в данном случае не обязательна, т.к выполняется последовательность чтения из SR и записи в DR. В этом случае TC сбрасывается сам. Учтите, что TXE показывает состояние DR, а не завершение передачи. Вообще правильно ли настроена скорость UART'а? Цитата(sidy @ Jul 13 2012, 16:32)  Проблема заключается в следующем: смотрю в отладчике значение регистра USART3->DR, данное значение всегда=0 и на ножке USART3 tx всегда единица, т.е. передачи нет. Ножку tx чем смотрите? Осциллографом надеюсь? Цитата(sidy @ Jul 13 2012, 16:32)  И еще вопрос по поводу отладчика в Keil когда я ставлю точку останова в прерывании от TIM7 после строки i1=TIM7->CNT; То значение i1 в окне Watch1 i1=0; а значение TIM->CNT в View->System Viewer -> TIM7 совершенно произвольное - не совсем понятно с чем это связанно. Оно не произвольное, просто когда вы останавливаетесь на любой строчке кода в отладке, переферия продолжает работать, приостанавливается только выполнение кода. Соответственно таймер продолжает считать. Да и все окна в keil'e (local, watch, memory.....) обновляются с периодом ~1 сек. По это и получаются разные значения в CNT. Кстати по этой же причине можете и не увидеть дерганье ножкой TX через отладчик.
Сообщение отредактировал PoReX - Jul 17 2012, 06:51
--------------------
«У современных мобильных телефонов такая же вычислительная мощь, что и у компьютеров NASA в 60-е годы. И в то время этого хватало, чтобы запустить человека в космос, а сегодня — только чтобы запускать птиц в свиней.»
|
|
|
|
|
Jul 17 2012, 15:37
|
Местный
  
Группа: Участник
Сообщений: 280
Регистрация: 2-11-08
Пользователь №: 41 333

|
Сейчас поправил: USART3->BRR=0x0A2C; //9600 while(1){ USART3->DR=170; while((USART3->SR&USART_SR_TC)==0){}; USART3->SR&=~USART_SR_TC; }; Но изменений никаких нет. На ТХ постоянно единица. Цитата(PoReX @ Jul 17 2012, 10:51) Ножку tx чем смотрите? Осциллографом надеюсь? Ножку TX смотрю осциллографом.
Сообщение отредактировал sidy - Jul 17 2012, 15:38
|
|
|
|
|
  |
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|