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

 
 
5 страниц V   1 2 3 > »   
Reply to this topicStart new topic
> Ошибка IAR или чтото еще?
Sergio66
сообщение Dec 18 2006, 12:47
Сообщение #1


Местный
***

Группа: Свой
Сообщений: 235
Регистрация: 9-02-05
Пользователь №: 2 526



Столкнулся со следующей проблемой:
Использую IAR 4.20А
В программе (в функции) перемножаю два числа типа long int. Одно из них - локальная временная переменная (для упрощения расчетов). Результат умножения получается неверным (просто бред!). АВР СТУДИО показывает, что компиллятор размещает временную переменную в регистрах.
Вылечил данную проблему тем, что правдами - неправдами добился того, чтобы компиллятор разместил данную переменную в памяти. Вот только тогда все и заработало.
Кто нибудь может прокомментировать этот случай?
Go to the top of the page
 
+Quote Post
aesok
сообщение Dec 18 2006, 13:06
Сообщение #2


Знающий
****

Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484



Показывайте код.
Go to the top of the page
 
+Quote Post
Sergio66
сообщение Dec 18 2006, 13:15
Сообщение #3


Местный
***

Группа: Свой
Сообщений: 235
Регистрация: 9-02-05
Пользователь №: 2 526



Цитата(aesok @ Dec 18 2006, 13:06) *
Показывайте код.


Вот такой код:
unsigned long int temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;
тип INJ_time - unsigned long int. Эта переменная локальная.
PRODUCTIVITY - константа
Так вот, переменная temp размещалась компилятором в регистрах и все было плохо

Теперь я переменную temp сделал членом локальной структуры data_temp_struct
Т.о. она стала размещаться в памяти а не в регистрах. Вот с этого все и заработало.
data_temp_struct.temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;
Go to the top of the page
 
+Quote Post
_Bill
сообщение Dec 18 2006, 14:48
Сообщение #4


Местный
***

Группа: Участник
Сообщений: 416
Регистрация: 18-04-06
Из: Челябинск
Пользователь №: 16 219



Цитата(Sergio66 @ Dec 18 2006, 13:15) *
Вот такой код:
unsigned long int temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;
тип INJ_time - unsigned long int. Эта переменная локальная.
PRODUCTIVITY - константа
Так вот, переменная temp размещалась компилятором в регистрах и все было плохо

Теперь я переменную temp сделал членом локальной структуры data_temp_struct
Т.о. она стала размещаться в памяти а не в регистрах. Вот с этого все и заработало.
data_temp_struct.temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;

Ну, так все правильно. Компилятор перед генерацией производит свертку констант, т.е. вычисляет значение PRODUCTIVITY / 20000. Естественно, оно будет вычисленно неточно. Поставьте в выражении скобки в нужных местах. Еще советую объявить константы как long, тогда погрешность в вычислении уменьшится.
Go to the top of the page
 
+Quote Post
Sergio66
сообщение Dec 18 2006, 15:01
Сообщение #5


Местный
***

Группа: Свой
Сообщений: 235
Регистрация: 9-02-05
Пользователь №: 2 526



Цитата(_Bill @ Dec 18 2006, 14:48) *
Цитата(Sergio66 @ Dec 18 2006, 13:15) *

Вот такой код:
unsigned long int temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;
тип INJ_time - unsigned long int. Эта переменная локальная.
PRODUCTIVITY - константа
Так вот, переменная temp размещалась компилятором в регистрах и все было плохо

Теперь я переменную temp сделал членом локальной структуры data_temp_struct
Т.о. она стала размещаться в памяти а не в регистрах. Вот с этого все и заработало.
data_temp_struct.temp = INJ_time * data_temp_struct.FREQ * PRODUCTIVITY / 20000;

Ну, так все правильно. Компилятор перед генерацией производит свертку констант, т.е. вычисляет значение PRODUCTIVITY / 20000. Естественно, оно будет вычисленно неточно. Поставьте в выражении скобки в нужных местах. Еще советую объявить константы как long, тогда погрешность в вычислении уменьшится.


А что, если переменная размещена не в регистрах, а в памяти, свертка констант не производится? Или это происходит как то иначе?
Я ведт ничего не поменял, просто добился иного размещения в памяти переменной!!! И никаких скобок.И без них все заработало. Нет! Дело не в этом!!!
Go to the top of the page
 
+Quote Post
aesok
сообщение Dec 18 2006, 15:18
Сообщение #6


Знающий
****

Группа: Участник
Сообщений: 596
Регистрация: 26-05-06
Из: Москва
Пользователь №: 17 484



Опишите проблемму полностью:

Как переменые и структуры объявленны, полный код где они используються, используются ли в прерываниях, что нужно получить, что происходит в действительности.


Анатлий.

Сообщение отредактировал aesok - Dec 18 2006, 15:23
Go to the top of the page
 
+Quote Post
Dog Pawlowa
сообщение Dec 18 2006, 15:28
Сообщение #7


Гуру
******

Группа: Свой
Сообщений: 2 702
Регистрация: 14-07-06
Пользователь №: 18 823



