|
"Оптимизация" в WinAVR и как с этим бороться |
|
|
|
Nov 16 2011, 18:07
|

Местный
  
Группа: Участник
Сообщений: 253
Регистрация: 15-04-10
Из: Волгоград
Пользователь №: 56 658

|
Перейдя с ассемблера на WinAVR, невольно стал обращать на размер кода. Когда стал разбираться в конкретике генерируемого кода , хваленный на многих сайтах WinAVR обнажил свое несовершенство. Короче, программка : Код #include <avr/io.h> #include <inttypes.h>
#define Btn1 PB2 #define Btn2 PB3
#define KeyMask (1<<Btn1)|(1<<Btn2) #define sbi(p,b) (p |= (1<<b)) //Установить бит
volatile register int8_t Cnt asm("r19"); // фоновый счетчик volatile register int8_t a asm ("r16");
int main (void) { asm("nop"); a = 1;
while(1) { if (~(PINB)&(KeyMask)) { a |= 0x01; } if ((--Cnt)==0) { if (a==1 ) { a=0; sbi (PINB,PB2); } } } } Соответственно , полученный код: Код a = 1; ldi r16, 0x01
while(1) { [color="#FF00FF"]if (~(PINB)&(KeyMask)) in r24, 0x16 ldi r25, 0x00 com r24 com r25 andi r24, 0x0C andi r25, 0x00 or r24, r25 breq .+2[/color] { a |= 0x01; } ori r16, 0x01
[color="#FF0000"]if ((--Cnt)==0) mov r24, r19 subi r24, 0x01 mov r19, r24[/color] brne .-26 { if (a==1 ) cpi r16, 0x01 brne .-30 { a=0; ldi r16, 0x00
sbi (PINB,PB2); sbi 0x16, 2 rjmp .-36 Конструкцию if ((--Cnt)==0) выделенную крас.цветом может заменить всего одна машинная команда: dec r19! Вопрос: как заставить компилятор это делать ? Во втором случае: if (~(PINB)&(KeyMask)) , невижу смысла во втором парном регистре r25. Можно использовать "tst r24". Можно как нибудь с этим бороться ?! Не хочеться чтобы потом код получался неоправданно раздутым! Может быть стоит подождать другую версию компилятора (пользуюсь WinAVR-20100110) или уже пререходить на совсем другой ?
|
|
|
|
|
 |
Ответов
|
Nov 25 2011, 08:40
|

Местный
  
Группа: Участник
Сообщений: 253
Регистрация: 15-04-10
Из: Волгоград
Пользователь №: 56 658

|
Спасибо за ответы ! Опять я возвращаюсь к своим любимым регистровым глобальным переменным. Вначале программы обычно происходит инициализация переменных. В моей программе три регистровых глобальных переменных. Одна из них обьявленна как битовая область, и с ней проблем нет. Две других как беззнаковый байт (см. программу). В месте задания им начальных значений, компилятор игнорировал эти операции, чтобы я не делал. Все уровни оптимизации , кроме -O0 исключали эти команды. Но, после перемещения блока инициализации в отдельную подпрограмму , компилятор всеже их заметил, и правильно откомпилировал! У меня возникла мысль, что какието ключи не позволяют оптимизатору игнорировать команды в подпрограммах. Хотел бы услышать ваши предположения. Код #include <avr/io.h> #include <avr/interrupt.h> // задает макросы sei() , cli() #include <inttypes.h>
//===================================================================== // определение регистров: volatile register uint8_t FLCnt asm("r16"); //фоновый счетчик длительности переключения свдиода volatile register uint8_t DBKCnt asm("r18"); //фоновый счетчик для отсчета периода блокировки опроса кнопок volatile register struct { uint8_t bDbRKey : 1; uint8_t bFLed : 1; } RFGP asm ("r17");
//;---------------------------------------------------------------------------------------------------------------------------------------- //=== Определение макросов #define sbi(p,b) (p |= (1<<b)) //Установить бит //;---------------------------------------------------------------------------------------------------------------------------------------- //Определение портов: /* направление для порта В*/ #define DIRB 0b00010001 /* Pull-ups для порта В*/ #define PUPB 0b00000101
//;---------------------------------------------------------------------------------------------------------------------------------------- //Определение контактов #define Control1 PB4 /* линия управления VT (1 - откр; 0 - закр ) */ #define Btn1 PB2 /* линия кнопки (на общ.пров) */ #define Led PB0 /* линия светодиода ("1" - вкл. ч/з резистор на общ.) */
//;---------------------------------------------------------------------------------------------------------------------------------------- /* длительность запрета на опрос клавиш t=(101-1)*0,1=10 sec */ #define Vl_DBKCnt 101
/* t=5*0,1=0,5 sec */ #define Vl_FLCnt 5
// Маска кнопок:"Btn" #define KeyMask (1<<Btn1)|(1<<1)
//===================================================================== //===================================================================== SIGNAL ( SIG_OUTPUT_COMPARE0A) {//______ Моргание светодиода t=5*0,1=0,5 sec if (!(--FLCnt)) {//__ Переключение свдиода FLCnt=Vl_FLCnt;// перезагрузка ф.счетчика !!!! ~(RFGP.bFLed); sbi (PINB,Led);// ________ Переключение свдиода ! }
//______ Формирование запрета на опрос клавиш t=(101-1)*0,1=10 sec if (RFGP.bDbRKey==1) { //__ проверка на первый запуск if (DBKCnt == 0 ) DBKCnt=Vl_DBKCnt; --DBKCnt;//__ продолжение счета if (DBKCnt==0) // checking of =0 { //__ сброс флага RFGP.bDbRKey=0; DBKCnt=Vl_DBKCnt; } } }
//============================================================================= //============================================================================= int main (void) { //_________________________ ИНИЦИАЛИЗАЦИЯ _____________________________ uint8_t temp;
PORTB=PUPB; //иницализация порта B DDRB=DIRB; // задание направления для порта B TIMSK0=(1<<OCIE0A); /* установка разр. прер-ия по совпадению т/сч.0 с регистром OCR0A */ OCR0A=234; //загрузка регистра совпадения OCR0A коэф. деления TCCR0A= (1<<WGM01); //установка режима СТС - обнуление Т/С0 при совпадении с регистром OCR0A TCCR0B=(1<<CS02)|(1<<CS00); // <---- конфигурация и запуск сч-ка в реж. СТС с предделителем ckl/1024 RFGP.bDbRKey=0; RFGP.bFLed=0; [color="#ff0000"]DBKCnt=Vl_DBKCnt; //задание начальных значений для счетчиков FLCnt=(uint8_t)Vl_FLCnt;[/color]
sei (); // Разрешение общего прерывания //____________________ ЦИКЛ РАБОЧЕЙ ПРОГРАММЫ ______________________ while (1) { //____ Считывание кнопки temp=~(PINB); temp &= KeyMask; if (temp) { //______ Обработка нажатия кн."Btn" if ( RFGP.bDbRKey==0)//____ проверка на запрет считывания кнопок { RFGP.bDbRKey=1; // sbr RFGP,(1<<bDbRKey) sbi (PINB,Control1); // ________ Переключение линии Control1 _______________!!!!! } } } }
|
|
|
|
|
Nov 25 2011, 12:07
|

Местный
  
Группа: Участник
Сообщений: 253
Регистрация: 15-04-10
Из: Волгоград
Пользователь №: 56 658

|
Цитата(Сергей Борщ @ Nov 25 2011, 12:27)  Прочитайте еще раз про яйцо и микроволновку. Мне лень считать, сколько раз вам писали, что регистровую переменную нельзя делать volatile, о чем прямым текстом пишут создатели компилятора. Вы же с упорством пьяного продолжаете писать register volatile и пенять на компилятор. Извиняюсь что возмутил вас употребением и применением volatile ! Кстати сказать, из ответ на вопрос о использовании Volatile к регистровым глобальным переменным я со своим плохим знанием английского понял что компилятор уже считает регистровые переменные как volatile. Другими словами использование квалификатора бессмысленно. Я убрал в обьявлении переменных FLCnt, DBKCnt volatile, результат тотже ! Вопрос остается открытым
|
|
|
|
Сообщений в этой теме
MaxiMuz "Оптимизация" в WinAVR и как с этим бороться Nov 16 2011, 18:07 Палыч Цитата(MaxiMuz @ Nov 16 2011, 22:07) хвал... Nov 16 2011, 18:45 MaxiMuz Цитата(Палыч @ Nov 16 2011, 21:45) А, вот... Nov 16 2011, 19:19  Палыч Цитата(MaxiMuz @ Nov 16 2011, 23:19) KeyM... Nov 16 2011, 20:10   MaxiMuz Цитата(Палыч @ Nov 16 2011, 23:10) Почему... Nov 16 2011, 21:06    aaarrr Цитата(MaxiMuz @ Nov 17 2011, 01:06) or ... Nov 16 2011, 21:19     MaxiMuz Цитата(aaarrr @ Nov 17 2011, 00:19) Это о... Nov 17 2011, 15:19      Палыч Цитата(MaxiMuz @ Nov 17 2011, 19:19) ... ... Nov 17 2011, 17:42      AHTOXA Цитата(MaxiMuz @ Nov 17 2011, 21:19) А ес... Nov 17 2011, 17:47      _Pasha Цитата(MaxiMuz @ Nov 17 2011, 19:19) Код ... Nov 18 2011, 06:25 AHTOXA Цитата(MaxiMuz @ Nov 17 2011, 00:07) Пере... Nov 16 2011, 19:58 MaxiMuz Цитата(AHTOXA @ Nov 16 2011, 22:58) Вам ж... Nov 18 2011, 09:00  Палыч Цитата(MaxiMuz @ Nov 18 2011, 13:00) На О... Nov 18 2011, 10:59   _Pasha Цитата(Палыч @ Nov 18 2011, 13:59) Имхо, ... Nov 18 2011, 14:36    neiver Цитата(_Pasha @ Nov 18 2011, 18:36) и не ... Nov 18 2011, 14:45    ReAl Цитата(_Pasha @ Nov 18 2011, 16:36) ГЦЦ н... Nov 18 2011, 16:17     demiurg_spb Паша верно перечислил основные недочёты avr-gcc, с... Nov 18 2011, 17:13     neiver Цитата(ReAl @ Nov 18 2011, 20:17) Вот еще... Nov 18 2011, 17:23      MaxiMuz Цитата(neiver @ Nov 18 2011, 20:23) К сож... Nov 20 2011, 11:58       ReAl Цитата(MaxiMuz @ Nov 20 2011, 12:55) Хоте... Nov 20 2011, 12:23        MaxiMuz Цитата(ReAl @ Nov 20 2011, 15:23) .......... Nov 23 2011, 11:30         demiurg_spb Цитата(MaxiMuz @ Nov 23 2011, 15:30) где ... Nov 23 2011, 13:39          ReAl Тьху, ну конечно, -ffixed-reg
Что-то меня на = пот... Nov 23 2011, 21:19         AHTOXA КодCFLAGS += -ffixed-r16
CFLAGS += -ffixed-r18 Nov 23 2011, 14:40   MaxiMuz Цитата(Палыч @ Nov 18 2011, 13:59) Если В... Nov 18 2011, 16:06    ReAl Цитата(MaxiMuz @ Nov 18 2011, 18:06) боль... Nov 18 2011, 22:38  Сергей Борщ QUOTE (MaxiMuz @ Nov 18 2011, 12:00) Это ... Nov 18 2011, 11:54 ReAl Цитата(MaxiMuz @ Nov 16 2011, 20:07) Код#... Nov 16 2011, 21:53 Genadi Zawidowski Код#define KeyMask (1<<Btn1)|... Nov 17 2011, 01:30 neiver Мда, можно вытащить ассемблерщика из ассемблера, н... Nov 17 2011, 08:19 Палыч Цитата(neiver @ Nov 17 2011, 12:19) integ... Nov 17 2011, 09:27 neiver Я к чему, тут про целочисленное расширение намекаю... Nov 18 2011, 05:25 MaxiMuz neiver , _Pasha да действительно, можно и так напи... Nov 18 2011, 08:38 neiver Цитата(MaxiMuz @ Nov 18 2011, 12:38) neiv... Nov 18 2011, 08:44 neiver GCC прекрасно может сгенерировать одну команду sbi... Nov 18 2011, 11:07 Палыч Цитата(neiver @ Nov 18 2011, 15:07) GCC п... Nov 18 2011, 11:17 ReAl Жаль. Nov 18 2011, 19:58   AHTOXA Цитата(MaxiMuz @ Nov 25 2011, 18:07) Вопр... Nov 25 2011, 14:16    ReAl Цитата(AHTOXA @ Nov 25 2011, 16:16) Какой... Nov 25 2011, 14:35     AHTOXA По-моему, на этот вопрос тоже уже ответили, и не р... Nov 25 2011, 19:17 ReAl Провёл маленький эксперимент.
Убрал все эти regist... Nov 25 2011, 20:32 MaxiMuz AHTOXA с вами не поспоришь
ReAl По сути , кусок... Nov 28 2011, 10:59 ReAl Цитата(MaxiMuz @ Nov 28 2011, 12:59) подо... Nov 28 2011, 14:16 sigmaN перед main воткните __attribute__ ((noreturn));
h... Nov 28 2011, 19:40 MaxiMuz Цитата(sigmaN @ Nov 28 2011, 22:40) перед... Jan 23 2012, 09:15 ReAl Для этого в AVR-GCC уже давно есть OS_main и OS_ta... Nov 28 2011, 20:17 sigmaN ну или так, да.
а ещё я из исходников библиотеки ... Nov 28 2011, 22:10 ILYAUL Цитата(sigmaN @ Nov 29 2011, 02:10) ну ил... Nov 29 2011, 04:15  ARV Цитата(ILYAUL @ Nov 29 2011, 08:15) ИМХО ... Jan 23 2012, 09:53 MaxiMuz При использовании int OS_main (void) компилятор вы... Jan 23 2012, 14:50 sigmaN warning это не error и по идее не должен приводить... Jan 24 2012, 02:07 MaxiMuz Цитата(sigmaN @ Jan 24 2012, 05:07) warni... Feb 2 2012, 11:49 _Pasha Таварисч не панимаит.
Кодint main(void) __... Feb 2 2012, 12:16 MaxiMuz Цитата(_Pasha @ Feb 2 2012, 15:16) Тавари... Feb 3 2012, 10:42  Сергей Борщ QUOTE (MaxiMuz @ Feb 3 2012, 12:42) Да... Feb 3 2012, 11:08 MaxiMuz Доброго времяни суток!
Не стал создавать отдел... Oct 16 2012, 18:35 Палыч Цитата(MaxiMuz @ Oct 16 2012, 22:35) здес... Oct 17 2012, 06:15  MaxiMuz Цитата(Палыч @ Oct 17 2012, 09:15) Это - ... Oct 17 2012, 12:11   Сергей Борщ В этом стандарте операция "&" выполн... Oct 17 2012, 12:59   Палыч Цитата(MaxiMuz @ Oct 17 2012, 16:11) стан... Oct 17 2012, 13:04 Genadi Zawidowski Используйте компилятор поновее (avr-gcc 4.7.2, avr... Oct 16 2012, 19:26
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|