2

実行時チェックで利用可能な仮想メモリ (または RAM) が 4GB を超えないことが確認された場合、次のようなことができるプラットフォームはありますか?

// 1) cast pointer to void pointer
// 2) cast void pointer to uint64 type
// 3) set most significant bytes of uint64 type to 0 (might be wrong choice)
// 4) store as uint32 type
uint32_t trimmed_pointer = (uint64_t) (void *) pointer & 0x00000000ffffffff;

元のポインターを取得するには、次のようにします。

same_as_before_t *pointer = (void *) (uint64_t) trimmed_pointer

これはおそらくひどいハックであり、OS のメモリ マネージャーが仮想メモリを実装する方法 (コンパイラと同様に?) に完全に依存していることを認識しているので、純粋に好奇心からこれを尋ねています。

4

2 に答える 2

3

ポインターを 32 ビット整数型に安全に格納できると想定していた古い 32 ビット プログラムの移植を支援するために、WindowsIMAGE_FILE_LARGE_ADDRESS_AWAREは 64 ビット プログラムの PE ヘッダーのフラグを引き続き尊重します。

そのフラグがプログラムのヘッダーに設定されていない場合、システムは 2GB を超えるアドレスをプロセスに割り当てません。

64 ビット ビルドのデフォルトでは、リンカーはフラグを設定します (つまり、デフォルトでは、64 ビット プログラムのアドレス空間は制限されません) 64 ビット プログラムに 2GB を超えるアドレス空間を与えてはならないことを示したい場合/largeaddressaware:noは、プログラムのビルド時にオプションをリンカーに渡します。詳細については、 http://msdn.microsoft.com/en-us/library/windows/desktop/aa384271.aspxを参照してください。

この機能は、ポインタを適切に処理しないプログラムの移植を支援するためのものであり、そのようなプログラムを作成できるようにするためのものではないことに注意してください。また、仮想アドレスは物理アドレスとはほとんど関係がないという重要な事実にも注意してください (つまり、RAM が 4GB 未満であっても、システムはテラバイト範囲の仮想アドレスを使用できます)。

于 2013-06-25T07:36:00.797 に答える