Цитата(Sergio66 @ Dec 18 2006, 15:01) *
А что, если переменная размещена не в регистрах, а в памяти, свертка констант не производится? Или это происходит как то иначе?
Я ведт ничего не поменял, просто добился иного размещения в памяти переменной!!! И никаких скобок.И без них все заработало. Нет! Дело не в этом!!!

Послушайте! :-)
Вам предлагают дело - записать формулу ПРАВИЛЬНО.
Разбираться в особенностях компилятора в случае неправильной записи - очень неблагодарное дело.
А еще можно начать разбираться в особенностях различных компиляторов. Путь в никуда.
Меня такие вещи давно не беспокоят - побольше скобок и преобразования типов.
И ффсе! smile.gif


--------------------
Уходя, оставьте свет...
Go to the top of the page
 
+Quote Post
Sergio66
сообщение Dec 18 2006, 15:44
Сообщение #8


Местный
***

Группа: Свой
Сообщений: 235
Регистрация: 9-02-05
Пользователь №: 2 526



Цитата(Dog Pawlowa @ Dec 18 2006, 15:28) *
Цитата(Sergio66 @ Dec 18 2006, 15:01) *

А что, если переменная размещена не в регистрах, а в памяти, свертка констант не производится? Или это происходит как то иначе?
Я ведт ничего не поменял, просто добился иного размещения в памяти переменной!!! И никаких скобок.И без них все заработало. Нет! Дело не в этом!!!

Послушайте! :-)
Вам предлагают дело - записать формулу ПРАВИЛЬНО.
Разбираться в особенностях компилятора в случае неправильной записи - очень неблагодарное дело.
А еще можно начать разбираться в особенностях различных компиляторов. Путь в никуда.
Меня такие вещи давно не беспокоят - побольше скобок и преобразования типов.
И ффсе! smile.gif

Скобки расставлял. Это ни к чему не привело. Проблема исчезла повторяю только после того, как переменная была размещена в памяти а не в регистрах!!!
Go to the top of the page
 
+Quote Post
prottoss
сообщение Dec 18 2006, 15:45
Сообщение #9


Гуру
******

Группа: Свой
Сообщений: 2 720
Регистрация: 24-03-05
Пользователь №: 3 659



Цитата(Dog Pawlowa @ Dec 18 2006, 19:28) *
Послушайте! :-)
Вам предлагают дело - записать формулу ПРАВИЛЬНО.
Разбираться в особенностях компилятора в случае неправильной записи - очень неблагодарное дело.
А еще можно начать разбираться в особенностях различных компиляторов. Путь в никуда.
Меня такие вещи давно не беспокоят - побольше скобок и преобразования типов.
И ффсе! smile.gif
Сказанно, если размещать переменную локально, не вычисляется, если глобально - вычислятся - при чем тут скобки???


--------------------
Go to the top of the page
 
+Quote Post
singlskv
сообщение Dec 18 2006, 16:11
Сообщение #10


дятел
*****

Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065



Цитата(Sergio66 @ Dec 18 2006, 12:47) *
Столкнулся со следующей проблемой:
Использую IAR 4.20А
В программе (в функции) перемножаю два числа типа long int. Одно из них - локальная временная переменная (для упрощения расчетов). Результат умножения получается неверным (просто бред!). АВР СТУДИО показывает, что компиллятор размещает временную переменную в регистрах.
Вылечил данную проблему тем, что правдами - неправдами добился того, чтобы компиллятор разместил данную переменную в памяти. Вот только тогда все и заработало.
Кто нибудь может прокомментировать этот случай?

Если Вы смотрите на получаемое значение в окошке Watch AVR Studio, то тогда у Вас
все в порядке. Смотрите на результат в регистрах он там правильный.

AVR Studio НЕ гарантирует что локальные переменные соптимизированные компилятором
(хранящиеся в регистрах) будут правильно показываться в Watch.

А скобочки все-таки поставьте
конечно если у Вас PRODUCTIVITY / 20000 - целое, тады не надо smile.gif
Go to the top of the page
 
+Quote Post
Dog Pawlowa
сообщение Dec 18 2006, 16:46
Сообщение #11


Гуру
******

Группа: Свой
Сообщений: 2 702
Регистрация: 14-07-06
Пользователь №: 18 823



Цитата(prottoss @ Dec 18 2006, 15:45) *
Сказанно, если размещать переменную локально, не вычисляется, если глобально - вычислятся - при чем тут скобки???

1. Было сказано так "побольше скобок И ПРЕОБРАЗОВАНИЯ ТИПОВ".
2. Ообще-тоавтор он мог бы разместить здесь ассемблерный текст и гадание на гуще не состоялось бы.
2. Видел подобный случай - я работал под IAR, клиент стал компилировать под ICC. Результат усреднения значений АЦП считался по разному. Именно из-за особенностей работы компилятора в случае некорректного написания программы. И что? И ничего.


--------------------
Уходя, оставьте свет...
Go to the top of the page
 
+Quote Post
prottoss
сообщение Dec 18 2006, 17:08
Сообщение #12


Гуру
******

Группа: Свой
Сообщений: 2 720
Регистрация: 24-03-05
Пользователь №: 3 659



