реклама на сайте
подробности

 
 
> Детская ошибка
amiller
сообщение May 2 2016, 06:22
Сообщение #1


Частый гость
**

Группа: Участник
Сообщений: 176
Регистрация: 20-02-14
Из: Томск
Пользователь №: 80 612



Недавно столкнулся с одной странностью (по крайней мере для меня). Хотелось бы понять.
Есть фрагмент года (упрощенный до безобразия):
CODE

int16u temp1, temp2;
for (int32u i = 0; i < 10; i++)
{
temp1 = 0x0001;
temp2 = 0xFFFE;
if (~temp1 != temp2) continue;
temp2 = temp1;
}

Так вот, в этом фрагменте условный оператор и код после него никогда не выполняется. В отладчике после выполнения операции "temp2 = 0xFFFE;" происходит сразу переход на начало цикла. Переменные объявлены как int16u (== unsigned short (16 бит беззнаковое))
При этом никаких предупреждений на этапе компиляции.
Если переменные объявить как int32u (== unsigned long (32 бита беззнаковое)), то условный оператор выполняется, но естественно результат всегда true.
И код работает как надо только в таком варианте:
CODE

int16u temp1, temp2;
for (int32u i = 0; i < 10; i++)
{
temp1 = 0x0001;
temp2 = 0xFFFE;
temp1 = ~temp1;
if (temp1 != temp2) continue;
temp2 = temp1;
}

В этом случае выполняются все операторы, входящие в тело цикла.
IAR C/C++ Compiler for ARM 7.40.3.8902 (7.40.3.8902)
Добавлю: Оптимизация отключена. Проект под микроконтроллер STM32F105VCT6

Сообщение отредактировал amiller - May 2 2016, 06:41
Go to the top of the page
 
+Quote Post
 
Start new topic
Ответов
AleksBak
сообщение May 2 2016, 07:08
Сообщение #2


Частый гость
**

Группа: Участник
Сообщений: 132
Регистрация: 6-02-16
Из: г. Баку
Пользователь №: 90 364



А если так:
Код
int16u temp1, temp2;
    for (int32u i = 0; i < 10; i++)
    {
        temp1 = 0x0001;
        temp2 = 0xFFFE;
        if ( (int16u)(~temp1) != temp2 ) continue;
        temp2 = temp1;
    }
Go to the top of the page
 
+Quote Post
amiller
сообщение May 2 2016, 07:16
Сообщение #3


Частый гость
**

Группа: Участник
Сообщений: 176
Регистрация: 20-02-14
Из: Томск
Пользователь №: 80 612



Цитата(AleksBak @ May 2 2016, 10:08) *
А если так:
Код
int16u temp1, temp2;
    for (int32u i = 0; i < 10; i++)
    {
        temp1 = 0x0001;
        temp2 = 0xFFFE;
        if ( (int16u)(~temp1) != temp2 ) continue;
        temp2 = temp1;
    }

Так как Вы предлагаете, тоже работает. Хотя в этом меня тоже смущает один момент. После выполнения оператора "~" не должна меняться размерность переменной.
Но больше всего меня беспокоит результат компиляции первого моего примера. В ассемблерном коде вообще отсутствует условный оператор и всё, что после него.
И при этом никаких предупреждений от компилятора.
Как это можно рассматривать? Бага компилятора? Или есть более простое объяснение?
Go to the top of the page
 
+Quote Post
scifi
сообщение May 2 2016, 11:30
Сообщение #4


Гуру
******

Группа: Свой
Сообщений: 3 020
Регистрация: 7-02-07
Пользователь №: 25 136



Цитата(amiller @ May 2 2016, 10:16) *
Но больше всего меня беспокоит результат компиляции первого моего примера. В ассемблерном коде вообще отсутствует условный оператор и всё, что после него.

Вы будете смеяться, но компилятор вовсе не обязан на каждый чих в исходнике генерить код. Обычно на минимальном уровне оптимизации генерит, но тоже не всегда и не везде. Компилятор отвечает только за то, что сгенерированный код выдаст тот результат, который следует из исходника. Если исходник никакого результата не подразумевает, то компилятор может не генерировать ничего - и будет в своём праве.

Цитата(amiller @ May 2 2016, 11:21) *
1. Раньше во всех случаях, когда в коде был фрагмент, который никогда не выполняется, я получал от компилятора соответствующее предупреждение. В данном случае - нет.

Это вам показалось. Если припомните, какое именно было предупреждение, то поймёте, что в данном случае оно не применимо. А если не припомните, то это просто испорченный телефон. Короче, показалось.

Цитата(amiller @ May 2 2016, 11:21) *
Но в этом случае компилятор не выбрасывает из кода условный оператор и всё что после него.
Есть вероятность, что ответ на этот простой вопрос, как обычно, лежит в более сложных материях.

Не надо там искать сложных материй. В одном случае выкинул бессмысленный код, в другом - нет. Подумаешь - бывает сплошь и рядом. Компилятор - это просто программа, а не какое-то высшее существо с высшим разумом.
Go to the top of the page
 
+Quote Post
amiller
сообщение May 2 2016, 11:35
Сообщение #5


Частый гость
**

Группа: Участник
Сообщений: 176
Регистрация: 20-02-14
Из: Томск
Пользователь №: 80 612



Цитата(scifi @ May 2 2016, 14:26) *
Вы будете смеяться, но компилятор вовсе не обязан на каждый чих в исходнике генерить код. Обычно на минимальном уровне оптимизации генерит, но тоже не всегда и не везде. Компилятор отвечает только за то, что сгенерированный код выдаст тот результат, который следует из исходника. Если исходник никакого результата не подразумевает, то компилятор может не генерировать ничего - и будет в своём праве.

В этом с Вами я согласен, но предупредить то надо. Например если поставить внутри функции безусловный return, генерится предупреждение. А в данном случае всё происходит молча. Ну и не совсем понятен алгоритм. В одном случае молча выбрасывает код, а в другом очень похожем случае всё же генерит код, который тем не менее также не выполняется.

Например, если в том же примере заменить строку с условным оператором "if (true) continue;" то получаем предупреждение:
Warning[Pe111]: statement is unreachable - что логично. А в моем примере это происходило "молча".

Тем не менее всем спасибо!
Ошибка локализована. И с утверждением, что компилятор "не обязан", я согласен. Остальное в общем то уже нюансы функционирования программы, которой также является и компилятор.

Сообщение отредактировал amiller - May 2 2016, 11:44
Go to the top of the page
 
+Quote Post
Tahoe
сообщение May 6 2016, 04:58
Сообщение #6


Местный
***

Группа: Свой
Сообщений: 459
Регистрация: 30-03-06
Из: Москва
Пользователь №: 15 600



Цитата(amiller @ May 2 2016, 14:35) *
Ошибка локализована. И с утверждением, что компилятор "не обязан", я согласен. Остальное в общем то уже нюансы функционирования программы, которой также является и компилятор.

1. Странно, что локализована. Лично мне резануло глаз присваивание константы в цикле, при том что константа объявлена не volatile. Стало быть, весь цикл вообще теряет смысл. И никакие неявные приведения типов тут вообще ни причем.

2. Упрощения, это хорошо. Но приводить упрощенный Си-код вне функции, дело бесполезное. Хотя бы потому, что не понятно, переменные temp1 и temp2 локальные или глобальные.

3. Насчет обязан или не обязан компилер. Конечно не обязан, его дело компилировать. Зато статический анализатор кода сразу завопил бы, с негодованием. Благо в последних IAR встроен C-Stat. Настоятельно рекомендую натравить его на код. Гарантирую(с), он еще много "чудес" выявит в коде. wink.gif
Go to the top of the page
 
+Quote Post
GetSmart
сообщение May 9 2016, 16:00
Сообщение #7


.
******

Группа: Участник
Сообщений: 4 005
Регистрация: 3-05-06
Из: Россия
Пользователь №: 16 753



Цитата(Tahoe @ May 6 2016, 08:58) *
3. Насчет обязан или не обязан компилер. Конечно не обязан, его дело компилировать. Зато статический анализатор кода сразу завопил бы, с негодованием. Благо в последних IAR встроен C-Stat. Настоятельно рекомендую натравить его на код. Гарантирую(с), он еще много "чудес" выявит в коде. wink.gif

Если в законе что-то не написано прямым текстом, то работает принцип аналогии.

