Skip to main content

IAR Embedded Workbench for Arm 9.70.x

変換の微調整

このセクションの内容:

最適化レベルごとに、一部の変換を個別に無効にできます。変換を無効にするには、適当なオプション(コマンドラインオプション‑‑no_inline、IDEでの同等オプションの[関数インライン化]など)か、#pragma optimizeディレクティブを使用します。以下の変換は、個別に無効化することができます。

  • 共通部分式除去

  • ループ展開

  • 関数インライン化

  • コード移動

  • 型ベースエイリアス解析

  • 静的クラスタ

  • 命令スケジューリング

  • ベクトル化

共通部分式除去

デフォルトでは[中]、[高]の最適化レベルにおいて、冗長な共通部分式が除去されます。この最適化により、コードサイズと実行時間の両方が削減されます。ただし、生成されるコードのデバッグが困難になる場合があります。

注記

このオプションは、最適化レベルが[なし]、[低]の場合には動作しません。

危険

コマンドラインオプションの詳細については、‑‑no_cseを参照してください。

ループ展開

ループ展開とは、コンパイル時に繰り返し回数を決定できるループのコード本体の複製を意味します。 ループ展開によって、複数の繰り返しに分割することにより、ループのオーバヘッドが少なくなります。

この最適化は、ループのオーバヘッドがループ本体合計の大部分を占めるような、小さいループの場合に最も効率的です。

ループ展開は、、最適化レベルが[高]の場合に実行可能で、通常は実行時間が短縮されますが、コードサイズは増加します。また、生成されるコードのデバッグも困難になる場合があります。

コンパイラは、ヒューリスティックにより、展開するループを決定します。ループのオーバヘッド減少が明確な、比較的小さいループのみが展開されます。実行する最適化の内容(速度、サイズ、速度とサイズのバランス)に応じて、異なるテクニックが使用されます。

注記

このオプションは、最適化レベルが[なし]、[低]、[中]の場合には動作しません。

危険

ループの展開を無効にするには、コマンドラインオプション‑‑no_unrollを使用します(‑‑no_unrollを参照)。

関数インライン化

関数インライン化とは、定義がコンパイル時に判明している関数を、その呼び出し元関数の本体に統合し、呼び出しによるオーバヘッドを解消することです。 通常この最適化では実行時間は短縮されますが、コードサイズが大きくなることがあります。

詳細については、インライン関数を参照してください。

危険

関数のインライン化を無効にするには、コマンドラインオプション ‑‑no_inlineを使用します(‑‑no_inlineを参照)。

コード移動

ループ不変式や共通部分式の評価式を移動し、冗長な再評価を回避します。この最適化は、最適化レベルが[中]またはそれ以上の場合に実行可能で、通常はコードサイズと実行時間が短縮されます。ただし、生成されるコードのデバッグは困難になる場合があります。

注記

このオプションは、最適化レベルが[中]以上の場合にのみ有効です。

危険

コマンドラインオプションの詳細については、‑‑no_code_motionを参照してください。

型ベースエイリアス解析

複数のポインタが同一メモリ位置を参照する場合、これらのポインタをそれぞれのエイリアスといいます。エイリアスが存在すると、特定の値が変更されるかどうかがコンパイル時にわからない場合があるため、最適化が困難になります。

型ベースエイリアス解析による最適化では、同一オブジェクトへのすべてのアクセスは、そのオブジェクトの宣言型またはchar型の使用を前提としています。これにより、コンパイラはポインタが同一のメモリ位置を参照しているかどうかを検出することができます。

型ベースエイリアス解析は、最適化レベルが[高]の場合のみ実行されます。標準のC/C++アプリケーションコードに準拠するアプリケーションコードの場合、この最適化によってコードサイズが減少して実行時間が短縮されることがあります。ただし、非標準のC/C++コードの場合は、予期せぬ動作の原因となるコードをコンパイラが生成することがあります。そのため、この最適化を無効にできるようになっています。

注記

このオプションは、最適化レベルが[なし]、[低]、[中]の場合には動作しません。

危険

コマンドラインオプションの詳細については、‑‑no_tbaaを参照してください。

short F(short *p1, long *p2)
{
  *p2 = 0;
  *p1 = 1;
  return *p2;
}

型ベースエイリアス解析では、p1にポイントされるshortへのライトアクセスは、p2がポイントするlongの値に影響しないと見なされます。このため、この関数が0を返すことがコンパイル時に分かっています。しかし、規格に準拠していないC/C++コードでは、これらのポインタが同一の共用体に含まれ、相互に重複することがあります。明示的なキャストを使用する場合、異なるポインタ型のポインタが同一メモリ位置を参照するように強制することもできます。

静的クラスタ

静的クラスタが有効にされている場合、同じモジュール内で定義される静的およびグローバル変数は、同じ関数でアクセスされる変数がそれぞれ近くに格納されるように配置されます。これにより、コンパイラは、いくつかのアクセスに対して同じベースポインタを使用できるようになります。

注記

このオプションは、最適化レベルが[なし]、[低]の場合には動作しません。

危険

コマンドラインオプションの詳細については、‑‑no_clusteringを参照してください。

命令スケジューリング

コンパイラは、生成されるコードのパフォーマンスを改善する命令スケジューラとして機能します。 スケジューラは、その目的を達成するため、命令を再配置して、マイクロプロセッサ内のリソース競合から広がるパイプラインストールの数を最小に抑えます。

危険

コマンドラインオプションの詳細については、‑‑no_schedulingを参照してください。

ベクトル化

連続するベクトル化変換は、アセンブラコードを書き込んだり、組込み関数を使用したりせずに、NEONベクタ操作にループします。これは移植を強化します。ターゲットプロセッサにNEON機能があり、自動ベクトル化が有効な場合にのみ、ループがベクトル化されます。自動ベクトル化は64ビットモードではサポートされていません。

ベクトル化は、、最適化レベルが[高]の場合に実行可能で、通常は実行時間が短縮されますが、コードサイズは増加します。また、生成されるコードのデバッグも困難になる場合があります。

注記

このオプションは、オプション--do_cross_callを使用する場合を除いて、最適化レベルが[なし]、[低]、[中]、高バランス、または高サイズの場合には動作しません。個々の関数でベクトル化を無効にするには、optimizeまたはvectorizeのいずれかのプラグマディレクティブを使用します。詳細はoptimizeおよびvectorizeを参照してください。

危険

コマンドラインオプションの情報については、‑‑vectorizeを参照してください。