Coins Java - SPARCでの例外処理

SPARCアーキテクチャ上での例外処理

[Coins Java - 例外処理]

レジスタウィンドウ

SPARCのレジスタは、レジスタウィンドウという方式でフレーム処理のサポートを自動で行ってくれる。

レジスタはフレーム作成ごとにその位置をスライドして行き、フレームごとに新しいレジスタを使用することが可能である。また、一部のグローバルレジスタや、カスケードされたレジスタも存在し、引数の受け渡しや返戻値の受け渡しなども容易に行える。

gcc内部でのレジスタの扱い

各レジスタに割り振られるレジスタ番号は、以下の表のようになっている。

番号 レジスタ名 備考
0-7 %g0-%g7 グローバルレジスタ
8 %o0
9 %o1
10 %o2
11 %o3
12 %o4
13 %o5
14 %o6 %sp スタックポインタ
15 %o7 呼び元でリターンアドレスをプッシュする場所
16-23 %l0-%l7 ローカルレジスタ
24 %i0
25 %i1
26 %i2
27 %i3
28 %i4
29 %i5
30 %i6 %fp フレームポインタ
31 %i7 呼び先でリターンアドレスが存在する場所
32-95 %f0-%f63 浮動小数点レジスタ
96-99 %fcc0-%fcc3
100 %icc
101 %sfp

prologue処理

基本的には、以下のようなプログラムになっている。

// レジスタウィンドウの保存
!#PROLOGUE# 0
save	%sp, -120, %sp

CIEの形状

基本的な部分の解説はCIEにまわすとして、アーキテクチャ依存する部分のみを記述する。

要素 備考
code align 1
data align -4
return address column 15 %o7のレジスタ番号

また、CIEが持つCFAは以下のようになっていた。

// CFAの定義
// i386では %sp が 14 番のレジスタで、関数呼び出し直後は %sp がフレームの先頭になるため
def_cfa 14 0

FDEの形状

基本的な部分の解説はFDEにまわすとして、アーキテクチャ依存する部分のみを記述する。FDECIEのような設定は無く、CFAから始まる。

// PCの移動
// 開始直後にウィンドウレジスタの機能を使用し、%spだったものが%fpに格納される。
// このため、[[CFA|Coins Java - CFA]]の先頭アドレスまでずれてしまう。
// このアドレスがずれる直後までPCを移動する。
// もし、PCがここに達していない場合は、これ以降のインストラクションは考慮しない。
advance_loc4 (saveを行った直後のアドレス - メソッドの開始位置)
// CFAの再定義
// %spが%fpになったため、その旨を伝える。
// %fp のレジスタ番号は30であるため、それを指定する。
def_cfa_register 30
// ウィンドウのセーブ
// ウィンドウのセーブが行われたため、その旨を伝える。
gnu_window_save
// 復帰すべきレジスタの登録
// まだはっきり解明していないが、%i7レジスタの内容を%o7レジスタに書き戻さないと、
// シグナルハンドラの作動による例外発生時に強制終了させられてしまう模様。
register 15 31

キャッチ時の状態

次のレジスタにキャッチ時の情報が格納されている。

レジスタ名 情報
%i0 unwindHeader
%i1 ar_filter

Copyright (C) 2002-2006 s.arakawa