6

far はコンパイラ固有であることは理解していますが、ポインターを本当に理解している人にとっては far 指定子の配置が意味を成すはずだと期待しています。

したがって、プロセッサのメモリ空間全体を共有する 2 つのアプリケーションがあります。

アプリ A は、アプリ B に存在する関数 foo を呼び出す必要があります。

関数 foo のメモリ位置はわかっています。

したがって、これはアプリ A で機能するはずです。

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

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

   foo = (MYFP) 0xFFFFFA;

   returnvalue = foo(39);
}
  • __far は typedef の適切な場所にありますか?
  • (MYFP) キャストに __far を追加する必要がありますか?
  • いくつかの情報は、foo への呼び出しを逆参照する必要がないことを示唆しています。あなたの経験は何ですか?
  • これについて他に何が間違っているように見えますか、またはこれを達成しようとする可能性がありますか?

  • これを行うより良い方法はありますか?

編集:

これは、Code Warrior を使用する組み込みデバイス (Freescale S12XEQ デバイス) にあります。これは 24 ビットのメモリ空間を持つ 16 ビット デバイスなので、セグメント化/バンク化されています。

-アダム

4

5 に答える 5

10

__farキーワードは、少なくとも MS の世界では、セグメント化されたメモリを使用するバイナリを作成するときに使用されました。これを理解するには、8086 メモリ システムを理解する必要があります。8086 はメモリをセグメントに分割し、各セグメントの長さは 64K であったため、セグメント内の各アドレスには 16 ビットが必要でした。アドレスには、near と far の 2 つの形式がありました。ニア アドレスは 16 ビットで、現在のセグメントへのオフセットであり、命令に応じて CS、DS、ES、SS のいずれかです。ファー アドレスは 32 ビットで、セグメントとオフセットで構成されていました。8086 では、絶対アドレスは 16 * セグメント + オフセットであり、アドレス可能な範囲は 1Mb でした。

セグメント化されたメモリ システムを使用しておらず、使用していないように見える場合は、すべてのアドレスのビット数が同じであるため、near/far の区別は必要ありません。つまり、コンパイラによってキーワードが無視される可能性があります。

于 2008-11-20T17:06:39.093 に答える
8

__farはtypedefの正しい場所にありますか?

[編集、ChrisNのコメントに応えて-ありがとう]

これはANSICの一部ではないため、コンパイラに依存する機能です。コンパイラのマニュアルによると<http://www.freescale.com/files/soft_dev_tools/doc/ref_manual/CW_Compiler_HC12_RM.pdf >、第8章、正しく配置されています。他のコンパイラでは、順序を逆にする必要がある場合があります。ただし、2つのオプションの1つだけが任意のコンパイラでコンパイルされるため、これは非常に簡単に理解できるはずです。

(MYFP)キャストに__farを追加する必要がありますか?

いいえ、それはタイプの一部です。

いくつかの情報は、fooの呼び出しを逆参照する必要がないことを示唆していますが、あなたの経験は何ですか?

関数ポインタは、オプションでCで逆参照できます。次の行はどちらも有効で、まったく同じことを行います。

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

これについて他に何が間違っているように見えますか、または私はこれを達成しようとするかもしれませんか?

あなたはそれを正確に正しく行いました。

于 2008-11-20T18:27:54.123 に答える
1

これは、私が取り組んでいるプロジェクトから機能するコードのスニペットです。これはパラダイムC++であるため、Borlandの一部のバージョンを使用します。使用するCPUは8086クローンであるため、セグメント化された20ビットメモリです。

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

私はsoftHandlerを文句なしに0に初期化します。

それで、

softHandler = softSerial0SR;

セットアップコードで。

これを呼び出すには、通常の関数のようにsoftHandlerを呼び出すだけです。

このコードは、私が持っている実際のコードから少し調整されていることに注意してください。

于 2008-11-20T18:22:57.067 に答える
0

コードが正常に見えることに同意します。この場合、生成されたコードの逆アセンブリを取得し、それが正しいかどうかを判断します。多くても 10 個の命令しかないはずです。そうすれば、それが機能したかどうかが確実にわかります。

于 2008-11-30T16:11:13.480 に答える
0

両方のプログラムが同じコンパイラ/オプションによってビルドされたので、同じ OBI を使用しますか?

于 2008-11-21T17:57:49.257 に答える