Conversión de entero a carácter

Estoy usando el microcontrolador PIC18f. Tengo que escribir una variable entera de 16 bits (2 bytes) que se transformó en una variable de dos caracteres, es decir, escribir cada byte en una dirección consecutiva de EEPROM. Primero tengo que escribir un byte superior (datos de 8 bits) en la EEPROM. No puedo obtener los 8 bits superiores de la variable entera con el siguiente código (donde puedo escribir los ocho bits inferiores de la variable entera). mi codigo es

void int_EEPROM_putc(unsigned char address, unsigned char data);
unsigned char int_EEPROM_getc(unsigned char address);
unsigned char c;
unsigned int d;
unsigned char* e;
unsigned char f;

void main()
{
d=0xffff;
e=(unsigned char*)&d;
//f=*e
f=*(e+1);
int_EEPROM_putc(0x02,f); 
delay_ms(100);
c=int_EEPROM_getc(0x02); 
while(true)
{
    if(c==255)
    {
    PORTB=~PORTB;
    }
    else
    {
    PORTB=0xff;
    }
}
Incluso si parece complicar demasiado las cosas, la aritmética de punteros parece correcta a primera vista. ¿Esperas cser 0xFF, pero no lo es?
¿Y está seguro de que sus rutinas EEPROM están funcionando? ¿Cómo verificaste eso con el byte inferior? Recuerde que el contenido predeterminado de EEPROM es 0xFF, usaría algún valor inicial como d=0xAABB;para diferenciar los valores.
ya he comprobado el byte inferior con otros valores, funciona bien @ Rev1.0
¿Qué tienes conectado a PORTB? ¿LED? Dado que simplemente alterna ese PUERTO continuamente sin demora, es posible que no pueda ver el parpadeo. ¿Puedes usar un programador para leer el contenido de la EEPROM?
Estoy usando un osciloscopio digital para verificar la alternancia del puerto B
Bueno, a juzgar por el código anterior, incluso cambiaría si falla la escritura de EEPROM ya que el contenido inicial es 0xFF. ¿Pero supongo que no se alterna en absoluto? Puede escribir el contenido de csu puerto y evaluar el valor.
cuando una imagen no parece funcionar correctamente, generalmente encuentro que he pasado por alto algo en la documentación y algún puerto solo hace X por N mientras Y está habilitado...

Respuestas (2)

El enfoque más general para extraer partes de un valor entero es desplazar y enmascarar. Entonces:

d = whatever;
c = d & 0xff; // extract low 8 bits
c = (d >> 8) & 0xff; // extract next 8 bits

Si, como aquí, sabe que el valor en d es de 16 bits, puede simplificar un poco el código para los siguientes 8 bits escribiendo

c = d >> 8; // extract high 8 bits of 16-bit value
Si bien esto es correcto, no responde a la pregunta de por qué el código propuesto por los OP no funciona.

En general... no es una excelente práctica asumir cualquier tamaño de bit o "endian-ness" para cualquier int, por razones de portabilidad. Según el procesador y el compilador, e int puede ser de 8 bits a 64 bits, o incluso algún otro tamaño extraño, y puede almacenarse en formato little-endian o big-endian.

¿Qué pasa si haces cualquiera de estos dos?

if(d==255)
{
}

// or 

int d = 0xffff;
d >> 8;
char c = d;
if (c==255)
{
}
Estoy usando MPLAB8.70 y Pic18f45k80. d>>8 no funciona, el operador de división tampoco funciona.
d>>8;no tendrá ningún efecto. Es puramente un valor de mano derecha, no asignado a nada. probablemente quierasd=d>>8;
@Dzarda - buena captura; Dejé caer un personaje. DEBERÍA haber sido "d>>=8;". Dependiendo del compilador, suele ser más barato (en términos de ciclos de CPU) que "d=d>>8;".
@TDHofstetter, ¿tiene un ejemplo real de dicho compilador? Lo consideraría muy extraño si d >>= 8;se d = d >> 8;compilara en un código diferente.
No tengo un compilador específico en mente en este momento, pero sé que algunos compiladores realizarán un d>>=8 en el lugar, cambiando el valor dentro del registro, mientras que otros compiladores cambiarán el valor, reescribiendo la variable en la memoria, luego vuelva a leer esa memoria y vuelva a escribirla con el mismo valor. Con un poco de tiempo, probablemente podría mostrarle tres o cuatro ejemplos de compilación a ensamblado de compiladores del mundo real. He estado optimizando el código durante mucho tiempo... 8)
@TDHofstetter: Lo encuentro realmente extraño. Quizás soy de la generación que se basa en compiladores modernos :)
Sí, probablemente. 8) Hemos olvidado, hoy, una TONELADA de los conceptos básicos en los que los tipos como yo tuvimos que trabajar: escribimos los precursores de los compiladores de hoy. Cuando comencé, gran parte del trabajo que hice incluso era anterior al lenguaje ensamblador: escribíamos código de máquina manualmente y prestamos mucha atención a cada byte y ciclo de reloj porque la memoria disponible estaba en kilobytes (o menos) y las velocidades de reloj a menudo estaban por debajo de 1 MHz. . Ha resultado útil: hoy en día, todavía escribo código de eficiencia extrema porque eso es lo que exigen mis proyectos.