Существует ли стандартный макрос для обнаружения архитектур, требующих согласованного доступа к памяти?

Предполагая что-то вроде:

void mask_bytes(unsigned char* dest, unsigned char* src, unsigned char* mask, unsigned int len)
{
  unsigned int i;
  for(i=0; i<len; i++)
  {
     dest[i] = src[i] & mask[i];
  }
}

Я могу работать быстрее на машине с невыровненным доступом (например, x86 ), написав что-то вроде:

void mask_bytes(unsigned char* dest, unsigned char* src, unsigned char* mask, unsigned int len)
{
  unsigned int i;
  unsigned int wordlen = len >> 2;
  for(i=0; i<wordlen; i++)
  {
    ((uint32_t*)dest)[i] = ((uint32_t*)src)[i] & ((uint32_t*)mask)[i]; // this raises SIGBUS on SPARC and other archs that require aligned access.
  }
  for(i=wordlen<<2; i<len; i++){
    dest[i] = src[i] & mask[i];
  }
}

Однако он должен строиться на нескольких архитектурах, поэтому я хотел бы сделать что-то вроде:

void mask_bytes(unsigned char* dest, unsigned char* src, unsigned char* mask, unsigned int len)
{
  unsigned int i;
  unsigned int wordlen = len >> 2;

#if defined(__ALIGNED2__) || defined(__ALIGNED4__) || defined(__ALIGNED8__)
  // go slow
  for(i=0; i<len; i++)
  {
     dest[i] = src[i] & mask[i];
  }
#else
  // go fast
  for(i=0; i<wordlen; i++)
  {
    // the following line will raise SIGBUS on SPARC and other archs that require aligned access.
    ((uint32_t*)dest)[i] = ((uint32_t*)src)[i] & ((uint32_t*)mask)[i]; 
  }
  for(i=wordlen<<2; i<len; i++){
    dest[i] = src[i] & mask[i];
  }
#endif
}

Но я не могу найти никакой хорошей информации о макросах, определенных компилятором (например, мой гипотетический __ ALIGNED4 __ ] выше), которые определяют выравнивание или любые хитрые способы использования препроцессора для определения выравнивания целевой архитектуры. Я мог бы просто протестировать defined (__SVR4) && defined (__sun) , но я бы предпочел что-то, что будет Just Work TM на других архитектурах, требующих согласованного доступа к памяти.

7
задан Brian Tompsett - 汤莱恩 3 April 2016 в 20:07
поделиться