next up previous
: スタック、スタックポインタ $sp : [SPIM] 手続き hello の : [SPIM] 手続き hello の

jal (jump and link) と レジスタ $ra

本章では、前章でみた手続き hello を MIPS のアセンブリ言語を用いて実現する。 いつも通り data06.zip をダウンロードせよ。

HelloFunc.asm がこの問題で取り扱うプログラムファイルである。 これはこのままで完成しているので、 シミュレータで動かすことができる。 (ただし問題の最後に、少しプログラムに手を加えてもらうことになる)

このプログラムをテキストエディタで開いて中身を確認し、 内容を理解しよう。 まず、HelloFunc.asm をロードしたときのメモリのテキスト領域 の様子の模式図を示したのが図 3 である。

図 3: HelloFunc.asm をロードした時の、メモリのテキスト領域の様子。
\begin{figure}\begin{center}
\epsfbox{memory.eps}\end{center}\end{figure}
前回の Switch 文のところでも触れたように、 プログラムの本体はメモリのテキスト領域に 格納される。 (テキスト領域は、Windows 版 SPIM (pcspim.exe) では 上から 2 番目の窓で見ることができる。)

プログラムのメイン部 (main:) はメモリアドレス 0x00400020 から始まる [1]。それより前の領域は シミュレータが main を呼び出すために使われる。 まず、次の 2 つの事実を了解して欲しい。

すなわち、プログラムの本体 main は「jal main」という 命令で呼びだされる。これはメモリアドレス 0x00400014 で実行されている。

手続き main が jal 命令で呼び出されてから終了した後、 処理は元の位置の次の命令、すなわちメモリアドレス 0x00400018 に戻らねばならない。 それはジャンプ命令 「jr $ra」 で実現される。

$ra (return address) は特別なレジスタで、 「関数を呼び出したアドレスの次のアドレス」の値が jal を呼び出した時に (自動的に) 代入されている。 つまり、jal main が実行されると $ra = 0x00400018 にセットされ、 jr $ra を実行することで main を呼び出した所の次の命令に 処理が戻る。

今まで扱ったプログラムは全て最後に jr $ra が実行されていたが、これは以上のような理由による。


平成16年11月17日