singlskv 0 19 октября, 2007 Опубликовано 19 октября, 2007 · Жалоба Т.е., на 12 лишних байт вы соптимизировали :) Мораль сей басни - оптимизировать низкоуровневые вещи должен компилятор, ему то в 95% случаев надо эту оптимизацию и доверить... Если максимальная оптимизация по размеру, то первый вариант весит 312 байт, второй - 192. Тут действительно вылезают обещанные singlskv 120 байт. А осадок то остался... © (не мой) :) :) На самом деле в первом варианте "по скорости", IAR просто переклинило по какой-то только ему ведомой причине. Так иногда бывает с компиляторами. :( Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
SapegoAL 0 20 октября, 2007 Опубликовано 20 октября, 2007 · Жалоба А осадок то остался... © (не мой) :) :) На самом деле в первом варианте "по скорости", IAR просто переклинило по какой-то только ему ведомой причине. Так иногда бывает с компиляторами. :( По сравнению с вариантом от Сергей Борщ, любезно им предоставленном мне, проигрыш вашего варианта оптимизации на этой подпрограмме составил 26 байт. Хотя честно говоря я не понимаю почему. Я оптимизировал прерывания примерно вашим способом. Видимо знаний компилятора недостаточно. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
singlskv 0 21 октября, 2007 Опубликовано 21 октября, 2007 · Жалоба По сравнению с вариантом от Сергей Борщ, любезно им предоставленном мне, проигрыш вашего варианта оптимизации на этой подпрограмме составил 26 байт. Хотя честно говоря я не понимаю почему. Я оптимизировал прерывания примерно вашим способом. Видимо знаний компилятора недостаточно.Мой вариант, это еще был не "мой" вариант, к реальной оптимизации я просто не приступал ;) так, показал направление .... Вам нравится IAR ? Хорошо, будет для IAR: 143 144 __z void InvMixColumn1( byte * column ,byte bpoly_); 145 \ In segment CODE, align 2, keep-with-next 146 __z void InvMixColumn(byte *column) \ InvMixColumn: 147 { 148 InvMixColumn1( column ,BPOLY); \ 00000000 E10B LDI R16, 27 \ 00000002 REQUIRE InvMixColumn1 \ 00000002 ; // Fall through to label InvMixColumn1 149 } \ In segment CODE, align 2, keep-with-next 150 __z void InvMixColumn1( byte * column ,byte bpoly) \ InvMixColumn1: 151 { 152 byte r0, r1, r2, r3; 153 byte co0 = column[0],co1=column[1],co2=column[2],co3=column[3]; \ 00000000 8110 LD R17, Z \ 00000002 8121 LDD R18, Z+1 \ 00000004 8132 LDD R19, Z+2 \ 00000006 8143 LDD R20, Z+3 154 byte tmp; 155 156 r0 = co1 ^ co2 ^ co3; \ 00000008 2F53 MOV R21, R19 \ 0000000A 2752 EOR R21, R18 \ 0000000C 2754 EOR R21, R20 157 r1 = co0 ^ co2 ^ co3; \ 0000000E 2F63 MOV R22, R19 \ 00000010 2761 EOR R22, R17 \ 00000012 2764 EOR R22, R20 158 tmp = r0 ^ r1; \ 00000014 2F76 MOV R23, R22 \ 00000016 2775 EOR R23, R21 159 r2 = tmp ^ co3; \ 00000018 2E04 MOV R0, R20 \ 0000001A 2607 EOR R0, R23 160 r3 = tmp ^ co2; \ 0000001C 2E13 MOV R1, R19 \ 0000001E .... RCALL ?Subroutine0 161 162 co0 = (tmp=co0) << 1; 163 if ((tmp & 0x80)==0x80) co0 ^= bpoly; 164 co1 = (tmp=co1) << 1; 165 if ((tmp & 0x80)==0x80) co1 ^= bpoly; 166 co2 = (tmp=co2) << 1; 167 if ((tmp & 0x80)==0x80) co2 ^= bpoly; 168 co3 = (tmp=co3) << 1; 169 if ((tmp & 0x80)==0x80) co3 ^= bpoly; 170 171 r0 ^= co0 ^ co1; \ ??CrossCallReturnLabel_0: \ 00000020 2F72 MOV R23, R18 \ 00000022 2771 EOR R23, R17 \ 00000024 2757 EOR R21, R23 172 r1 ^= co1 ^ co2; \ 00000026 2F73 MOV R23, R19 \ 00000028 2772 EOR R23, R18 \ 0000002A 2767 EOR R22, R23 173 r2 ^= co2 ^ co3; \ 0000002C 2F74 MOV R23, R20 \ 0000002E 2773 EOR R23, R19 \ 00000030 2607 EOR R0, R23 174 r3 ^= co0 ^ co3; \ 00000032 2F74 MOV R23, R20 \ 00000034 2771 EOR R23, R17 \ 00000036 .... RCALL ?Subroutine0 175 176 co0 = (tmp=co0) << 1; 177 if ((tmp & 0x80)==0x80) co0 ^= bpoly; 178 co1 = (tmp=co1) << 1; 179 if ((tmp & 0x80)==0x80) co1 ^= bpoly; 180 co2 = (tmp=co2) << 1; 181 if ((tmp & 0x80)==0x80) co2 ^= bpoly; 182 co3 = (tmp=co3) << 1; 183 if ((tmp & 0x80)==0x80) co3 ^= bpoly; 184 185 r0 ^= co0 ^ co2; \ ??CrossCallReturnLabel_1: \ 00000038 2F73 MOV R23, R19 \ 0000003A 2771 EOR R23, R17 \ 0000003C 2757 EOR R21, R23 186 r1 ^= co1 ^ co3; \ 0000003E 2F74 MOV R23, R20 \ 00000040 2772 EOR R23, R18 \ 00000042 2767 EOR R22, R23 187 r2 ^= co0 ^ co2; \ 00000044 2F73 MOV R23, R19 \ 00000046 2771 EOR R23, R17 \ 00000048 2607 EOR R0, R23 188 r3 ^= co1 ^ co3; \ 0000004A 2F74 MOV R23, R20 \ 0000004C 2772 EOR R23, R18 \ 0000004E .... RCALL ?Subroutine0 189 190 co0 = (tmp=co0) << 1; 191 if ((tmp & 0x80)==0x80) co0 ^= bpoly; 192 co1 = (tmp=co1) << 1; 193 if ((tmp & 0x80)==0x80) co1 ^= bpoly; 194 co2 = (tmp=co2) << 1; 195 if ((tmp & 0x80)==0x80) co2 ^= bpoly; 196 co3 = (tmp=co3) << 1; 197 if ((tmp & 0x80)==0x80) co3 ^= bpoly; 198 199 tmp=co0 ^ co1 ^ co2 ^ co3; \ ??CrossCallReturnLabel_2: \ 00000050 2721 EOR R18, R17 \ 00000052 2723 EOR R18, R19 \ 00000054 2724 EOR R18, R20 200 201 column[0] = tmp ^ r0; \ 00000056 2752 EOR R21, R18 \ 00000058 8350 ST Z, R21 202 column[1] = tmp ^ r1; \ 0000005A 2762 EOR R22, R18 \ 0000005C 8361 STD Z+1, R22 203 column[2] = tmp ^ r2; \ 0000005E 2602 EOR R0, R18 \ 00000060 8202 STD Z+2, R0 204 column[3] = tmp ^ r3; \ 00000062 2612 EOR R1, R18 \ 00000064 8213 STD Z+3, R1 205 } \ 00000066 9508 RET \ In segment CODE, align 2, keep-with-next \ ?Subroutine0: \ 00000000 2617 EOR R1, R23 \ 00000002 2F71 MOV R23, R17 \ 00000004 0F11 LSL R17 \ 00000006 FB77 BST R23, 7 \ 00000008 F40E BRTC ??Subroutine0_0 \ 0000000A 2710 EOR R17, R16 \ ??Subroutine0_0: \ 0000000C 2F72 MOV R23, R18 \ 0000000E 0F22 LSL R18 \ 00000010 FB77 BST R23, 7 \ 00000012 F40E BRTC ??Subroutine0_1 \ 00000014 2720 EOR R18, R16 \ ??Subroutine0_1: \ 00000016 2F73 MOV R23, R19 \ 00000018 0F33 LSL R19 \ 0000001A FB77 BST R23, 7 \ 0000001C F40E BRTC ??Subroutine0_2 \ 0000001E 2730 EOR R19, R16 \ ??Subroutine0_2: \ 00000020 2F74 MOV R23, R20 \ 00000022 0F44 LSL R20 \ 00000024 FB77 BST R23, 7 \ 00000026 F40E BRTC ??Subroutine0_3 \ 00000028 2740 EOR R20, R16 \ ??Subroutine0_3: \ 0000002A 9508 RET ИТОГО: 150 байтов программного кода (уже в 2 раза лучше чем оригинал ;) ) И если еще чуть напрячь мозг, то можно на 20-30 байт сократить... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
SapegoAL 0 22 октября, 2007 Опубликовано 22 октября, 2007 · Жалоба Внимательно просмотрю. Правда я отказался на сегодняшний момент от ужатия, так как в угоду функциональности всётаки проект распух. :( Он уже работает. С другой стороны, как я вижу, и как вы сами доказываете - вполне можно пользоваться любым инструментом. Надо просто его хорошо знать. Методы такого рода оптимизации основаны на знании как именно сам компилятор генерит код. С другой стороны, такая оптимизация достаточно зависима от компилятора. Спасибо всем за помощь в реализации данного проекта. :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
pvp 0 22 октября, 2007 Опубликовано 22 октября, 2007 · Жалоба __z void InvMixColumn(...) Поясните, пожалуйста, назначение "__z" (и источник информации) - в описании на компилятор 4.30A("Help>AVR>AVR C/C++ Compiler Reference Guide")не нашёл ничего подобного. Без использования "__z"код "прибавляет в весе" 4 байта. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 140 22 октября, 2007 Опубликовано 22 октября, 2007 · Жалоба Поясните, пожалуйста, назначение "__z" (и источник информации)Было в каком-то из .html в папке документации. Указывает компилятору передавать первый указатель в регистровой паре Z. Встречается также в вариациях __x, __xz (если память не изменяет). Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
singlskv 0 22 октября, 2007 Опубликовано 22 октября, 2007 · Жалоба С другой стороны, как я вижу, и как вы сами доказываете - вполне можно пользоваться любым инструментом. Надо просто его хорошо знать. Методы такого рода оптимизации основаны на знании как именно сам компилятор генерит код. С другой стороны, такая оптимизация достаточно зависима от компилятора.Эээ... попробую пояснить почему я Вас агитировал за Gcc. Конечно у IAR оптимизатор написан чуть лучше чем у Gcc(в среднем), и на "плохом" коде это всегда сказывается. Дальше все зависит от конкретной задачки и от модели компиляции разными компиляторами. У IAR AVR есть одно принципиальное отличие от других компиляторов, он использует регистровую пару Y под стек и на этом очень часто превосходит другие компиляторы, но, задачки то разные бывают... Посмотрев исходники я увидел что в данной проге очень часто нужно >2 указателей одновременно. Соответственно преимущество для таких задач будет иметь компилятор у которого больше регистровых пар в распоряжении, а это Gcc а не IAR. Просто посмотрите на листинги первоначального варианта кода и количество использования в них инструкций типа mov X/Z, R(xx):R(xx+1) и mov R(xx):R(xx+1), X/Z Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
SapegoAL 0 22 октября, 2007 Опубликовано 22 октября, 2007 · Жалоба :) Я когда первый раз увидел результаты компилирования IAR, то тоже был немало удивлён наличием двух стеков. И первый вопрос - зачем! Чем не устраивает стандартный стэк? Зачем использовать такую дефицитную вещь как регистровая пара? Внимательно рассматривая листинги - я понял. Именно при оптимизации по объёму такой подход даёт преимущество. При оптимизации по объёму появляется большое количество подпрограмм. При использовании второго стека можно делать подпрограммы сохранения регистров и восстановления. Есть и ещё ряд преимуществ. В частности возможность прямого обращения к данным в стэке. Например когда параметры находятся в стеке. Если использовать основной стек, то это более сложно получится. Короче каждый подход имеет свои положительные стороны и свои отрицательные. Что очевидно. К GCC претензий у меня нет и не может быть. Я не против данного компилятора. Просто работать с ним оказалось сложнее чем с IAR. Может быть когда-нибудь я его освою. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
pvp 0 23 октября, 2007 Опубликовано 23 октября, 2007 · Жалоба Было в каком-то из .html... Спасибо за ответ. Найду и почитаю. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
skripach 6 9 ноября, 2009 Опубликовано 9 ноября, 2009 · Жалоба Не стал создавать новую тему, поэтому здесь. Можно ли заставить работать(не получается пока) приложение скомпилированное с такими настройками линкера define symbol __ICFEDIT_intvec_start__ = 0x00000000; /*-Memory Regions-*/ define symbol __ICFEDIT_region_ROM_start__ = 0x00000044; define symbol __ICFEDIT_region_ROM_end__ = 0x0007FFFF; define symbol __ICFEDIT_region_RAM_start__ = 0x40000040; define symbol __ICFEDIT_region_RAM_end__ = 0x4000FFFF; если расположить его по адресу скажем 0х1000? Скопировал вектора, сделал ремап, передал управление на 0-вой адрес. Переходит разумеется не туда... Если я к тому что лежит с 0х40000020-го адреса прибавляю число 0х1000 то после сброса переходит туда куда надо но приложение всё равно не работает. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
skripach 6 12 ноября, 2009 Опубликовано 12 ноября, 2009 · Жалоба Что никто не знает? ...или я что-то не то спросил. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
zltigo 2 12 ноября, 2009 Опубликовано 12 ноября, 2009 · Жалоба Что никто не знает? ...или я что-то не то спросил. Нет желания разгадывать шарады. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
KSN 0 27 февраля, 2010 Опубликовано 27 февраля, 2010 · Жалоба Есть вопрос по прерываниям в bootloader и application. Итак, контроллер atmega8. Карта памяти: 0x0000 - 0x13FF: Application 0x1400 -0x17FF: Common memory (здесь храняться общие функции, доступные из application & bootloader) 0x1800 - 0x1FFF: Bootloader. В bootloader используется одно прерывание от таймера2 по сравнению. Контроллер программируется Avreal и стартует с Bootloader, проверяется CRC, если все ок, то переход на application. Также есть возможность запуска bootloader из application. Итак, программирую контроллер только прошивкой загрузчика: все хорошо, прерывание работает. Теперь, программирую контроллер с общей прошивкой (приложение+загрузчик): загрузчик запускается, отрабатывает и передает управление приложению. Затем из приложения вызываю загрузчик и вижу, что прерывание не работает. В загрузчике и приложении использую разные low_level_init, причем в загрузчике устанавливаю IVSEL, а в приложении сбрасываю. Может у кого было подобное? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 140 27 февраля, 2010 Опубликовано 27 февраля, 2010 · Жалоба Может у кого было подобное?Нет, не было. Прекрасно работают прерывания и там и там. Можете прислать проект на serzh собака rrt.lv, посмотрю. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
zltigo 2 28 февраля, 2010 Опубликовано 28 февраля, 2010 · Жалоба Отправил повторно..... Moderator: Для обильной личной переписки существует служба личных сообщений. Заодно напоминаю, что кросспосты на форуме запрещены. Личная переписка удалена. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться