|
Непонятные действия оптимизации. |
|
|
|
Dec 22 2008, 11:01
|
Знающий
   
Группа: Свой
Сообщений: 922
Регистрация: 3-06-05
Из: Москва
Пользователь №: 5 709

|
Начал проект с простого (WinAVR-20070525), таймер и исключающее ИЛИ пина порта (PORTA) в обработчике прерывания этого самого таймера. На выходе ожидался генератор меандра. Загрузил, не работает. После некоторых мук определил, что виновата оптимизация, собираю проект без оптимизации всё работает. Немного расширил проект, стал работать и с оптимизацией, но всё равно некоторые важные части оптимизирует на свой лад. Я понимаю соптимизировать переменную, которая ничего кроме инвертирования не делает, но выкидывание работы с портом, этого я не понимаю. Может я и правда чего не понимаю.
|
|
|
|
|
 |
Ответов
|
Dec 22 2008, 12:54
|
Знающий
   
Группа: Свой
Сообщений: 922
Регистрация: 3-06-05
Из: Москва
Пользователь №: 5 709

|
Я переменными для начала не пользовался и volatile мне не к чему. А на порт volatile ставить… В АСМе порты программировать можно, но если проект на Си, то и с портами желательно в Си работать. Простенький код Код ISR (TIMER0_COMP_vect) { TCNT0 = 0x00; PORTA ^= 1; }
int main(void) { TCCR0 = (1 << CS00); TCNT0 = 0x00; OCR0 = Dl; TIMSK |= (1 << OCIE0);
DDRA = 0xFF; PORTA = 0xFF;
sei();
while (1) { } return 0; }
|
|
|
|
|
Dec 22 2008, 16:35
|
Знающий
   
Группа: Свой
Сообщений: 922
Регистрация: 3-06-05
Из: Москва
Пользователь №: 5 709

|
Цитата(_Pasha @ Dec 22 2008, 16:13)  Уважаемый, никакой Си не избавит Вас от необходимости курить мануал и думать головой.  Каким макаком у Вас будет прерывание, если Вы не потрудились даже настроить таймер на работу с OCR0??? Уважаемый, я Вас не понял. Где тут ошибка??? В регистр TCCR0 устанавливаю бит CS00, который clkI/O/(No prescaling). Не отметил, МК ATMetga32. Я же говорю, без оптимизации все работает!!! Вочдог не использую и фьюз не стоит. Цитата(demiurg_spb @ Dec 22 2008, 16:28)  Пожалуйста форматируйте код в постах (есть волшебная кнопка # над окном ввода текста сообщения). Спасибо, учту. Цитата(defunct @ Dec 22 2008, 16:42)  Ваша программа работает одинаково, как с оптимизацией, так и без нее. Уточняйте, где смотреть проблему? Увы не одинаково и не стабильно. Без оптимизации всё нормально, с –Os и до –O1 чудеса.
|
|
|
|
|
Dec 22 2008, 18:50
|
Знающий
   
Группа: Свой
Сообщений: 922
Регистрация: 3-06-05
Из: Москва
Пользователь №: 5 709

|
Цитата(defunct @ Dec 22 2008, 20:44)  Опишите плз. эти самые "чудеса". Что не так? С той простенькой программой при оптимизации меандра на выходе нет, а без оптимизации есть. В более расширенной версии оптимизатор «выкидывает» всё что в мейне под if (Start == 1) … Код ISR (TIMER0_COMP_vect) { TCNT0 = 0x00; if (Flag == 1) { PORTA ^= 0x01; if ((PINA & 0x02) == 0) CountIn_1++; CountCycleImp++; if (CountCycleImp == ConstCntCycleImp) { PORTA &=~ 0x01; Flag = 0; CountCycleImp = 0; Start = 1; return; } } else { CountCycleImp++; if (CountCycleImp == ConstCntCycleWithoutImp) { Flag = 1; CountCycleImp = 0; } } }
////////////////////// MAIN /////////////////// int main(void) { TCCR0 = (1 << CS00); TCNT0 = 0x00; OCR0 = 0x50; TIMSK |= (1 << OCIE0);
DDRA = 0xFD; PORTA = 0xFF;
sei();
while (1) { if (Start == 1) { Start = 0; if (CountIn_1 < CountIn_1_Min) PORT_W |= 0x04;
if (CountIn_1 > CountIn_1_Max) PORT_W &=~ 0x04;
CountIn_1 = 0; } } return 0; }
|
|
|
|
|
Dec 23 2008, 00:48
|

кекс
     
Группа: Свой
Сообщений: 3 825
Регистрация: 17-12-05
Из: Киев
Пользователь №: 12 326

