次に、v に指定できる値を示します。
表 A–42 -xport64 の値
値 |
意味 |
---|---|
no |
32 ビット環境から 64 ビット環境へのコード移植に関し、まったく警告を生成しない。 |
implicit |
暗黙の変換に関してのみ警告を生成する。明示的なキャストが存在する場合には警告を生成しない。 |
full |
32 ビット環境から 64 ビット環境へのコード移植に関し、あらゆる警告を生成する。具体的には、64 ビット値の切り捨て、ISO 値保護規則に基づく 64 ビットへの符号拡張、ビットフィールドの配置の変更などです。 |
-xport64 を指定しない場合のデフォルトは、-xport64=no です。-xport64 を値なしで指定した場合は、コンパイラでは -xport64=full が指定されます。
以降では、型の切り捨て、符号の拡張、ビット配置の変更を行うコード例を紹介します。
V9 などの 64 ビットアーキテクチャーを移植する場合、データが切り捨てられることがあります。切り捨ては、初期化時に代入によって暗黙的に行われることもあれば、明示的なキャストによって行われることもあります。2 つのポインタの違いは typedef ptrdiff_t であり、32 ビットモードでは 32 ビット整数型、64 ビットモードでは 64 ビット整数型です。大きいサイズから小さいサイズの整数型に切り捨てると、次の例にあるような警告が生成されます。
example% cat test1.c int x[10]; int diff = &x[10] - &x[5]; //warn example% CC -c -xarch=v9 -Qoption ccfe -xport64=full test1.c "test1.c", line 3: Warning: Conversion of 64-bit type value to "int" causes truncation. 1 Warning(s) detected. example% |
明示的キャストによってデータが切り捨てられている場合に、64 ビットのパイルモードでの切り捨て警告を抑止するには、-xport64=implicit を使用します。
example% CC -c -xarch=v9 -Qoption ccfe -xport64=implicit test1.c "test1.c", line 3: Warning: Conversion of 64-bit type value to "int" causes truncation. 1 Warning(s) detected. example% |
64 ビットアーキテクチャーへの移植でよく発生するもう 1 つの問題として、ポインタの切り捨てがあります。これは常に、C++ におけるエラーです。切り捨てを引き起こす、ポインタのキャスティングなどの操作は、-xport64 を指定した場合に V9 ではエラー診断となります。
example% cat test2.c char* p; int main() { p =(char*) (((unsigned int)p) & 0xFF); // -xarch=v9 error return 0; } example% CC -c -xarch=v9 -Qoption ccfe -xport64=full test2.c "test2.c", line 3: Error: Cannot cast from char* to unsigned. 1 Error(s) detected. example% |
符号なし整数型の式において、通常の ISO C 値保護規則が符号付き整数値の符号拡張に対処している状況があるかどうかを、-xport64 オプションを使用してチェックすることもできます。こういった符号拡張は、実行時に微妙なバグの原因となる可能性があります。
example% cat test3.c int i= -1; void promo(unsigned long l) {} int main() { unsigned long l; l = i; // warn promo(i); // warn } example% CC -c -xarch=v9 -Qoption ccfe -xport64=full test3.c "test3.c", line 6: Warning: Sign extension from "int" to 64-bit integer. "test3.c", line 7: Warning: Sign extension from "int" to 64-bit integer. 2 Warning(s) detected. |
長いビットフィールドに対する警告を生成するには、-xport64 を使用します。こういったビットフィールドが存在していると、ビットフィールドの配置が大きく変わることがあります。ビットフィールド配置方式に関する前提事項に依存しているプログラムを、64 ビットアーキテクチャーに問題なく移植できるためには、あらかじめ確認作業を行う必要があります。
example% cat test4.c #include <stdio.h> union U { struct S { unsigned long b1:20; unsigned long b2:20; } s; long buf[2]; } u; int main() { u.s.b1 = 0XFFFFF; u.s.b2 = 0XFFFFF; printf(" u.buf[0] = %lx u.buf[1] = %lx\n", u.buf[0], u.buf[1]); return 0; } example% |
V9 における出力
example% u.buf[0] = ffffffffff000000 u.buf[1] = 0 |
警告が生成されるのは、-m64 などのオプションを指定して 64 ビットモードでコンパイルしたときだけです。