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

Как сказать по IARски?

Адаптирую позаимствованное :)

 

В произведении есть такие строки:

#define strncmp_flash(sram,sflash,n) strncmp_P(sram,PSTR(sflash),n)

 

strncmp_flash(cl,"help",4);

 

strncmp_P в IARе не нашел, PSTR тоже.

Не подскажете, кто праздновать устал, как это записать по IAR'ски?

Можно это сделать без копирования флэшевой строки в ОЗУ?

Спасибо.

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


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

strncmp_P в IARе не нашел.

Не подскажете, кто праздновать устал, как это записать по IAR'ски?

Можно это сделать без копирования флэшевой строки в ОЗУ?

strncmp_P сравнение строк в ИАРе есть. Из хелпа:

int strncmp_P(const char *s1, PGM_P s2, size_t n);

Identical to strncmp except that the string s2 is in flash memory, not in data memory.

This function is available in both the CLIB and the DLIB library.

Эта функция как раз и сравнивает без копирования.

Если не хочется применять библиотечную функцию, могу предложить свою:

//==============================================================//
//      Compare n bytes strings from SRAM and FLASH             //
//    Return: 0 - strings are identical, 1 - not equal          //
//==============================================================//
unsigned char TextCmp(char *str1, char __flash *str2, unsigned char n)
  {
  unsigned char i, result = 0;
  
  for (i=0; i<n; i++) result |= *str1++ ^ *str2++;
  return result;
  }

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

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


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

#include <pgmspace.h>

void Test()
{
         static char const __flash str[] = "help";
         strncmp_P(cl,str,4);
}

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


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

А ещё рекомендую прочитать в доке на компилятор про extended keywords.

 

"The __generic pointer type attribute declares a generic pointer that can point to objects in both code and data space."

 

С использованием этого расширения можно писать функции с формальными параметрами вроде char __generic *s, которые могут работать с данными как в RAM так и во Flash.

К сожалению есть только у IAR, при переносе на другой компилятор придётся переделывать.

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


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

С использованием этого расширения можно писать функции с формальными параметрами вроде char __generic *s, которые могут работать с данными как в RAM так и во Flash.

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

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


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

2: SSerge

А у вас какая версия IAR ? Дело в том что у меня начиная с версии IAR AVR 4.30 при создании таких функций выдается ошибка. И 4.30 пришлось снести :(

2: Baser

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

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


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

День добрый! Назрел такой вопрос: как ИАР-у(4.20) сказать чтобы перед циклом запомнил в регистр процессора адрес регистра выходных данных и потом не грузил его снова каждый раз. (Нужно ускорить процесс). Написал так:

register uint16_t *pcSource;
register uint32_t *pOut;
        pcSource = (uint16_t*)( xRxDescriptors[ ulNextRxBuffer ].addr & emacADDRESS_MASK);
pin_off(clk_pin); 
  // from  AT91SAM7X256.h :     
  //#define AT91C_PIOA_ODSR ((AT91_REG *)     0xFFFFF438) // (PIOA) Output Data Status Register
        pOut = (uint32_t*) AT91C_PIOA_ODSR; 
    while( ulTotalFrameLength)
    {
                  *pOut = *(pcSource++);
                  pin_on(clk_pin);
                  ulTotalFrameLength --;
                  pin_off(clk_pin);
            }

Но в результате компиляции упорно получается следующее:

//  385         pOut = (uint32_t*) AT91C_PIOA_ODSR;
        LDR      R3,??vEMACRead_and_Go_0+0x8 ;; 0xfffff430
        CMP      R5,#+0
        BEQ      ??vEMACRead_and_Go_4
//  396                   *pOut = *(pcSource++);
??vEMACRead_and_Go_5:
        LDR      R6,??vEMACRead_and_Go_0+0xC ;; 0xfffff438
        LDRH     R7,[R4, #+0]
        STR      R7,[R6, #+0]
        ADDS     R4,R4,#+2
//  399                   pin_on(clk_pin);
        MOVS     R6,#+128
        LSLS     R6,R6,#+10      ;; #+131072
        STR      R6,[R3, #+0]
//  400                   ulTotalFrameLength --;
        SUBS     R5,R5,#+1
//  401                   pin_off(clk_pin);
        STR      R6,[R2, #+0]
...

Тоесть при инициализации pOut в регистр пишется совсем другой адрес, который затем используется совсем в другом месте - макросом pin_on. Это макросы из ascold.h - знатокам знаком этот хедер. Оптимизация выставлена максимальная. При других уровнях оптимизации компилятор и вовсе игнорирует переменную pOut.

Как это победить?

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


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

он ее вроде бы и в данном случае игнорирует.

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

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


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

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

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


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

Скомпилировал ради интереса этот пример.

//#pragma optimize=size
...
        MOVS     R0,#+0
        MOVS     R1,#+128
        LSLS     R1,R1,#+10      ;; #+131072
        LDR      R5,??task_0     ;; _ZN3GSM5stateE
        LDR      R2,??task_0+0x4 ;; 0xfffff430
        CMP      R6,#+0
        B        ??task_1
//  272   INT32S i,n,respLen;
//  273 
//  274     uint32_t   *pOut = (uint32_t*) AT91C_PIOA_ODSR;
//  275     uint16_t *pcSource = (uint16_t*)0;
//  276     while( i)
//  277     {
//  278                   *pOut = *(pcSource++);
??task_2:
        LDRH     R3,[R0, #+0]
        STR      R3,[R2, #+8]
        ADDS     R0,R0,#+2
//  279                   *AT91C_PIOA_SODR=131072;
        STR      R1,[R2, #+0]
//  280                   i --;
        SUBS     R6,R6,#+1
//  281                   *AT91C_PIOA_CODR=131072;
        STR      R1,[R2, #+4]
//  282             }
??task_1:
        BNE      ??task_2

IAR EWARM 5.11.

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


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

0_0 Красиво компилит! Только что заметил что у меня почемуто компилятор не использует смещение при записи в регистры...

А вообще, как я говорил, у меня там в цикле еще есть громоздкая обработка конца буфера, которая кушает регистры. С ней возможно результат уже не будет выглядеть так хорошо.

 

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

{-----------------------------------UPDATED 10.06.08-----------------------------------------}

Обнаружил что у меня в настройках установлен THUMB MODE. Без него все получается красиво в асме, но зато в железе сразу же улетает в Undefvec..... :wacko:

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


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

приведенный мной выше листинг - это код THUMB.

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

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


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

Привет всем. Не стал создавать новую тему решил написать сдесь.

 

помогите :help:

 

есть функции

 

1) pgm_read_byte

2) loop_until_bit_is_set

3) bit_is_set

 

взял исходник WinAVR, а в IAR таких функций нет , вот не знаю что делать.

Описание функций есть, и заменять их кусом кода не хочется.

Я мало знаю особенности ИАРа , может опытные подскажут аналоги этих функций ???

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

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


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

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

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

Гость
К сожалению, ваш контент содержит запрещённые слова. Пожалуйста, отредактируйте контент, чтобы удалить выделенные ниже слова.
Ответить в этой теме...

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

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

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

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

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

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