DenisIV 0 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Кстати, раз уж о глюках: У меня при включенной оптимизации компилятор думает, что раз тела у while нет, то можно и зациклить сам на себя БЕЗ проверки условия, т.е. MojBit=1; while(MojBit==1) { }; в асме выглядит так: Addr: rjmp Addr Если в тело хотя бы вставить _NOP(); т.е. while(MojBit==1) {_NOP();}; картина меняется - добавляется загрузка вита в 1 и проверка в теле while. Вопрос знатокам: Почему? Компилятор умнее пользователя? Модератор. Тема выделена как отдельная из другого топика. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Палыч 9 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Вопрос знатокам: Почему? Компилятор умнее пользователя? Почему картина поменялась после добавления _NOP(); - не скажу, вроде на условие в цикле не влияет... А, вот, проверять условие цикла - нет необходимости: переменной MojBit присвоено значение 1 и условие MojBit==1 - всегда выполняется! Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
scifi 1 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Вопрос знатокам: Почему? Компилятор умнее пользователя? Ответ прост: бывают умные компиляторы и не очень умные (ну и тупые тоже бывают). Видимо, Ваш компилятор не очень умный: в одной ситуации может оптимизировать до предела, а в другой - не может. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
DenisIV 0 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Почему картина поменялась после добавления _NOP(); - не скажу, вроде на условие в цикле не влияет... А, вот, проверять условие цикла - нет необходимости: переменной MojBit присвоено значение 1 и условие MojBit==1 - всегда выполняется! Не согласен. Вы забыли про прерывания? Вот они и меняют этот бит. Может компилёру нужно дополнительно сообщить, что этот бит ещё где-то может модифицироваться? Вопрос, как... P.S. Я с асмом дружу очень, но большие модули переписываю на С, потому что надоело при смене типа мк в пределах одного изготовителя приходится сильно менять исходник, а при смене Z80<>PIC<>Holtek<>AVR<>msp430<>PC<>mcs48<>mcs51 и т.д. просто волосы дыбом встают... Поэтому и прошу помощи... Как было указано в начале темы, мож у мя глюки? 2Moderator: Может мне создать отдельную тему? Но я её хотел назвать именно так, как назвал автор:) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Nemo2000 0 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Вы забыли про прерывания? Вот они и меняют этот бит. Может компилёру нужно дополнительно сообщить, что этот бит ещё где-то может модифицироваться? а прочитать тему с самого начала? при объявлении своей переменной MojBit укажите что она volatile и будет вам счастье Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
sergeeff 1 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Просто не устаю поражаться. На нашем форуме про volatile уж было все рассказано, подробнее, чем где-бы то ни было, учитывая специфику программирования железа. Ан нет, есть еще граждане про сие не читавшие, да еще и вопрос задающие не поймешь как. Чудно, все это. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
DenisIV 0 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба Просто не устаю поражаться. На нашем форуме про volatile уж было все рассказано, подробнее, чем где-бы то ни было, учитывая специфику программирования железа. Ан нет, есть еще граждане про сие не читавшие, да еще и вопрос задающие не поймешь как. Чудно, все это. Прошу простить... Это как допустим чья-то жена получила вчера права, начинает спрашивать мужа: "Как там решить вопрос с ГАИшниками, если..." Муж: "Я ж те говорил, книжки покупал..." На сколько я знаю, volatile говорит компилятору о том, что все связанные с переменной действия ни в коем случае не оптимизировать. Вопрос для многозадачных или "мощных" систем вроде выглядит по другому: требуется ещё лочить переменную на время обработки данных(например в прерывании меняется массив данных и указатели на него а основная прога может вылететь) И если можно про static. Просветите плиз тонкости... Может быть еще раз... Ну "я месяц назад получил права" :) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
rezident 0 23 декабря, 2008 Опубликовано 23 декабря, 2008 · Жалоба И если можно про static. Просветите плиз тонкости... Может быть еще раз... Ну "я месяц назад получил права" :) Вот тут не найдется для вас ответа на вопрос про static? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
sergeeff 1 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Прошу простить... Это как допустим чья-то жена получила вчера права, начинает спрашивать мужа: "Как там решить вопрос с ГАИшниками, если..." Муж: "Я ж те говорил, книжки покупал..." На сколько я знаю, volatile говорит компилятору о том, что все связанные с переменной действия ни в коем случае не оптимизировать. Вопрос для многозадачных или "мощных" систем вроде выглядит по другому: требуется ещё лочить переменную на время обработки данных(например в прерывании меняется массив данных и указатели на него а основная прога может вылететь) И если можно про static. Просветите плиз тонкости... Может быть еще раз... Ну "я месяц назад получил права" :) Во-первых, понять, что если есть в системе прерывания и вы их используете - значит уже система многозадачная. Во-вторых. Что значит "приказ не оптимизировать"? Это значит, что какая-то другая задача тоже может эту переменную использовать, а по сему эта самая переменная будет размещена в памяти, а не в регистрах. Вопрос о том, "лочить" или нет эту переменную - вопрос ее размера и особенностей процессора. Если обращение к ней проходит за время, когда прерывание не может возникнуть, то и "лочить" не нужно. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
DenisIV 0 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба 2rezident: со static (и не тоько) разобрался, спасибо! Ещё вопросик... Насколько я понимаю, у меня эти проблемы с оптимизацией начались после того, как у меня образовалось более одного модуля, т.е. каждый модуль независим для компилятора и компилёр оптимизирует не проект, а данный модуль и если я в одном модуле только читаю а в другом только пишу переменную, то в обоих случаях если я не допишу volatile компилёр просто выкинет эти строки (просто примет за константу данные при компиляции), а с линкера не спросишь-он просто склеит готовые блоки. Опять же, если будет это всё в одном файле/модуле, то даже при макс. оптимизации компилёр может понять, что переменная юзается внутри в разных функциях (в т.ч и в прерываниях) и не будет оптимизировать до упора? Т.е. в данном случае не нужен тип global/static/volatile ? (модуль-то один, global итак будет автоматом, вопрос только про оптимизатор) Да, самое интересное: Я объявляю в модуле main глобальные переменные, в остальных модулях их же, но через extern, т.е. получается, что глобально в пределах проекта, но вот эта заноза-оптимизатор видит только в пределах модуля переменную (в смысле её использования), а не в пределах проекта? Или есть тонкости? Объясните плиз, где грабли... Крыша уже течёт... Просто я не умею их готовить... (с) какая-то реклама Чем-то чувствую, что и прав и нет. Хотелось бы понять, где. Я понимаю, RTFM, но всё же... F1 ! То, что люди задают глупые вопросы не означает, что они глупы, просто иногда не хватает опыта... Сорри, если чуть оффтоп... ;) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
sergeeff 1 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Я все не пойму, что за проблемы "с этой оптимизацией"? Где конкретно, с чем проблемы? Что компилятор делает не так, как вы хотите? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
DenisIV 0 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Я все не пойму, что за проблемы "с этой оптимизацией"? Где конкретно, с чем проблемы? Что компилятор делает не так, как вы хотите? Каждый модуль независим для компилятора и компилёр оптимизирует не проект, а данный модуль и если я в одном модуле только читаю а в другом только пишу переменную, то в обоих случаях если я не допишу volatile компилёр просто выкинет эти строки (просто примет за константу данные при компиляции) Вот в этом и грабли. Всё могло быть хорошо, если модуль один. (Вроде бы) Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
xvr 12 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Каждый модуль независим для компилятора и компилёр оптимизирует не проект, а данный модуль и если я в одном модуле только читаю а в другом только пишу переменную, то в обоих случаях если я не допишу volatile компилёр просто выкинет эти строки (просто примет за константу данные при компиляции) Нет. Компилятор ОБЯЗАН обеспечить состояние переменных, видимое с точки зрения программиста, в любой точке программы. volatile всего лишь заставляет компилятор считать, что состояние переменной может быть изменено не только тем, что написанно в программе. Т.е. компилятор не имеет права выкидывать любые записи и чтения этой переменной. Но он не обязан каким либо другим способом синхронизировать доступ к ней - это обязанность программиста. Например, если мы имеем код a=1; ... a=2; ... a=3; то для не volatile переменной компилятор может оставить только последнее присваивание (если в промежутке не было вызовов других функций), для volatile все присваивания останутся Вот в этом и грабли. Всё могло быть хорошо, если модуль один. (Вроде бы)От количества модулей это не зависит. А вот качество оптимизации может зависеть. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
DenisIV 0 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Нет. Компилятор ОБЯЗАН обеспечить состояние переменных, видимое с точки зрения программиста, в любой точке программы. volatile всего лишь заставляет компилятор считать, что состояние переменной может быть изменено не только тем, что написанно в программе. Т.е. компилятор не имеет права выкидывать любые записи и чтения этой переменной. Но он не обязан каким либо другим способом синхронизировать доступ к ней - это обязанность программиста. Например, если мы имеем код a=1; ... a=2; ... a=3; то для не volatile переменной компилятор может оставить только последнее присваивание (если в промежутке не было вызовов других функций), для volatile все присваивания останутся От количества модулей это не зависит. А вот качество оптимизации может зависеть. Согласен. А есть ли возможность указать компилятору в данном конкретном примере какой-нибудь командой #cmdxxx НЕ ОПТИМИЗИРОВАТЬ например именно строчку где a=2; ? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
sergeeff 1 24 декабря, 2008 Опубликовано 24 декабря, 2008 · Жалоба Уважаемый DenisIV! Если вы хотите быть "более продвинутым компилятором", чем имеющийся в вашем распоряжении компилятор, то вам надо это написать на ассемблере и тогда там точно будет выполняться то, что вы сами напишете. Но я все равно в толк не возьму, что за странные оптимизационные трюки вы хотите выполнять? На кой вам это сдалось? Я уже раньше отмечал, что современные компиляторы занимаются оптимизацией совместно с линкером. Об этом и Александреску в своих книгах пишет. Да и сами можете убедиться, сравнив ассемблерный листинг, генерируемый компилятором и дизассемблированный код. Так что замечания насчет оптимизации на уровне модуля тоже не совсем правомочны. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться