|
Переменная типа bool не инвертируется, Но если заменить на if, то всё работает) |
|
|
|
Apr 16 2014, 05:33
|

Познающий...
     
Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125

|
Добрый день! IAR 6.40, ARM. Это не работает, переменная не меняет своё значение при каждом вызове функции CODE void CSmcsCh::ledTask() { ledState = !ledState; CSmcsChHal::turnLed( ledState ); } А это работает CODE void CSmcsCh::ledTask() { if( ledState ) { ledState = false; } else { ledState = true; } CSmcsChHal::turnLed( ledState ); } ledState объявлена как приватный члена класса CSmcsCh. Вопрос: кто тупит?
--------------------
Выбор.
|
|
|
|
|
Apr 16 2014, 06:06
|

Познающий...
     
Группа: Свой
Сообщений: 2 963
Регистрация: 1-09-05
Из: г. Иркутск
Пользователь №: 8 125

|
1-й случай. CODE 55 void CSmcsCh::ledTask() 56 { 57 ledState = !ledState; \ _ZN7CSmcsCh7ledTaskEv: \ 00000000 0xF890 0x103C LDRB R1,[R0, #+60] \ 00000004 0xF081 0x0101 EOR R1,R1,#0x1 \ 00000008 0xF880 0x103C STRB R1,[R0, #+60] 58 /* 59 if( ledState ) 60 { 61 ledState = false; 62 } 63 else 64 { 65 ledState = true; 66 }*/ 67 CSmcsChHal::turnLed( ledState ); \ 0000000C 0x4608 MOV R0,R1 \ 0000000E 0x.... B.N _ZN10CSmcsChHal7turnLedEb 68 } 2-й случай. CODE 55 void CSmcsCh::ledTask() 56 { 57 // ledState = !ledState; 58 59 if( ledState ) \ _ZN7CSmcsCh7ledTaskEv: \ 00000000 0xF890 0x203C LDRB R2,[R0, #+60] \ 00000004 0x1E51 SUBS R1,R2,#+1 \ 00000006 0x4189 SBCS R1,R1,R1 \ 00000008 0x0FC9 LSRS R1,R1,#+31 \ 0000000A 0xF880 0x103C STRB R1,[R0, #+60] 60 { 61 ledState = false; 62 } 63 else 64 { 65 ledState = true; 66 } 67 CSmcsChHal::turnLed( ledState ); \ 0000000E 0xF890 0x003C LDRB R0,[R0, #+60] \ 00000012 0x.... B.N _ZN10CSmcsChHal7turnLedEb 68 } Сам я в асме не силён, но если мне память не изменяет, то такое поведение ИАРа у меня не в первой. Но раньше как-то не задевало, и обходил это if'ами.
--------------------
Выбор.
|
|
|
|
|
Apr 16 2014, 06:26
|
Гуру
     
Группа: Свой
Сообщений: 2 106
Регистрация: 23-10-04
Из: С-Петербург
Пользователь №: 965

|
А какое значение переменной было до входа в этот кусок программы? Дело в том, что когда идет if, то делается все честно, ноль считается за false, остальное - true. Когда Вы написали !LedState, то компилятор инвертирует только младший бит переменной - имеет право, если его внутреннее представление про true и false этому соответствует. Но если Ваша переменная имела значение, отличное от 0 и 1, то никакой инверсии не будет, т.к. поменяется только младший бит, переменная останется true, т.к. значение будет не 0.
|
|
|
|
|
Apr 16 2014, 07:42
|

Гуру
     
Группа: Модераторы
Сообщений: 8 455
Регистрация: 15-05-06
Из: Рига, Латвия
Пользователь №: 17 095

|
Цитата(megajohn @ Apr 16 2014, 10:29)  если без иннициализации, то должно было бы помочь ledState = !!!ledState; ( с тремя ! ) Почему? Результат оператора ! имеет тип bool, неявного преобразования его операнда к int, в процессе обратного преобразования от которого к bool сыграло бы правило "все, что не 0, то true", я тут не вижу.
--------------------
На любой вопрос даю любой ответ"Write code that is guaranteed to work, not code that doesn’t seem to break" ( C++ FAQ)
|
|
|
|
|
Apr 16 2014, 08:38
|
Гуру
     
Группа: Свой
Сообщений: 3 020
Регистрация: 7-02-07
Пользователь №: 25 136

|
Цитата(Сергей Борщ @ Apr 16 2014, 11:42)  Результат оператора ! имеет тип bool, неявного преобразования его операнда к int, в процессе обратного преобразования от которого к bool сыграло бы правило "все, что не 0, то true", я тут не вижу Даже не так. Результат оператора ! - это 0 или 1 по определению. Поэтому ! и !!! - это одно и то же. Другое дело, что компилятор вправе рассчитывать, что переменная типа bool содержит 0 или 1, отсюда и оптимизация (XOR). Если это условие нарушено (хотя бы из-за того, что переменная не инициализирована), то кодер сам дурак.
|
|
|
|
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0
|
|
|