Ещё со времён динозавров, компиляторы паскаля, си и многих других языков выдавали сообщение/варнинг при сравнении беззнаковой переменной со знаковой константой или или переменной с константой вне диапазона этой переменной. В примере топикстартера есть аналогичные признаки: сравнение двух выражений, которые заведомо вне диапазона друг друга. Программер имеет право ожидать, что ОБНАРУЖИВ подобную ситуацию, компилятор укажет на неё аналогично константе.

Если компилятор не слишком оптимизирующий, то он действительно может не выдавать сообщение, т.к. во время компиляции эту ситуацию не видит. Компилятор, опознавший always-result в выражении с переменными всё-таки должен (ака вектор эволюции) выдавать сообщение, по аналогии с другими предупреждениями. И профсоюз по защите прав программистов должен лоббировать эти правила )))

Молчание ИАРа тянет на недоработку. Если в публичных и непубличных нормативах не было явно указано на данную ситуацию.


--------------------
Заблуждаться - Ваше законное право :-)
Go to the top of the page
 
+Quote Post

Сообщений в этой теме
- amiller   Детская ошибка   May 2 2016, 06:22
|- - Сергей Борщ   QUOTE (amiller @ May 2 2016, 10:16) После...   May 2 2016, 07:24
||- - amiller   Цитата(Сергей Борщ @ May 2 2016, 10:24) М...   May 2 2016, 07:36
||- - Сергей Борщ   QUOTE (amiller @ May 2 2016, 10:36) Ну а ...   May 2 2016, 08:09
||- - amiller   Цитата(Сергей Борщ @ May 2 2016, 11:09) Д...   May 2 2016, 08:21
|- - AleksBak   Цитата(amiller @ May 2 2016, 15:35) В это...   May 2 2016, 12:20
|- - GetSmart   Цитата(amiller @ May 2 2016, 15:35) В это...   May 2 2016, 13:49
||- - Baser   Цитата(GetSmart @ May 2 2016, 16:49) Обна...   May 2 2016, 16:18
||- - ViKo   Цитата(GetSmart @ May 2 2016, 16:49) Обна...   May 2 2016, 16:19
||- - Огурцов   Цитата(GetSmart @ May 2 2016, 13:49) Хоро...   May 2 2016, 16:36
||- - jcxz   Цитата(GetSmart @ May 2 2016, 19:49) Код{...   May 3 2016, 15:33
||- - GetSmart   Цитата(jcxz @ May 3 2016, 19:33) И что в ...   May 3 2016, 16:23
||- - zltigo   QUOTE (GetSmart @ May 3 2016, 19:23) Искр...   May 3 2016, 19:47
||- - GetSmart   Цитата(zltigo @ May 3 2016, 23:47) Так чт...   May 3 2016, 21:42
|- - amiller   Цитата(Tahoe @ May 6 2016, 07:58) 1. Стра...   May 6 2016, 06:23
||- - Tahoe   Цитата(amiller @ May 6 2016, 09:23) Если ...   May 6 2016, 08:32
|||- - scifi   Цитата(Tahoe @ May 6 2016, 11:32) Еще раз...   May 6 2016, 08:45
|||- - amiller   Цитата(Tahoe @ May 6 2016, 11:32) Еще раз...   May 6 2016, 08:58
|||- - zltigo   QUOTE (amiller @ May 6 2016, 11:58) И в о...   May 6 2016, 13:44
|||- - amiller   Цитата(zltigo @ May 6 2016, 16:44) Опять ...   May 6 2016, 14:19
|||- - scifi   Цитата(amiller @ May 6 2016, 17:19) 1. Ес...   May 6 2016, 15:29
||||- - Огурцов   Цитата(scifi @ May 6 2016, 16:29) Предупр...   May 7 2016, 16:57
||||- - scifi   Цитата(Огурцов @ May 7 2016, 19:57) а не ...   May 7 2016, 18:27
|||- - Tahoe   Цитата(amiller @ May 6 2016, 17:19) 1. Ес...   May 6 2016, 16:31
||||- - amiller   Цитата(Tahoe @ May 6 2016, 19:31) Последн...   May 7 2016, 02:52
||||- - Tahoe   Цитата(amiller @ May 7 2016, 05:52) Предс...   May 7 2016, 05:14
||||- - amiller   Цитата(Tahoe @ May 7 2016, 08:14) Предста...   May 7 2016, 05:37
||||- - svss   Цитата(amiller @ May 7 2016, 11:37) ... 5...   May 7 2016, 09:24
|||||- - zltigo   QUOTE (svss @ May 7 2016, 12:24) не полаг...   May 7 2016, 10:25
||||- - Tahoe   Цитата(amiller @ May 7 2016, 08:37) А кро...   May 7 2016, 13:47
||||- - amiller   Цитата(Tahoe @ May 7 2016, 16:47) Так мож...   May 7 2016, 14:04
||||- - Tahoe   Цитата(amiller @ May 7 2016, 17:04) сразу...   May 7 2016, 16:06
||||- - amiller   Цитата(Tahoe @ May 7 2016, 19:06) Не поня...   May 7 2016, 17:33
|||- - Сергей Борщ   QUOTE (amiller @ May 6 2016, 17:19) 2. Од...   May 6 2016, 21:37
||- - halfdoom   Цитата(amiller @ May 6 2016, 09:23) Если ...   May 9 2016, 06:43
||- - amiller   Цитата(halfdoom @ May 9 2016, 09:43) Где-...   May 9 2016, 07:54
|- - zltigo   QUOTE (GetSmart @ May 9 2016, 19:00) Ещё ...   May 9 2016, 16:11
- - aiwa   Вообще-то да, это работа не компилятора, но редакт...   May 4 2016, 11:59
- - aiwa   Цитата(amiller @ May 7 2016, 08:37) 2. .....   May 7 2016, 07:59
- - aiwa   Цитата(Огурцов @ May 7 2016, 19:57) а не ...   May 7 2016, 20:41
- - Огурцов   вы можете между собой договориться, есть в предпис...   May 7 2016, 21:59
- - aiwa   Цитата(Огурцов @ May 8 2016, 00:59) вы мо...   May 7 2016, 22:31
|- - zltigo   QUOTE (aiwa @ May 8 2016, 01:31) Причем, ...   May 8 2016, 03:44
|- - Огурцов   Цитата(aiwa @ May 7 2016, 22:31) А о чем ...   May 8 2016, 06:05
|- - jcxz   Цитата(Огурцов @ May 8 2016, 12:05) о сво...   May 8 2016, 06:18
||- - Огурцов   > Выбросил 2+3, заменил на 5. Сообщать? скорее ...   May 8 2016, 06:53
||- - jcxz   Цитата(Огурцов @ May 8 2016, 12:53) >В...   May 8 2016, 13:30
||- - Огурцов   Цитата(jcxz @ May 8 2016, 13:30) Каким бо...   May 8 2016, 14:53
|- - ViKo   Цитата(Огурцов @ May 8 2016, 09:05) о сво...   May 8 2016, 06:18
|- - jcxz   Цитата(ViKo @ May 8 2016, 12:18) У Кейла ...   May 8 2016, 06:32
|- - ViKo   Цитата(jcxz @ May 8 2016, 09:32) IAR всё ...   May 8 2016, 07:18
- - ViKo   Прочитав тему еще раз, понял, что топикстартер при...   May 8 2016, 05:55
|- - amiller   Цитата(ViKo @ May 8 2016, 08:55) Прочитав...   May 8 2016, 09:07
- - ViKo   Keil Example1 CODE; generated by Component: ARM Co...   May 8 2016, 10:35
- - aiwa   Цитата(Огурцов @ May 8 2016, 09:05) о сво...   May 8 2016, 12:13
|- - amiller   Цитата(aiwa @ May 8 2016, 15:13) Так он в...   May 8 2016, 12:24
- - aiwa   Цитата(zltigo @ May 8 2016, 06:44) Маразм...   May 8 2016, 12:29
- - ViKo   И во что же должно продвинуться беззнаковое uint16...   May 8 2016, 12:34
- - aiwa   Цитата(amiller @ May 8 2016, 15:24) Вроде...   May 8 2016, 12:54
- - aiwa   Цитата(jcxz @ May 8 2016, 16:30) Хмммм......   May 8 2016, 14:27
- - ViKo   Правильно, продвигается до знакового целого. Но по...   May 8 2016, 14:37
|- - jcxz   Цитата(ViKo @ May 8 2016, 20:37) Правильн...   May 8 2016, 16:41
|- - Огурцов   Цитата(jcxz @ May 8 2016, 17:41) Ещё раз ...   May 8 2016, 18:19
|- - jcxz   Цитата(Огурцов @ May 9 2016, 00:19) ещё р...   May 9 2016, 08:59
- - aiwa   Цитата(ViKo @ May 8 2016, 17:37) Правильн...   May 8 2016, 14:43
- - ViKo   О! Может, топикстартер все же напутал с опреде...   May 8 2016, 14:45
|- - amiller   Цитата(ViKo @ May 8 2016, 17:45) О! М...   May 8 2016, 15:04
- - aiwa   Цитата(ViKo @ May 8 2016, 17:45) О! М...   May 8 2016, 15:24
- - ViKo   Почему никто не комментирует листинги от Кейла? Вс...   May 8 2016, 15:45
- - aiwa   Цитата(ViKo @ May 8 2016, 18:40) Почему н...   May 8 2016, 15:53
- - ViKo   Кейл, он же Кайл, он же Keil (нем.), он же куплен ...   May 8 2016, 15:57
|- - scifi   Цитата(ViKo @ May 8 2016, 18:57) Кейл, он...   May 8 2016, 16:43
|- - jcxz   Цитата(ViKo @ May 8 2016, 21:57) Кейл, он...   May 8 2016, 17:00
- - aiwa   Цитата(ViKo @ May 8 2016, 18:57) Кейл, он...   May 8 2016, 16:20
- - ViKo   Дополню для ясности. У Cortex-M команды - THUMB2 -...   May 8 2016, 18:11
- - ViKo   Таки да, операция ~temp1 дает число 0xFFFFFFFE. Во...   May 8 2016, 19:42
- - aiwa   Цитата(ViKo @ May 8 2016, 22:42) Таки да,...   May 8 2016, 22:52
- - aiwa   Цитата(halfdoom @ May 9 2016, 09:43) Пере...   May 9 2016, 11:10
|- - zltigo   QUOTE (aiwa @ May 9 2016, 14:10) В резуль...   May 9 2016, 11:56
||- - svss   Цитата(zltigo @ May 9 2016, 17:56) Если ...   May 10 2016, 05:13
|- - halfdoom   Цитата(aiwa @ May 9 2016, 14:10) В резуль...   May 9 2016, 14:51
- - aiwa   Цитата(zltigo @ May 9 2016, 14:56) Если ...   May 9 2016, 12:41
|- - scifi   Цитата(aiwa @ May 9 2016, 15:41) Вы вопро...   May 9 2016, 12:49
||- - jcxz   Цитата(scifi @ May 9 2016, 18:49) Было бы...   May 9 2016, 16:51
|- - zltigo   QUOTE (aiwa @ May 9 2016, 15:41) Вы вопро...   May 9 2016, 13:38
|- - dxp   QUOTE (zltigo @ May 9 2016, 19:38) Python...   May 9 2016, 16:29
|- - zltigo   QUOTE (dxp @ May 9 2016, 19:29) Питон - в...   May 9 2016, 16:57
|- - dxp   QUOTE (zltigo @ May 9 2016, 22:57) Ага. Б...   May 10 2016, 06:57
- - aiwa   Цитата(halfdoom @ May 9 2016, 17:51) Если...   May 9 2016, 23:30
|- - halfdoom   Цитата(aiwa @ May 10 2016, 02:30) наводит...   May 10 2016, 04:20
|- - aiwa   Цитата(halfdoom @ May 10 2016, 07:20) Ста...   May 10 2016, 07:58
|- - scifi   Цитата(aiwa @ May 10 2016, 10:58) повторю...   May 10 2016, 08:13
|- - halfdoom   Цитата(aiwa @ May 10 2016, 10:58) Все дов...   May 10 2016, 08:49
- - aiwa   Цитата(scifi @ May 10 2016, 11:13) Код, к...   May 10 2016, 09:43
2 страниц V   1 2 >


Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 20th July 2025 - 10:28
Рейтинг@Mail.ru


Страница сгенерированна за 0.0159 секунд с 7
ELECTRONIX ©2004-2016