a
es un puntero a una matriz de bytes. Si lo convierte en un uint16_t y lo asigna a b
, entonces b
contendrá la dirección de la base de la matriz (donde se almacena) en SRAM. Si desea tratar los dos bytes de la matriz a
como un entero, entonces use una unión como lo sugiere el usuario 14284, pero tenga en cuenta que la unión representará la matriz de bytes en el orden de bytes de memoria de la arquitectura (en AVR que sería little-endian, lo que significa que el byte 0 es el byte menos significativo). La forma de escribir eso en el código es:
union{
uint8_t a[2];
uint16_t b;
} x;
x.b[0] = 0x35;
x.b[1] = 0x4A;
// by virtue of the above two assignments
x.a == 0x4A35 // is true
Otra forma de hacer esto sin usar una unión es convertir a
a un puntero uint16_t y luego desreferenciarlo así:
uint8_t a[2] = {0x35, 0x4A};
uint16_t b = *((uint16_t *) a);
b == 0x4A35; // because AVR is little endian
Si está utilizando el búfer para almacenar datos de big endian (por ejemplo, el orden de bytes de la red), entonces necesitará un intercambio de bytes para usar cualquiera de estas técnicas. Una forma de hacerlo sin ninguna rama o variable temporal es:
uint8_t a[2] = {0x35, 0x4A};
a[0] ^= a[1];
a[1] ^= a[0];
a[0] ^= a[1];
a[0] == 0x4A; // true
a[1] == 0x35; // true
Por cierto, esto no es un AVR o incluso un problema solo incrustado. El código de red de nivel de aplicación escrito para PC normalmente llama a funciones llamadas htonl
, htons
(host a la red, variantes de 32 y 16 bits) y ntohl
, ntohs
(red a host, 32 y 16 bits variantes) cuyas implementaciones dependen de la arquitectura de destino en cuanto a si intercambian los bytes o no (bajo el supuesto de que los bytes transmitidos "en el cable" siempre son big-endian cuando forman parte de palabras de múltiples bytes).