Перейти к содержанию
    

Как использовать переменные типа volatile и одновременно пользоваться стандартными библиотеками, где все сплошником char*.

Приходится везде вписыать что то типа:

volatile char Buf1[100], Buf2[100];

.....

memcopy((char*)Buf1,(char*)Buf2,20);

.....

Если же Buf не будут volatile, то оптимизатор выбрасывает строки типа: Buf1[0]=7;

Может как то можно переопределить в билиотеках char на volatile char, ну или еще как то справится с этими неудобствами?

Изменено пользователем vlad_new

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Если же Buf не будут volatile, то оптимизатор выбрасывает строки типа: Buf1[0]=7;

А почему это проблема? Если выбрасывает, значит они не нужны.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А почему это проблема? Если выбрасывает, значит они не нужны.

 

Вот пример кода.

Заполняем массив Buf_RS485 и отправляем его в UART. Первый байт в массиве определяет его длинну.

Первые 2 строки после case00: копируют некие данные известной длинны. Поэтому в следующей строке эта длинна и записывается.

Далее, если есть Cnt_sob, то туда еще кучка всего вписывается и другая длинна перезаписывается.

Таким образом отправляется либо короткий, либо более длинный пакет.

Так вот 3 строку оптимизатор игнорирует и пакет отправляется с неверной длинной!

 

vu8  Buf_RS485[256];  // Глобальная

