コード:
char keyStr[50]={ 0x5F, 0x80 /* bla bla */ };
uint32_t* reCast = reinterpret_cast< uint32_t* >( &keyStr[29] );
uint32_t* reCast2 = ( uint32_t* )&keyStr[29];
if( reCast == reCast2 ){
cout << "Same Thing!";
}
出力:
同じこと!
2 つのキャスト方法の違いは何だろうか。また、(例を使用して)static_cast、dynamic_cast、および他のタイプのキャストの違いを指定できれば(つまり、できるだけ低レベルでアセンブリ言語にできるだけ近い状態で)。
static_cast
dynamic_cast
const_cast
reinterpret_cast
C-style cast (type)value
Function-style cast type(value)
ありがとう。
reinterpret_cast が int ポインターに keyStr[29] のアドレスを割り当てることを上記の例から知っている PS を読んでください。
lea eax, [keyStr+1D]
mov [reCast], eax
つまり、低レベルの見通しでは、元のデータを変更しないため、reinterpret_cast はまったく危険ではありません。
他のキャスト メソッドが低レベルでどのように動作するかを知りたかったのです。したがって、たとえば、オブジェクトは、低レベルの方法では、アドレスを保持する単なる変数です。そして、そのオブジェクトの型は、コンパイラがそのアドレスを解釈し、それをオフセットする方法です(これはまさに私が興味のないものです。アセンブリでは、その変数が値、ポインター、またはオブジェクト (つまり、別のポインター) )。まったく同じかもしれないもう 1 つのことは、int と int* または unsigned int と int の違いです。4 つの宣言はすべて同じアセンブリ命令を生成します。( push value ) または (sub esp-(length of int) && mov esp, value) これで質問が明確になり、「低レベルコード」および「アセンブリ」とタグ付けした理由が明確になることを願っています
PSこのプログラムでは、移植性やその他の高レベルのものは気にしません。私はできるだけ低レベルで、できるだけアセンブリ言語に近づけようとしています。つまり、このプログラムでは、メモリは単なるメモリ (つまり 0 と 1 ビット) であり、型は重要ではありません (たとえば、mem アドレス: 0x123 が「int」型か「float」型かは気にしません。 "データ")