|
Цитата(Oleg_IT @ Dec 22 2008, 20:50)  С той простенькой программой при оптимизации меандра на выходе нет, а без оптимизации есть. А что есть вместо меандра? Точнее плз ;> У меня с той простенькой программой при оптимизации -Os меандр есть, по крайней мере я вижу что порт переключается... Насчет Вашей новой программы, с учетом советов предыдущих ораторов, можно написать как-то так: Код #include <avr/io.h> #include <avr/interrupt.h>
typedef unsigned char U8; typedef unsigned short U16; typedef unsigned long U32;
typedef volatile unsigned char V8; typedef volatile unsigned short V16; typedef volatile unsigned long V32;
#define ConstCntCycleImp 5 #define ConstCntCycleWithoutImp 3
#define CountIn_1_Min 5 #define CountIn_1_Max 10
#define PORT_W PORTA
typedef struct tagDEVICE_CONTEXT { U8 Flag; V8 Start; U8 CountIn_1; U8 CountCycleImp; } TDEVICE_CONTEXT, *PDEVICE_CONTEXT;
TDEVICE_CONTEXT devContext = { 0 };
ISR (TIMER0_COMP_vect) { TCNT0 = 0x00; if (devContext.Flag == 1) { PORTA ^= 0x01; if ((PINA & 0x02) == 0) devContext.CountIn_1++; devContext.CountCycleImp++; if (devContext.CountCycleImp == ConstCntCycleImp) { PORTA &=~ 0x01; devContext.Flag = 0; devContext.CountCycleImp = 0; devContext.Start = 1; return; } } else { devContext.CountCycleImp++; if (devContext.CountCycleImp == ConstCntCycleWithoutImp) { devContext.Flag = 1; devContext.CountCycleImp = 0; } } }
////////////////////// MAIN /////////////////// int main(void) { TCCR0 = (1 << CS00); TCNT0 = 0x00; OCR0 = 0x50; TIMSK |= (1 << OCIE0);
DDRA = 0xFD; PORTA = 0xFF;
sei();
while (1) { if (devContext.Start == 1) { devContext.Start = 0; if (devContext.CountIn_1 < CountIn_1_Min) PORT_W |= 0x04;
if (devContext.CountIn_1 > CountIn_1_Max) PORT_W &=~ 0x04;
devContext.CountIn_1 = 0; } } return 0; } Я не знаю значений Ваших констант, поэтому поставьте какие должны быть. Работает абсолютно одинаково, с оптимизацией и без нее. Что я поменял: 1. Сгруппировал все переменные в одну структуру (удобнее писать программу, т.к. не нужно помнить все переменные, можно помнить только имя одной структуры остальное сделает Code Completion, и удобнее отлаживать - в watch достаточно написать только имя структуры и видно сразу все переменные). 2. Объявил типы в удобной форме (вместо длинючих "volatile unsigned char", ведь много удобнее и понятнее написать V8). 3. Объявил поле Start как volatile, чтобы компилятор не выбрасывал обращения к этой переменной на свое усмотрение.
|
|
|
|
|
Dec 23 2008, 04:11
|
Знающий
   
Группа: Свой
Сообщений: 922
Регистрация: 3-06-05
Из: Москва
Пользователь №: 5 709

|
Цитата(defunct @ Dec 23 2008, 03:48)  А что есть вместо меандра? Точнее плз ;> У меня с той простенькой программой при оптимизации -Os меандр есть, по крайней мере я вижу что порт переключается... Спасибо за подсказку модификации кода. В той простенькой программе с оптимизацией на выходе вообще ни чего нет.
|
|
|
|
Сообщений в этой теме
Oleg_IT Непонятные действия оптимизации. Dec 22 2008, 11:01 mandrew Как на счет объявить переменные с квалификатором v... Dec 22 2008, 11:22 Сергей Борщ Цитата(Oleg_IT @ Dec 22 2008, 13:01) Може... Dec 22 2008, 11:23 demiurg_spb Цитата(Сергей Борщ @ Dec 22 2008, 14:23) ... Dec 22 2008, 13:28  defunct Цитата(demiurg_spb @ Dec 22 2008, 15:28) ... Dec 22 2008, 13:42   demiurg_spb Цитата(defunct @ Dec 22 2008, 16:42) А за... Dec 22 2008, 13:51    defunct Цитата(demiurg_spb @ Dec 22 2008, 15:51) ... Dec 22 2008, 13:55  Сергей Борщ Цитата(demiurg_spb @ Dec 22 2008, 15:28) ... Dec 22 2008, 14:11     smac Цитата(Oleg_IT @ Dec 22 2008, 21:50) С то... Dec 22 2008, 19:14 Ivan A-R % avr-gcc --version
avr-gcc (GCC) 4.3.1
Полёт нор... Dec 22 2008, 13:15 Goodefine Цитата(Oleg_IT @ Dec 22 2008, 19:35) В ре... Dec 22 2008, 16:56 Oleg_IT Цитата(Goodefine @ Dec 22 2008, 19:56) Та... Dec 22 2008, 17:03 Ivan A-R Oleg_IT, попробуй сгенерить ассемблерный листинг с... Dec 22 2008, 17:09 Александр Куличок Викидывает, потому что при запуске программы Start... Dec 22 2008, 19:09 sonycman А вы нам приведите ассемблерный листинг того вариа... Dec 23 2008, 19:57
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|