Цитата(Dog Pawlowa @ Dec 18 2006, 20:46) *
Цитата(prottoss @ Dec 18 2006, 15:45) *

Сказанно, если размещать переменную локально, не вычисляется, если глобально - вычислятся - при чем тут скобки???

1. Было сказано так "побольше скобок И ПРЕОБРАЗОВАНИЯ ТИПОВ".
Это было сказанно, вернее посоветованна, Вами, и товарищем aesok. Смысл же вопроса автора топика был именно в том, что сказал я - если размещать переменную локально, не вычисляется, если глобально - вычислятся , при чем здесь cкобки, позвольте? У меня, в данный момент, есть тоже подобный фокус в программе, которой сейчас занимаюсь. Если обсуждаемая сдесь проблема не решится, поделюсь своей...


--------------------
Go to the top of the page
 
+Quote Post
Oldring
сообщение Dec 18 2006, 17:27
Сообщение #13


Гуру
******

Группа: Свой
Сообщений: 3 041
Регистрация: 10-01-05
Из: Москва
Пользователь №: 1 874



Цитата(_Bill @ Dec 18 2006, 14:48) *
Ну, так все правильно. Компилятор перед генерацией производит свертку констант, т.е. вычисляет значение PRODUCTIVITY / 20000. Естественно, оно будет вычисленно неточно. Поставьте в выражении скобки в нужных местах. Еще советую объявить константы как long, тогда погрешность в вычислении уменьшится.


Не имеет права. Ассоциативность этих операций фиксирована - слева направа.

Нужно сравнивать листинг того, как получается неправильно, и того, как получается правильно. Иначе можно много фантазировать.

Цитата(Dog Pawlowa @ Dec 18 2006, 15:28) *
Вам предлагают дело - записать формулу ПРАВИЛЬНО.


Все записано правильно.

Но нужно бы еще выяснить, какие диапазоны переменных и чему точно равны константы.


--------------------
Пишите в личку.
Go to the top of the page
 
+Quote Post
Dog Pawlowa
сообщение Dec 18 2006, 18:48
Сообщение #14


Гуру
******

Группа: Свой
Сообщений: 2 702
Регистрация: 14-07-06
Пользователь №: 18 823



Цитата(prottoss @ Dec 18 2006, 17:08) *
Цитата(Dog Pawlowa @ Dec 18 2006, 20:46) *
Цитата(prottoss @ Dec 18 2006, 15:45) *

Сказанно, если размещать переменную локально, не вычисляется, если глобально - вычислятся - при чем тут скобки???

1. Было сказано так "побольше скобок И ПРЕОБРАЗОВАНИЯ ТИПОВ".
Это было сказанно, вернее посоветованна, Вами, и товарищем aesok. Смысл же вопроса автора топика был именно в том, что сказал я - если размещать переменную локально, не вычисляется, если глобально - вычислятся , при чем здесь cкобки, позвольте? У меня, в данный момент, есть тоже подобный фокус в программе, которой сейчас занимаюсь. Если обсуждаемая сдесь проблема не решится, поделюсь своей...
Видимо, Вы не поняли смысла того, что хотел сказать я. wink.gif Если есть малейшая возможность, что компилятор "спровоцирован" некорректным текстом, то лучше эту возможность исключить.

Цитата(Oldring @ Dec 18 2006, 17:27) *
Цитата(Dog Pawlowa @ Dec 18 2006, 15:28) *

Вам предлагают дело - записать формулу ПРАВИЛЬНО.

Все записано правильно.
Но нужно бы еще выяснить, какие диапазоны переменных и чему точно равны константы.
Тогда мы по разному понимает слово "правильно". Я включал в это понятие учет возможности переполнения и максимальной независимости от констант. А Вы - нет? smile.gif


--------------------
Уходя, оставьте свет...
Go to the top of the page
 
+Quote Post
Oldring
сообщение Dec 18 2006, 19:08
Сообщение #15


Гуру
******

Группа: Свой
Сообщений: 3 041
Регистрация: 10-01-05
Из: Москва
Пользователь №: 1 874



Цитата(Dog Pawlowa @ Dec 18 2006, 18:48) *
Тогда мы по разному понимает слово "правильно". Я включал в это понятие учет возможности переполнения и максимальной независимости от констант. А Вы - нет? smile.gif


Дело в том, что Билл написал просто чепуху про "естественную" свертку целочисленных констант перед вычислением выражения, а Вашего предложения я вообще почему-то не вижу в истории переписки. Так как так и не была озвучена информация про диапазоны операндов, хотелось бы все-таки увидеть, что именно Вы считаете "правильной" записью данного выражения, если это понятие "правильности" отличется от формальной правильности. Хотелось бы также узнать Ваше мнение по следующему вопросу: существует ли с точки зрения стандарта языка программирования С какая-либо разница между выражениями

Код
a * b * c / d


и

Код
((a * b) * c)  / d


?

И, кстати, считаете ли Вы что компилятор имеет право выражение

Код
a = b * 2 / 3;


заменить на

Код
a = 0;


?


--------------------
Пишите в личку.
Go to the top of the page
 
+Quote Post

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

 


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


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