4.アセンブリ言語プログラムおよびクロスソフトとの 関連
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
272
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
273
4.1 アセンブリ言語プログラムとの関連
SuperH RISC engine C/C++コンパイラは、日立 SuperH RISC engine ファミリ専用の特殊命令までサ
ポートしているため、ほとんどのプログラムは C 言語で記述できます。しかし、性能を追及する場
合、鍵になる部分をアセンブリ言語で記述し、C 言語プログラムと接続する必要があります。
本節では、C 言語プログラムとアセンブリ言語プログラムの接続時に注意すべき次の事項につい
て概説します。
• 外部名の相互参照方法
• 関数呼び出しのインタフェース
詳細については、『SuperH RISC engine C/C++コンパイラ ユーザーズマニュアル』を参照
してください。
4.1.1 外部名の相互参照方法
(1)アセンブリ言語プログラムの外部定義名を C 言語プログラムで参照する方法
C 言語プログラムからアセンブリ言語プログラムの外部定義名を参照するには、次のように
します。
• アセンブリ言語プログラムで先頭に"_"を付けたシンボル名(32 文字以内)を".EXPORT"または".GLOBAL"アセンブラ制御命令を用いて外部定義宣言します。
• C 言語プログラムでは"extern"記憶クラス指定子を用いて先頭に"_"がないシンボル名を外
部参照宣言します。
アセンブリ言語プログラム(定義する側) C言語プログラム(参照する側)
図 4.1 アセンブリ言語プログラムの外部定義名を C 言語プログラムから参照する例
(2)C 言語プログラムの外部定義名をアセンブリ言語プログラムで参照する方法
C 言語プログラムにとっての外部定義名とは次のものです。
• 大域変数であって、かつ static 記憶クラスでないもの
• extern 記憶クラスで宣言されている変数名
• static 記憶クラスを指定されていない関数名
アセンブリ言語プログラムから C 言語プログラムの外部定義名を参照するには、次のように
します。
• C 言語プログラムでシンボル名(先頭に_がない)を外部定義(グローバル変数)します。
• アセンブリ言語プログラムでは".IMPORT "または".GLOBAL "アセンブラ制御命令を用い
て先頭に"_"を付加したシンボル名を外部参照宣言します。
.EXPORT _a , _b .SECTION D, DATA, ALIGN=4_a : .DATA.L 1_b : .DATA.L 1 .END
extern int a , b;f (){a+=b;
}
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
274
C 言語プログラム(定義する側) アセンブリ言語プログラム(参照する側)
図 4.2 C 言語プログラムの外部定義名をアセンブリ言語プログラムから参照する例
【注】
関数名、静的データメンバから生成する外部名は、C++コンパイルのとき一定の規則で変
換を行っています。コンパイラが生成した外部名を知る必要があるときは、コンパイラオ
プション code=asm または、listfileにてコンパイラが生成する外部名を参照してください。
「SuperH RISC engine C/C++コンパイラユーザーズマニュアル 付録 G エンコード規則」
もあわせて参照してください。また、C++の関数を「extern “C”」を付与して関数定義を行
えば、外部名は C の関数と同様の生成規則になります。ただし、その関数を多重定義でき
なくなります。
4.1.2 関数呼び出しのインタフェース
C 言語プログラムとアセンブリ言語プログラムとの間で相互に関数呼び出しを行うとき、アセン
ブリ言語プログラム側で守るべき規則には、次の 4 つがあげられます。
(1)スタックポインタに関する規則
(2)スタックフレームの割り付け/解放に関する規則
(3)レジスタに関する規則
(4)引数とリターン値の設定/参照に関する規則
ここでは、(1)~(3)までを説明します。(4)については、「4.1.3 引数とリターン値の設定/参照」
を参照してください。
(1)スタックポインタに関する規則
スタックポインタの指すアドレスよりも下位(0 番地の方向)のスタック領域に、有効なデ
ータを格納しないでください。スタックポインタより下位アドレスに格納されたデータは、
割り込み処理で破壊される可能性があります。
(2)スタックフレームの割り付け/解放に関する規則
関数呼び出しが行なわれた時点(JSR または BSR 命令の実行直後)では、スタックポイン
タは呼び出し関数側で使用したスタックの最下位アドレスを指しています。この領域より上
位アドレス(H'FFFFFFFF 番地の方向)のデータの割り付け/設定は呼び出し側の関数の役目
です。
関数のリターン時は、呼び出された関数で確保した領域を解放してから、通常 RTS 命令を
用いて呼び出し関数へ返ります。これより上位アドレスの領域(リターン値アドレスおよび
引数の領域)は、呼び出し側の関数で解放します。
int a; .IMPORT _a.SECTION P,CODE, ALIGN=2MOV.L A_a, R1MOV.L @R1, R0ADD #1,R0RTSMOV.L R0,@R1
A_a: .DATA.L _a.END
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
275
図 4.3 スタックフレームの割り付け/解放
(3)レジスタに関する規則
C/C++コンパイラが関数呼び出し前後において、値を保証するレジスタと保証しないレジス
タがあります。レジスタの保証規則を表 4.1に示します。
表 4.1 C 言語プログラムでの関数呼び出し前後のレジスタ保証規則
項番 項目 対象レジスタ アセンブリ言語プログラミングにおける注意点
1
保証しない
レジスタ
R0~R7
FR0~FR11*1
DR0~DR10*2
FPUL*1,*2,FPSCR*1,*2
関数呼び出し時に対象レジスタに有効な値があれ
ば、呼び出し側で値を退避する。呼び出される側の
関数では退避せずに使用できる。
2 保証する
レジスタ
R8~R15
MACH,MACL,PR
FR12~FR15*1
DR12~DR14*2
対象レジスタのうち関数内で使用するレジスタの値
を退避し、リターン時に回復する。ただし、"-macsave= 0"オプション指定時はMACH、MACL は保証しない
レジスタ。
【注】 *1:SH-2E,SH-3E,SH-4 の単精度浮動小数点用レジスタです。
*2:SH-4 の倍精度浮動小数点用レジスタです。
C言語プログラムとアセンブリ言語プログラムの関数の接続は、次のようにしてくだい。
(a)アセンブリ言語関数を C 言語プログラムから呼び出す場合
• 対象アセンブリ言語関数が別のモジュールを呼び出しているときには、アセンブリ言語
関数の入口で PR レジスタの値のスタックへの退避、出口でスタックからの回復を行っ
てください。
• アセンブリ言語関数内で R8~R15、MACH、MACL のレジスタを使用するときには、使
用前にレジスタ値のスタックへの退避、使用後にスタックからの回復を行ってください。
• アセンブリ言語関数へどのように引数が渡されるかについては「4.1.3 引数とリターン
値の設定/参照」を参照してください。
リターン値アドレス
引数領域
呼び出される側で
使用するスタック
呼び出し側で
使用するスタック
下位アドレス ↑
上位アドレス ↓
SP →
0
関数呼出し直後、または呼び出された関数のリターン直後
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
276
(b)C 言語関数をアセンブリ言語プログラムから呼び出す場合
• R0~R7 レジスタに有効な値があれば、C 言語関数呼び出し前に空きレジスタまたはスタ
ックへ値を退避してください。
• アセンブリ言語関数へどのようにリターン値が渡されるかについては「4.1.3 引数とリ
ターン値の設定/参照」を参照してください。
C言語関数 f からアセンブリ言語関数 g を呼び出し、さらにアセンブリ言語関数 g から C 言語関
数 h を呼び出している例を図 4.4に示します。
C言語関数f
アセンブリ言語関数 g
C 言語関数 h
図 4.4 C 言語プログラム関数とアセンブリ言語プログラム関数の相互呼び出し例
extern void g( );
f( ){
g( );}
h( ){
::
}
.EXPORT _g
.IMPORT _h
.SECTION P, CODE, ALIGN=2_g : STS.L PR ,@-R15
MOV.L R14,@-R15MOV.L R13,@-R15:
MOV.L R2,@R15MOV.L R1,@R15MOV.L L_h,R0JSR @R0NOP:
MOV.L @R15+,R13MOV.L @R15+,R14RTSLDS.L @R15+,PR
L_h : .DATA.L _h.END
関数gの外部定義宣言関数hの外部参照宣言
PRレジスタ値の保存関数gでの使用レジスタの保存
関数hでの使用レジスタの保存
関数hの呼び出し
関数gでの使用レジスタの回復
PRレジスタ値の回復
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
277
4.1.3 引数とリターン値の設定/参照
C/C++コンパイラの引数とリターン値の設定/参照に関する規則は、関数宣言において個々の引
数とリターン値の型が明示的に宣言されているかどうかによって異なります。C 言語プログラムで
引数とリターン値の型を明示的に宣言するには、関数の原型宣言を用います。
以下の説明では、まず C 言語プログラムでの引数とリターン値に対する一般的な規則について述
べたあと、引数の割り付け領域と割り付け方、およびリターン値の設定場所について述べます。
(1) C 言語プログラムでの引数とリターン値に対する一般的な規則
(a)引数の渡し方
引数の値を、必ずレジスタまたはスタック上の引数の割り付け領域にコピーしたあとで
関数を呼び出します。呼び出し側の関数では、リターン後に引数の割り付け領域を参照す
ることはありませんので、呼び出された側の関数で引数の値を変更しても呼び出し側の処
理は直接には影響を受けません。
(b)型変換の規則
引数を渡す場合、またはリターン値を返す場合、自動的に型変換を行うことがあります。
型変換の規則について表 4.2に示します。
表 4.2 型変換の規則
型変換 変換方法
型の宣言された引数の型変換 原型宣言によって型が宣言されている引数は、宣言され
た型に変換します。
型の宣言されていない引数の型変換
原型宣言によって型が宣言されていない引数は、次の規
則に従って変換します。
・ char 型、unsigned char 型、short 型、unsigned short
型の引数は、int 型に変換します。
・ float 型の引数は、double型に変換します。
・上記以外の型は変換しません。
リターン値の型変換 リターン値は、その関数の返す型に変換します。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
278
例 1) 原型宣言により型が宣言されている例long f();long f(){ float x; : :
return x;}
リターン値 x は、原型宣言に従って long 型に変換されます。
例 2) 原型宣言により型が宣言されていない例 1void p(int,...);
long f(){ char c; :
p(1.0, c); :
}第 1 引数は、対応する引数の型が int 型なので、int 型に変換されます。
第 2 引数は、対応する引数の型がないので、int 型に変換されます。
例 3) 原型宣言により型が宣言されていない例 2原型宣言によって引数の型を宣言していない場合、正しく引数が渡されるように呼び出
される側と呼び出す側で同じ型に指定してください。型が合っていない場合は、動作が保
証されません。void f(x)float x;{ : :
}
void main(){ float x; f(x);
}この例では、関数 fの引数の原型宣言がないため、関数mainの側で呼び出すときに引数xをdouble
型に変換します。一方、関数 f の側では引数を float 型として宣言しています。このため、正しく
引数を受け渡しすることはできません。原型宣言によって引数の型を宣言するか、関数 f の側の
引数宣言を double 型にする必要があります。
原型宣言によって正しく引数の型を宣言すると次のようになります。void f(float x){ : :
}
void main(){ float x; f(x);
}
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
279
(2) C言語プログラムでの引数の割り付け方
引数は、レジスタに割り付ける場合とレジスタに割り付けられないときスタック上の引数領域に
割り付ける場合があります。引数の割り付け領域を図 4.5 に、引数割り付け領域の一般規則を表 4.3にそれぞれ示します。
スタック
リターン値アドレス
引数領域
図 4.5 C 言語プログラムでの引数割り付け領域
↑下位アドレス
SP→
R4
R5
R6
R7
引数割り付け領域
FR4(DR4)
FR5
FR6(DR6)
FR7
FR8(DR8)
FR9
FR10(DR10)
FR11
(CPUがSH-2E,SH-3E,SH-4の場合)
引数格納用レジスタ
↓上位アドレス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
280
表 4.3 C 言語プログラムでの引数割り付けの一般規則
割り付け規則
レジスタで渡される引数
引数格納用
レジスタ
対象の型 スタックで渡される引数
R4~R7 char, unsigned char, bool,
short, unsigned short,
int, unsigned int,
long, unsigned long,
float(CPU が SH-1、SH-2、SH-3 の場合),ポインタ,データメンバへのポ
インタ,リファレンス
(1)引数の型がレジスタ渡しの対象
の型以外のもの
(2)プロトタイプ宣言により可変個
の引数を持つ関数として宣言して
いるもの*3
(3)他の引数がすでに R4~R7 に割
り付いている場合
FR4~FR11*1
DR4~DR10*2
SH-2E、SH-3E のとき
・引数が float 型
・引数が double 型かつ
double=float オプション指定
SH-4 のとき
・引数型が float 型かつ
fpu=double オプション指定なし
・引数型が double 型かつ
fpu=single オプション指定
SH-4 のとき
・引数型が double 型かつ
fpu=single オプション指定なし
・引数型が float 型かつ
fpu=double オプション指定
(4)他の引数がすでに FR4(DR4)~FR11(DR10)に割り付いている
場合
【注】 *1:SH-2E,SH-3E,SH-4 の単精度浮動小数点用のレジスタです。
*2:SH-4 の倍精度浮動小数点用レジスタです。
*3:プロトタイプ宣言により可変個の引数をもつ関数として宣言している場合、宣言の中で対
応する型のない引数およびその直前の引数はスタックに割り付けます。
例)
int f2(int, int, int, int,...); f2(a, b, c, x, y, z) { :
}第 4 引数までは通常、レジスタに割り付けますが、ここでは x,y,z もスタックに割り付けます。
(a)引数格納用レジスタへの割り付け
引数格納用レジスタには、ソースプログラムの宣言の順に番号の小さいレジスタから割
り付けます。引数格納用レジスタの割り付け例を例 1に示します。
(b)スタック上の引数領域への割り付け
スタック上の引数領域には、ソースプログラム上で宣言した順に下位アドレスから割り
付けます。引数格納用スタックの割り付け例を例 2~例 8に示します。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
281
【構造体、共用体型引数に関する注意】
構造体、共用体型の引数を設定する場合は、その型の境界調整にかかわらず 4 バイト境界に
割り付けられ、しかもその領域として 4 の倍数バイトの領域が使用されます。これは、SuperHマイコンのスタックポインタが 4 バイト単位に変化するためです。
例 1) レジスタの対象の型である引数は、宣言順にレジスタ R4~R7 に割り付けます。
int f(char,short,int,float); :
f(1,2,3,4.0); :
例 2) レジスタに割り付けることができなかった引数は、スタックに割り付けます。また、引数の
型が(unsigned )char 型、または、( unsigned )short 型でスタック上の引数領域に割り付く
場合、4 バイトに拡張して割り付きます。
int f(int,short,long,float,char); :
f(1,2,3,4.0,5); :
例 3) レジスタに割り付けられない型の引数は、スタックに割り付けます。
struct s{int x,y;}a;int f(int,struct s,int); :
f(1,a,3); :
R4
R5
R6R7
保証しない 1保証しない 2
34.0
保証しない 5引数領域
(スタック)
↑下位アドレス
↓上位アドレス
a.xa.y
引数領域
(スタック)
↑下位アドレス
↓上位アドレス
13
R4R5
1保証しない 2
34.0
R4
R5
R6R7
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
282
例 4) プロトタイプ宣言により可変個の引数を持つ関数として宣言している場合、対応する型のな
い引数およびその直前の引数は、宣言順にスタックに割り付けます。
int f(double, int, int...) :
f(1.0, 2, 3, 4) :
例 5) 原型宣言がない場合
→ char 型は int 型に、float 型は double 型に拡張して割り付ける
例 6) 関数の返す型が 4 バイトを越える場合またはクラスの場合、引数領域の直前にリターン値ア
ドレスを設定します。また、クラスのサイズが 4 の倍数バイトでないとき、空領域が生じま
す。
struct s{char x,y,z;}a;double f(struct s); :
f(a);
2
34
引数領域
(スタック)
↑下位アドレス
↓上位アドレス
R4
1.0
int f ( )char a ;float b;
f (a ,b)
R4 a
引数領域
(スタック)
↑下位アドレス
↓上位アドレス
b
リターン値アドレス
a.x a.y a.z 空領域
↓上位アドレス
リターン値設定領域
引数領域
(スタック)
↑下位アドレス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
283
例 7) CPU が SH-2E、SH-3E の場合、float 型の引数は FPU レジスタに割り付きます。
int f(char,float,short,float,double); :
f(1,2.0,3,4.0,5.0); :
例 8) CPU が SH-4 かつ-fpu オプション指定なしの場合、float/double型の引数は FPU レジスタに
割り付きます。
int f(char,float,double,float,short); :
f(1,2.0, 4.0,5.0,3); :
5.0引数領域
(スタック)
↑下位アドレス
↓上位アドレス
R4
R5
R6R7
保証しない 1 保証しない 3
FR4
FR5
FR6
FR7
FR8
FR9
FR10FR11
2.04.0
引数領域
(スタック)
↑下位アドレス
↓上位アドレス
R4
R5
R6R7
保証しない 1保証しない 3
FR4 (DR4)
FR5
FR6 (DR6)
FR7
FR8 (DR8)
FR9
FR10 (DR10)FR11
2.05.04.0
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
284
(3)C 言語プログラムでのリターン値の設定場所
関数のリターン値の型により、リターン値をレジスタに設定する場合とスタックに設定する
場合があります。リターン値の型と設定場所の関係は表 4.4を参照してください。
関数のリターン値をスタックに設定する場合、リターン値はリターン値アドレスの指す領域
に設定します。呼び出す側では、引数領域のほかにリターン値設定領域を確保し、そのアドレ
スをリターン値アドレスに設定してから関数を呼び出します(図 4.6参照)。関数のリターン
値が void 型の場合、リターン値を設定しません。
表 4.4 C 言語プログラムでのリターン値の型と設定場所
No リターン値の型 リターン値の設定場所
1 (singed) char, unsigned char,
(singed) short, unsigned short,
(singed) int, unsigned int,
long, unsigned long,
float, ポインタ, bool
リファレンス、データメンバへのポインタ
R0 : 32 ビット
( signed) char,unsigned char の上位 3 バイト、(signed)short,unsigned short の上位 2 バイトの内容は保証しません。
(ただし、-rtnext オプション指定時は(signed) char,(singed)short 型は符号拡張、unsigned char,unsigned short 型はゼロ拡張を行います。)
FR0 : 32 ビット
(1)SH-2E、SH-3E のとき
・リターン値が float 型
・リターン値が double 型かつ double=float オプション指
定
(2)SH-4 のとき
・リターン値が float 型かつ fpu=double オプション指定な
し
・リターン値が浮動小数点型かつ fpu=single オプション指
定
2 double, long double
構造体、共用体、クラス型、
関数メンバへのポインタ
リターン値設定領域(メモリ)
DR0:64 ビット
SH-4 のとき
・リターン値が double 型かつ fpu=single オプション指定
なし
・リターン値が浮動小数点型かつ fpu=double オプション
指定
リターン値
アドレス
図 4.6 C 言語プログラムでリターン値をスタックに設定する場合のリターン値の設定領域
リターン値設定領域
スタック↑下位アドレス
SP→
↓上位アドレス
引数領域
(呼び出し側
で確保)
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
285
4.2 リンケージエディタとの関連
4.2.1 ROM 化支援機能
ロードモジュールを ROM に書き込む際、初期化データ領域も ROM に書き込まれてしまいます。
しかし、データ操作は RAM 上で行わなければならないので、起動時に初期化データ領域の ROMから RAM への複写が必要です。リンケージエディタの ROM 化支援機能を用いることにより、こ
の処理を容易に実行できます。
ROM 化支援機能を使用するには、リンク時にオプション"ROM(D,R)"(D:ROM 上の初期化
データ領域のセクション名、R:RAM 上の初期化データ領域のセクション名)を指定します。
ROM 化支援機能では、次の事項が行われます。
(1) ROM 上の初期化データ領域と同じ大きさの領域を RAM 上に確保します。図 4.7にメ
モリへの二重割り付け方を示します。
オブジェクト リンケージエディタの割り付け
図 4.7 ROM 化支援機能によるメモリ割り付け
(2) 初期化データ領域に宣言したシンボルの参照が RAM 領域のアドレスを指すようにアド
レス解決を自動的に行います。
ユーザはスタートアップルーチンに ROM 上のデータを RAM 上に複写する処理を組み込んで
おきます。例については「1.6.4 初期化部の作成」を参照してください。
ROM 化支援機能の詳細については、『H シリーズ リンケージエディタ ライブラリアン オ
ブジェクトコンバータユーザーズマニュアル』を参照してください。
なお、本機能は H シリーズリンケージエディタ Ver.4 以降でサポートしています。
ROM (D,R)
D:ROM上の初期化データ領域のセクション名R:RAM上の初期化データ領域のセクション名
初期化データ領域(D)
初期化データ領域(R)
初期値(D)
ROM領域
RAM領域
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
286
4.2.2 リンク時の注意事項
C/C++コンパイラが生成したリロケータブルオブジェクトファイルをリンクした際、出力される
エラーメッセージへの対処方法を表 4.5に示します。
表 4.5 リンク時のエラーメッセージへの対処方法
項番 現象 確認内容 対処方法
1
リンク時にエラー No. 314 cannot foundsection が出力される。
リンケージエディタの startオプションにおいて、コン
パイラ出力のセクション名
を大文字で指定しているか。
正しいセクション名を指定してください。
2 リンク時にエラー No. 105 undifinedexternal symbol が出力される。
C/C++プログラムとアセン
ブリプログラム間で変数を
相互参照している場合、アセンブリプログラム内で下
線を付加しているか。
正しい変数名で参照してくださ
い。
C/C++プログラムで C ライ
ブラリ関数を使用していな
いか。
リンク時に入力ライブラリとし
て標準ライブラリを指定してく
ださい。
未定義参照シンボル名が__で始まっていないか。
(標準ライブラリ中の実行時ルーチンを使用していま
す)
C ライブラリ関数の標準入
出力ライブラリを使用して
いないか。
低水準インタフェースルーチン
を作成してリンクしてくださ
い。
3 C/C++ソースレベルデバッグができない。 コンパイル時に debug オプ
ション、リンク時に sdebugオプションを指定したか。
コンパイル時に debug オプシ
ョン、リンク時に sdebug オプ
ションを指定してください。
リンケージエディタの
Ver.5.3 以上を使用しているか。
リンケージエディタの Ver.5.3以上を使用してください。
4 リンク時に、エラー No. 108 relocation sizeoverflow が出力される。
GBR ベース変数の指定で、指定した変数のオフセット
は制限内におさまっている
か。
制限を越えるデータに対し、#pragma gbr_base/ gbr_base1宣言を削除してください。
5 リンク時に、エラー No. 104 duplicatesymbol が出力される。
同じ名称の変数または関数を複数のファイル内で外部
定義していないか。
名前を変更するかまたは staticを指定してください。
複数のファイルでインクル
ードされるヘッダファイル
内で変数または関数を外部定義していないか。
(#pragma inline/ inline_asm指定した関数でも同様です)
static を指定してください。
なお、オブジェクトファイルがデバッグ情報付きであっても、リンク時に"-sdebug"オプションを
指定しないとデバッグ情報ファイルは出力されません。このとき、シミュレータ・デバッガでのソ
ースレベルデバッグは行えなくなります。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
287
4.3 シミュレータ・デバッガとの関連ロードモジュールをシミュレータ・デバッガを用いて実行した場合、"MEMORY ACCESS ERROR"
を発生する可能性があります。安全のため、下記の回避方法のどちらかを適用してください。
(1) シミュレータ・デバッガ使用時も実機と同様のメモリをマッピングする(必ず 1 つのセク
ションの総バイト数は 4 の倍数になる)。
(2) リンク時、P セクションを除くすべてのセクションの後に下記のアセンブリ言語プログラ
ムから作成するダミーセクションをリンクする。
アセンブリ言語プログラム
.SECTION DM,DUMMY,ALIGN=1
.RES.B 3
.END
リンク時の結合例
• コマンドオプションの場合
-START=P,C,DM/0400,B,DM,D,DM/01000000• サブコマンドファイルの場合
START P,C,DM(0400),B,DM,D,DM(01000000)
シミュレータ・デバッガを用いてソースレベルデバッグを行う際の注意事項を以下に示します。
(1)リンケージエディタは、Ver.6.0 以上を使用してください。
(2)コンパイル時には"-debug"オプションをリンク時には"sdebug"オプションを指定してくだ
さい。
(3)関数内で当該関数のローカルシンボルを参照できないことがあります。
(4)1 行のソース行に複数のステートメントを記述した場合、1 つのステートメントしか表示
できません。
(5)最適化により消失したソース行のデバッグはできません。
(6)最適化により行の入れ替え等が発生するため、プログラムの実行順序や逆アセンブル表
示がソースリストの記述順序とは異なる場合があります。
例)
C 言語プログラム
12 for (i=0; i<6; i++)13 {14 j = i+1;15 j++;16 }17 j++;
シミュレータ・デバッガでの逆アセンブル表示
14 j = i+1;12 for (i=0; i<6; i++)17 j++;(7)for 文、while 文はループ文の入口と出口で 2 回逆アセンブル表示を行うことがあります。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
288
4.4 日立統合化環境
4.4.1 日立統合化環境からのオプション指定方法
Options メニューからオプションを指定することができます。日立統合化環境からのオプション
指定方法を示します。
■ C/C++コンパイラ
Options メニューから SH C/C++ Cpmpiler…を選択し、SH C/C++ Cpmpiler Options(Debug)ダイア
ログボックスを開きます。
(1)[Source]タグ
表 4.6 [Source]タグの項目名とコンパイルオプションの対応表
ダイアログボックス コンパイルオプション
Show entries for
Include Files Directroies
Preinclude Files
Defines
-include=<パス名>
-preinclude=<ファイル名>
-define=<マクロ名>=<名前>
/<マクロ名>=<定数>
/ <マクロ名>
図 4.8 [Source]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
289
(2)[Object]タグ
表 4.7 [Object]タグの項目名とコンパイルオプションの対応表
ダイアログボックス コンパイルオプション
Object file Type -code=machinecode/asmcode
Genereate debug information -debug/-nodebug
Section
Program section (P)
Const section (C)
Data section (D)
Uninitialized data section (B)
-section=program=<セクション名>
-section=const=<セクション名>
-section=data=<セクション名>
-section=bss=<セクション名>
省略時:( p=P, c=C, d=D, b=B )
Store string data in -string=const/data
Use 16bit short address -abs16=run/all
Output directory -objectfile=<ファイル名>
図 4.9 [Object]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
290
(3)[List]タグ
表 4.8 [List]タグの項目名とコンパイルオプションの対応表
ダイアログボックス コンパイルオプション
Generate List File -listfile[=<ファイル名>]/nolistfile
Contents
Object list
Statistics
Source code list
After include expansion
After macro expansion
-show
-show=object/noobject
-show=statistics/nostatistics
-show=source/nosource
-show=include/noinclude
-show=expansion/noexpansion
図 4.10 [List]タグのダイアログボックス
-nolist と-show オプションでは-nolist オプションが優先して評価されます。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
291
(4)[Optimize]タグ
表 4.9 [Optimize]タグの項目名とコンパイルオプションの対応表
ダイアログボックス コンパイルオプション
Optimization -optimeize=0/1
Speed or size
Optimize for speed
Optimize for size
Optimize for both speed and size
-speed
-size
-nospeed
Generate file for inter-module optimization -goptimize
Inline function nesting -nestinline=<数値>
Automatic inline expansion -inline/inline=<数値>/noinline
Switch statement -case=ifthen/table
図 4.11 [Optimize]タグのダイアログボックス
• Speed or Size は Optimize for both speed and size を選択してください。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
292
(5)[CPU]タグ
表 4.10 [CPU]タグの項目名とコンパイルオプションの対応表
ダイアログボックス コンパイルオプション
CPU -cpu=sh1/sh2/sh2e/sh3/sh3e/sh4
Division -division=cpu/peripheral/nomask
Endian -endian=big/little
FPU -fpu=single/double
Round to -round=zero/near
Denormalized number allower as a result -denormalization=off/on
Position Independent Code (PIC) -pic=0/1
Treat double as float -double=float
図 4.12 [CPU]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
293
■ OptLinkerOptions メニューから SH IM OptLinker optios…を選択し、SH IM OptLinker optios(Debug)ダイア
ログボックスを開きます。
(6)[Input]タグ
表 4.11 [Input]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
Input files
Relocatable files and object files
Library files
Input *1
Library
Defines Define
Use entry point Entry
Use external subcommand file Subcommand
*1:プロジェクトに登録されているファイルについては明示的に追加する必要はなく
コンパイル/アセンブルしないオブジェクト等をリンクする場合に指定する。
図 4.13 [Input]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
294
(7)[Output]タグ
表 4.12 [Output]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
Form of load module ELF,SYSROF,SYSROFPLUS
Type of lode module Form=a/r
Debug information
None
In output load module
In separate debug file
Nodebug
Debug
Sdebug
ROM to RAM mapped sections Rom
Generate map file Print
Load module directory Output
図 4.14 [Output]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
295
(8) [Optimize]タグ
表 4.13 [Optimize]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
Optimize Optimize
Unify strings Optimize の string_unify
Eliminate dead code Optimize の symbol_delete
Reallocate registers Optimize の register
Eliminate same code Optimize の same_code
Optimize branches Optimize の branch
Eliminated size Samesize
Output information Information
Forbit item
Elimination of dead code
Elimination of same code
Symbol_forbid
Samecode_forbid
図 4.15 [Optimize]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
296
(9) [Section]タグ
表 4.14 [Section]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
Relocatable section start address START
Genereate external symbol file FSYMBOL
図 4.16 [Section]タグのダイアログボックス
[Add]ボタンでセクションの割り付けを新しく指定することができます。
[Modify]ボタンで既に指定されたセクション名、アドレスを編集することができます。
[New Overlay]ボタンで複数のセクションを同一アドレスに割り付けることができます。
[Remove]ボタンで既に指定されたセクションを削除することができます。
セクションの並び順は[UP]/[DOWN]ボタンで変更することができます。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
297
前頁のダイアログボックスの内容をリンケージエディタのサブコマンドファイルに記述した場合。
RAM_sct1 と RAM_sct2 は同一セクションに割り付けられます。
【注】リンケージエディタ用サブコマンドファイルの詳しい作成方法は、「H シリーズ リンケージ
エディタ、ライブラリアン、オブジェクトコンバータユーザーズマニュアル」を参照してください。
START RSTHandler START INITHandler,VECTTBL,INITTBL,IntPRG(800) START RestPRG(1000) START P,C,D(2000) START RAM_sct1:RAM_sct2(F00000)
START B,R(7F000000)START Stack(7FFFFBF0)
図4.16上で
見えている部分
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
298
(10)[Verify]タグ
表 4.15 [Verify]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
CPU information file path Cpu
Stop linkage on CPU information warning Cpucheck
図 4.17 [Verify]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
299
(11) [Other]タグ
表 4.16 [Other]タグの項目名と Optlinksh オプションの対応表
ダイアログボックス Optlinksh のオプション
Exclude unreferenced external symbol
Align section Align_section
Check for undefined symbols Udfcheck
Check for unlinked sections Check_section
図 4.18 [Other]タグのダイアログボックス
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
300
4.4.2 日立統合化環境からのコンパイラバージョンの指定
日立統合化環境でのコンパイラバージョンの指定方法について説明します。バージョンの指定は
日立統合化環境をアップグレードすることで可能になります。
旧バージョン(例 HEW1.0:SH5.1.0)で作成したワークスペースを新バージョン(例
HEW1.1:SH5.1A.0)でオープン時、図 4.20 の確認ダイアログを表示し、変更可能にします。旧バー
ジョンのツールが登録されている場合は、図 4.19 のように[Tools -> Upgrade...]で同様のダイアログ
([Missing Version]が[Current Version]と表示されます。)を表示し、コンパイラバージョンを指定し
てください。
図 4.19 Hitachi Enbedded Workshop
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
301
図 4.20 コンパイラバージョンの指定
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
302
4.5 モジュール間最適化ツール
4.5.1 モジュール間最適化ツール概要
モジュール間最適化ツールは、コンパイラが出力した複数のオブジェクトプログラムを入力とし
オブジェクトプログラムをまたがって最適化を実行した上で、リンケージエディタを起動し結合お
よび編集するソフトウェアシステムです。従来コンパイラでは、最適化できなかった、複数オブジ
ェクトの最適化を行います。
通常のリンクとモジュール間最適化を行った場合の処理の流れを図 4.21 に示します。
図 4.21 通常のリンクとモジュール間最適化を行った場合の処理の流れ
【注】 optlnksh は、内部でリンカを起動しますが lnk ではないので optlnksh のオプションとして lnkのオプションを直接指定することはできません。lnk のオプションは必ずリンカのサブコマ
ンドファイルを使用して指定してください。
C/C++ソース
プログラム
C/C++コンパイラ
リンケージエディタ
(lnk)
ロード
モジュール
オブジェクト
プログラム
付加情報
ファイル
モジュール間最適化ツール
(optlnksh)
最適化処理
最適化済み
オブジェクト
プログラム
リンケージエディタ
(lnk)
モジュール間
最適化済み
ロード
モジュール
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
303
また、本最適化ツールを使用することによりロードモジュールのフォーマットとして
• ELF/DWARF フォーマット(オブジェクト部:ELF、デバッグ情報部:DWARF)• SYSROF フォーマット(オブジェクト部:SYSROF、デバッグ情報部:SYSROF)• SYSROF PLUS フォーマット(オブジェクト部:SYSROF、デバッグ情報部:DWARF)
の 3 通りの出力が可能です。
【注】ロードモジュールを SYSROF フォーマット以外のフォーマットにするには、本ツールを起
動させなければなりません。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
304
4.5.2 最適化ツールの起動方法
最適化ツールの起動するコマンドラインの形式は次の通りです。
optlnksh[△<オプション>...]
最適化ツールを実行するためには、関連ソフトウェアを使用して、次のファイルを作成する必要
があります。(括弧内は関連ソフトウェア名称)
オブジェクトプログラム(SuperH RISC engine C/C++コンパイラ Ver.5.1)
リンケージエディタ用サブコマンドファイル
以下、最適化ツールの基本的な操作方法をサンプルプログラムを用いて説明します。
test1.c C プログラム
test1.sub リンケージエディタ用サブコマンドファイル
(1)プログラムのコンパイル
test1.c をコンパイルします。このとき必ず goptimize オプションを指定します。また、ここで debugオプションを指定することにより、ソースレベルデバッグを行うためのデバッグ情報を出力する
ことができます。
shc△–goptimize△–debug△test1.c(RET)
(2)デフォルトライブラリの設定
リンク時に使用する標準ライブラリをデフォルトライブラリとして設定します。デフォルトラ
イブラリについての詳細は「H シリーズ リンケージエディタ、ライブラリアン、オブジェクトコン
バータユーザーズマニュアル」を参照してください。
PC版(DOS プロンプト使用時) : set△HLNK_LIBRARY1=<ライブラリパス>¥shc.lib(RET)
UNIX 版 : setenv△HLNK_LIBRARY1<ライブラリディレクトリ>/shc.lib(RET)
(3)最適化ツールの実行
test1.obj の最適化を実施後、ロードモジュールを作成します。
ここでは、リンケージエディタ用サブコマンドファイルの指定は省略できません。必ず指定し
てください。
例 1) オブジェクトプログラムの最適化、結合
optlnksh△–optimize△–subcommand=test1.sub(RET)
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
305
<test1.sub>
align_section check_section
input test1 ; 入力ファイル名を指定します。
entry _main ; 実行開始の関数名を指定します。
sdebug ; デバッグ情報の出力を指定します。
start P,C(200),D,B(08000) ; 各セクションの開始アドレスを指定します。
exit ; 処理を終了します。
■ 説明 :
リンケージエディタ用サブコマンドファイルの作成方法は、「H シリーズ リンケージエディタ、
ライブラリアン、オブジェクトコンバータユーザーズマニュアル」を参照してください。
例 2) 最適化オプションの指定
optimize オプションのサブオプションによって、最適化の内容を指定することができます。
optlnksh△–optimize=speed△–subcommand=test1.sub(RET)
例 3) サブコマンドによる最適化オプションの指定
最適化ツールのオプションはサブコマンドとして、リンケージエディタ用サブコマンドフ
ァイル内で指定することもできます。
optlnksh△–subcommand=test2.sub(RET)
<test2.sub>
align_section check_section
optimize speed ; 最適化ツール用オプションを指定します。
input test1 ; 入力ファイル名を指定します。
entry _main ; 実行開始の関数名を指定します。
sdebug ; デバッグ情報の出力を指定します。
start P,C(200),D,B(08000) ; 各セクションの開始アドレスを指定します。
exit ; 処理を終了します。
(4)コマンドライン入力形式、オプションの表示
標準出力画面上にコマンドの入力形式、オプションの一覧を表示します。
optlnksh(RET)【注】 モジュール間の最適化のオプション/サブコマンドの詳細については「SuperH RISC engine
C/C++コンパイラユーザーズマニュアル 5.3 オプション/サブコマンド」を参照してく
ださい。
4. [アセンブリ言語プログラムおよびクロスソフトとの関連
306