2017-08-21 7 views
0

この質問に対する回答は見つかりません。スタックにプッシュされるデータのサイズは?スタックデータサイズ

スタック上のデータをプッシュするとしましょう。たとえば、int。スタックポインタの値が4バイト減少します。

今日まで私はスタックにプッシュできる最大のデータはポインタのサイズより大きくすることはできないと考えました。しかし、少し実験をしました。私はC#で簡単なアプリを書いた:それは8つのバイトを必要とするので、私は32ビットシステムに取り組んでいながら

int i = 0; //0x68 <-- address of variable 
int j = 1; //0x64 
ulong k = 2; //0x5C 
int l = 3; //0x58 

により、私の予測に、ULONGは、ヒープに割り当てされなければならない(ので、ポインタのサイズは4つのバイトです)。これは単純なローカル変数なので、非常に奇妙です。

しかし、スタックに押し込まれました。

私はスタックの考え方に間違っていると思います。我々は4バイト(intを押す場合)または8バイト(長いまたは2倍を押す場合)または1バイトだけ変更する必要がある場合、スタックポインタはどのようにスタック "知っている"だろうか?

ローカル変数の値はヒープ上にあるかもしれませんが、それらの変数のアドレスはスタックにあります。しかし、これは理にかなっていません。オブジェクトがどのように処理されるかということです。オブジェクトを作成すると(新しいキーワードを使用して)オブジェクトがヒープに割り当てられ、このオブジェクトのアドレスがスタックにプッシュされます。

誰かが実際にどのように私に教えてくれますか(記事へのリンクを付けることができますか)?

+0

[いいえ](https://stackoverflow.com/a/3542372/17034)。 –

答えて

1

コンパイラまたはランタイム環境では、使用しているデータの種類を知っていて、スタックに収まるように構造化する方法を知っています。したがって、たとえば、スタックポインタが32ビットのチャンク内でのみ移動するアーキテクチャでは、コンパイラまたは実行時に32ビットを超える複数の32ビットチャンクでデータ要素をプッシュする方法を知っています。同様に、それらをスタックからポップし、適切な型の変数を再構築する方法も知っています。

ここでの問題は、他の種類のメモリよりもスタックで実際には異なるわけではありません。 CPUアーキテクチャは、特定のサイズの少数のデータ要素で動作するように最適化されますが、プログラミング言語は通常、より広い範囲のデータ型を提供します。コンパイラまたはランタイム環境では、この状況で必要となるデータのパッキングとアンパックを処理する必要があります。

+0

だから私は正しいと思った。スタックのデータサイズはポインタのサイズに過ぎず、大きなデータで何をするかを知っているのはコンパイラまたはランタイム環境です。たとえば、スタックポインタが4バイトしか移動しない場合(スタックポインタを4バイト以上変更できないとすれば、それは真実ではないことが分かります)、スタックから長い値をポップするには2スタックポインタの移動と、 2つの4バイト値からの8バイト値。そうですか? –

+0

それは私には広範囲に聞こえます。しかし実際には、異なるCPUアーキテクチャでは、スタック上のデータの整列方法やパディング方法が異なるため、コンパイラはこのような要因を考慮する必要があります。 –