void sw_get(void)
{
u32 i, j, k, u; 

switch(GetSet)
  {

  case 0x00: Pool=1; RX_RS485=1;                                
             memcpy((char*)Buf_RS485+1,Mac_mas_bcd,4);  
             memcpy((char*)Buf_RS485+5,Mac_sl_bcd,4); u=9;
             Buf_RS485[0]=u-1;                                   

             if(Cnt_sob)                 
               {
               j=EE_rd_byte(UK_WRS);      
               if(j>=Cnt_sob) k=j-Cnt_sob;
               else k=KOL_BUF-(Cnt_sob-j);
               k=k*LEN_SOB+BAZA_S; i=0;
               EE_rd_nbyte(k,Buf_tmp,64); Buf_tmp[64]=0;  
               k=strlen((char*)Buf_tmp); k=k-6; Buf_RS485[u++]=k|0x40;
               for(i=0; i<12; i=i+2,u++)
                 Buf_RS485[u]=((Buf_tmp[i]-0x30)<<4)|((Buf_tmp[i+1]-0x30)&0xF);
               for(i=0; i<(k-6); i++) Buf_RS485[u++]=Buf_tmp[i+12];
               Buf_RS485[0]=u-1;                                 
               }

             SEND_RS485; return;
.........
   }

Изменено пользователем IgorKossak
[code]

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Несовсем понятно о какой строчке идёт речь. Можекте пометить её в исходнике?

Изменено пользователем Genadi Zawidowski

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Несовсем понятно о какой строчке идёт речь. Можекте пометить её в исходнике?

Угу. Пометил. Вот эта имелась ввиду:

Buf_RS485[0]=u-1;

Изменено пользователем vlad_new

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Этот код какой-то кривой. Например, переменная 'char Buf_RS485;' используется как массив. Что это? Неточно запостили? Будьте любезны постить реальный код. Кто знает, что Вы там ещё переиначили? И лучше с отступами, а также обрамлять тегами (code)(/code).

Вы подозреваете баг в компиляторе, а я подозреваю баг в программе. Чаще бывает второе.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Этот код какой-то кривой. Например, переменная 'char Buf_RS485;' используется как массив. Что это? Неточно запостили? Будьте любезны постить реальный код. Кто знает, что Вы там ещё переиначили? И лучше с отступами, а также обрамлять тегами (code)(/code).

Вы подозреваете баг в компиляторе, а я подозреваю баг в программе. Чаще бывает второе.

Уже подправил. Реальный код слишком длинный. К тому же похожие проблеммы с оптимизатором не редки. И как правило когда индекс =0, или он const.

Иногда помагало обозвать переменную индекса массива как static. Но вот в этом куске бубны с танцами не помогли.

Изменено пользователем vlad_new

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Уже подправил. Реальный код слишком длинный. К тому же похожие проблеммы с оптимизатором не редки. И как правило когда индекс =0, или он const.

Иногда помагало обозвать переменную индекса массива как static. Но вот в этом куске бубны с танцами не помогли.

Это глюки в программе с вероятностью 99%.

Поскольку реальный код видеть нет возможности, то больше сказать нечего. Даже если бы был реальный код, было бы слишком трудно в нём разобраться, так как написан он (если судить по показанному отрывку) не самым лучшим образом, мягко говоря.

 

Update:

Забыл добавить. О глюках судят по результатам выполнения программы. Например, если содержимое пакета данных на проводе отличается от ожидаемого. Если Вы смотрите на содержимое переменных в отладчике и видите неожиданные значения - не факт, что это глюк. На высоких уровнях оптимизации бывает так, что данные отладчика весьма слабо коррелируют с исходным кодом. И вообще отлаживать удобнее на самом низком уровне оптимизации.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Это глюки в программе с вероятностью 99%.

Поскольку реальный код видеть нет возможности, то больше сказать нечего. Даже если бы был реальный код, было бы слишком трудно в нём разобраться, так как написан он (если судить по показанному отрывку) не самым лучшим образом, мягко говоря.

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

Buf_RS485 описать как vu8 ( volatile unsigned char ), но тогда в сотнях местах приходится вписывать явное преобразование типов. memcopy((char*)Buf_RS485,.... )

 

Updete: Да я в таких случиях смотрю код ассемблера. А о веревке: Так и есть другое устройство принимает пакет с ошибочной длинной.

 

Изменено пользователем vlad_new

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Реальный код слишком длинный. К тому же похожие проблеммы с оптимизатором не редки.

Если проблемы не редки, то почти наверняка оптимизатор ни при чем. Вам в любом случае надо локализовать проблему, и оформить её в виде изолированного фрагмента - или чтобы аргументированно обвинить оптимизатор, или чтобы разобраться с изъянами своего кода. И уж точно не стоит "лечить" программу, добавляя разнообразные квалификаторы там, где они объективно не нужны.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

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

 

Потому что Вы не оформили свой код в теги [сode] [/сode]

 

Если бы оформили - все бы отсупало:

 с начала
      с отступом 8 пробелов

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А на счет глюков в программе: ну так она же работает если без оптимизатора или Buf_RS485 описать как vu8 ( volatile unsigned char ), но тогда в сотнях местах приходится вписывать явное преобразование типов. memcopy((char*)Buf_RS485,.... )

В сотнях мест?!! О ужас! Вероятность глюка в программе приблизилась к 99,9%.

Зачем вообще включаете оптимизацию? Если работает - не трогайте. Не открывайте ящик Пандоры. Есть большой класс ошибок, чувствительных к уровню оптимизации. Они Вам нужны?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Потому что Вы не оформили свой код в теги [сode] [/сode]

 

Если бы оформили - все бы отсупало:

 с начала
      с отступом 8 пробелов

Не знал что так надо. Век живи век учись. Ща попробую.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А на счет глюков в программе: ну так она же работает если без оптимизатора или

Buf_RS485 описать как vu8 ( volatile unsigned char ), но тогда в сотнях местах приходится вписывать явное преобразование типов. memcopy((char*)Buf_RS485,.... )

Подобные симптомы свидетельствуют отнюдь не в пользу версии о правильности программы, а совсем даже наоборот.

 

Зачем вообще включаете оптимизацию? Если работает - не трогайте. Не открывайте ящик Пандоры. Есть большой класс ошибок, чувствительных к уровню оптимизации. Они Вам нужны?

Странный совет. Правильнее было бы не выключать оптимизацию, дабы по мере написания программы выгребать содержимое ящика.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Подобные симптомы свидетельствуют отнюдь не в пользу версии о правильности программы, а совсем даже наоборот.

Естественно. Внешний массив и обязан быть volatile, тем более что он используется в прерываниях. Ну так я и спрашивал как бы

сделать так, чтоб в стандартные библиотеки передовать тип volatile без явного преобразования типа повсеместно.

Может через какой нибудь typedef переопределить типы параметров в библиотеке. А может еще какие то другие есть решения.

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...