Pregunta Uso de punteros de función lejana


Me doy cuenta de que hasta ahora es específico del compilador, pero mi expectativa es que la ubicación del especificador lejano debería tener sentido para aquellos que realmente entienden los punteros.

Entonces, tengo dos aplicaciones que comparten el espacio de memoria completo del procesador.

La aplicación A debe llamar a la función foo que existe en la aplicación B.

Sé la ubicación de la memoria de la función foo.

Entonces esto debería funcionar, en la aplicación A:

typedef int (* __far MYFP)(int input);

void somefunc(void)
{
   int returnvalue;
   MYFP foo;

   foo = (MYFP) 0xFFFFFA;

   returnvalue = foo(39);
}
  • ¿Está el __far en el lugar correcto en typedef?
  • ¿Debo agregar __far al molde (MYFP)?
  • Alguna información sugiere que la llamada a foo no necesita ser desreferenciada, ¿cuál es su experiencia?
  • ¿Qué más sobre esto parece incorrecto, o podría tratar de lograr esto?

  • ¿Hay una mejor manera de hacer esto?

Editar:

Esto está en un dispositivo integrado (dispositivo Freescale S12XEQ) que utiliza Code Warrior. Es un dispositivo de 16 bits con un espacio de memoria de 24 bits, así que sí, está segmentado / en bancos.

-Adán


6
2017-11-20 16:50


origen


Respuestas:


¿Está el __far en el lugar correcto en typedef?

[Editar, en respuesta al comentario de ChrisN - gracias]

Esta es una característica dependiente del compilador, ya que no es parte de ANSI C. Según el manual del compilador <http://www.freescale.com/files/soft_dev_tools/doc/ref_manual/CW_Compiler_HC12_RM.pdf>, capítulo 8, lo tienes colocado correctamente. En otros compiladores, es posible que deba revertir el pedido. Sin embargo, esto debería ser bastante fácil de entender, ya que exactamente una de las dos opciones se compilará con cualquier compilador determinado.

¿Debo agregar __far al molde (MYFP)?

No, es parte del tipo.

Alguna información sugiere que la llamada a foo no necesita ser desreferenciada, ¿cuál es su experiencia?

Los punteros a funciones se pueden desreferenciar opcionalmente en C. Las siguientes líneas son ambas válidas y hacen exactamente lo mismo:

foo = (MYFP)0xFFFFFA;
returnvalue = foo(39);  // 1
returnvalue = (*foo)(39);  // 2

¿Qué más sobre esto parece incorrecto, o podría tratar de lograr esto?

Lo has hecho exactamente correctamente.


8
2017-11-20 18:27



los __far la palabra clave, al menos en el mundo MS, se usó al crear binarios que usaban memoria segmentada. Necesita comprender el sistema de memoria 8086 para entender esto. El 8086 dividió la memoria en segmentos, cada segmento tenía 64K de longitud, por lo que cada dirección en un segmento necesitaba 16bits. Las direcciones vienen en dos formas: cerca y lejos. Una dirección cercana era de 16bits y era una compensación en el segmento actual, uno de CS, DS, ES, SS dependiendo de la instrucción, un lejos era de 32 bits y consistía en un segmento y un desplazamiento. En el 8086, la dirección absoluta era 16 * segmento + desplazamiento, dando un rango direccionable de 1Mb.

Si no está utilizando un sistema de memoria segmentada, y parece que no lo está, todas las direcciones tienen el mismo número de bits, por lo que no es necesaria la distinción de cerca / lejos, lo que significa que el compilador probablemente ignore la palabra clave.


10
2017-11-20 17:06



Este es un fragmento de código que funciona desde un proyecto en el que estoy trabajando. Es Paradigma C ++, por lo que usa alguna versión de Borland. La CPU que utiliza es un clon 8086, por lo que la memoria de 20 bits está segmentada.

void softSerial0SR(unsigned16);
void (__far *softHandler)(unsigned16);

Inicializo softHandler a 0 sin queja.

Entonces,

softHandler = softSerial0SR;

en el código de configuración.

Para llamarlo, simplemente llame a softHandler como una función normal.

Tenga en cuenta que este código es ligeramente modificado para usted desde el código real que tengo.


1
2017-11-20 18:22



ambos programas fueron construidos por el mismo compilador / opciones, ¿entonces usan el mismo OBI?


0
2017-11-21 17:57



Estoy de acuerdo en que el código se ve bien - en este caso, me gustaría obtener un desensamblaje del código generado, y averiguar si salió bien. Solo debería haber 10 instrucciones como máximo, y entonces sabrá con certeza si funcionó.


0
2017-11-30 16:11