フロー解析エンジンは、解析されたコードからパスを分析し、さまざまな問題を検出します。アプリケーション全体にわたって「実行される可能性があるパス」をすべて解析するのは現実的ではない場合もあるため、解析レベルの深さを設定できます。解析レベルが深いほど、発見される違反の数が増えます。ただし、パフォーマンスが低下し、若干メモリの消費量が増加します。
解析の深さは、DTP でテスト コンフィギュレーション インターフェイスを使用して設定します。 Report Center > [テスト コンフィギュレーション] > [静的解析] > [フロー解析詳細設定] > [パフォーマンス] > [解析の深さ] にアクセスし、以下のいずれかのオプションを選択します。
デフォルトの解析レベルの深さは [標準] です。
解析レベルの深さの他に、フロー解析エンジンはタイムアウト設定を利用して、妥当な時間内で解析が終了するようにします。タイムアウトの設定を行うには、DTP でテスト コンフィギュレーション インターフェイスを使用します。Report Center > [テスト コンフィギュレーション] > [静的解析] > [フロー解析詳細設定] > [パフォーマンス] > [タイムアウトの方針] にアクセスし、以下のいずれかのオプションを選択します。
デフォルトのタイムアウト オプションは [時間] であり、タイムアウト秒数は 60 秒です。解析中に発生したフロー解析タイムアウトについての情報を得るには、解析後に生成されるレポートで [セットアップの問題] セクションを確認してください。
スワップ モードでは、解析データをハードディスクに書き込みます。解析データのスワップは、インクリメンタル解析と同じ永続性記憶装置を使用し、インクリメンタル解析と似たプロセスで実行されます。大きなプロジェクトで解析を実行する場合、解析するソース コードの意味論的モデルを表す解析データが、フロー解析が使用できるすべてのメモリを消費する可能性があります。この現象が発生した場合、フロー解析は現在必要ない解析データをメモリから削除し、後でディスクから再び読み込みます。
一般的に、 Xmx JVM オプションを使って JVM ヒープのサイズを大きくしてを実行することを推奨します。これはスワップを最小限にするためであり、結果としてパフォーマンスが向上します。充分なメモリがある場合、解析データのスワップは無効化しても構いません。スワップを無効化すると、コード解析の速度が上がる場合があります。
スワップ モードを有効化/無効化するには、DTP のテスト コンフィギュレーション画面を使用します。
ディスクへの解析データのスワップを有効化: デフォルトで 無効 です。大量のメモリを必要としない小さなサイズのプロジェクトに対してフロー解析を実行する場合、または 64-bit システムのように十分なメモリがある場合、このオプションを無効化すると、解析のパフォーマンスが向上する場合があります。
DTP のテスト コンフィギュレーション画面では、次のオプションを設定できます。
[null チェック メソッド] オプションを指定すると、メソッドに null パラメーターが渡されたときに返す期待値を指定できます。そのため、偽陽性が減少するほか、null 変数の値が不明なときに通常作成される過剰なパスが減少します。
[有効] チェックボックスをオンにして、以下の情報を指定します。
フロー解析は解析スコープでメソッドを解析します。 たとえばサード パーティのライブラリなど、現在の解析スコープの外にメソッドがある場合、null チェック メソッドでパラメーターを指定する必要があります。この例のクラス Account
および AccountManager
は、別のアセンブリに定義されており、解析スコープの外にあります。AccountManager
クラスは、静的メソッドを使って次のように Account
クラスをチェックします。
public class Account { public int Balance { get; set; } } public class AccountManager { public static bool IsNullOrEmpty(Account account) { return account == null || account.Balance == 0; } } |
そして、フロー解析の ルール BD.EXCEPT.NR ルールによって解析される次のクラスがあります。
public class SomeClass { void SomeMethod() { Account account = null; //some other actions if (!AccountManager.IsNullOrEmpty(account)) { Console.WriteLine(account.Balance); } } } |
フロー解析は メソッド IsNullOrEmpty()
の戻り値が不明であると仮定します。その理由は、このメソッドは解析スコープ中にないからです。フロー解析は if ブランチを解析し、それらの文の 1 つで違反を発見します。しかし、変数が null の場合、IsNullOrEmpty()
メソッドの呼び出しは true を返します。
null チェック メソッドのメソッド リストに AccountManager.IsNullOrEmpty()
を追加して戻り値を指定することで、追跡された変数がこのメソッドに渡されたときにフロー解析は違反をレポートしなくなります。なぜなら、if
ブランチが解析されず、その結果として偽陽性が回避されるからです。
null チェック メソッドのパラメーターに追加されるメソッドは、単純な Bool 型の戻り値を持つ、static メソッドであるべきです。さらに、null チェック メソッドは入力パラメーターを 1 つだけ持つことができます。 この制限事項は、パラメーター指定が複雑になり過ぎることを防ぎ、null チェック メソッドの結果に影響しかねない変数が他にないことを保証します。
[リソース] タブでは、BD.RES (リソース) カテゴリのルールを使ってチェックするリソースを定義することができます。BD.RES カテゴリのルールは、[リソース] タブで定義および有効化されているすべてのリソースについて、リソースが正しく使用されているかをチェックします。
矢印をクリックして [リソース アロケーター] および [リソース クローザー] タブを開き、表示されたテーブルにリソースのアロケーター/クローザーの情報を入力します。詳細については以下のセクションを参照してください。
[リソース アロケーター ] テーブルには、リソースを生成するメソッドの記述を入力できます。テーブルには以下の列があります。
一般的に、アロケーター メソッドはエラー コードを返してリソース割り当ての失敗を表します。アロケーターメソッドはリソースを返し、通常 NULL 値はリソース割り当ての失敗を表します。リソース リークを探すときに、フロー解析はリソースの割り当てが成功したか失敗したかを把握できる必要があります。これは、割り当てが実際に発生したパス上で発見されない割り当て解除メソッドへの呼び出しだけをフロー解析がレポートするのに役立ちます。リソース アロケーターメソッドがリソースを返し、NULL でない場合、フロー解析はリソースが正常に割り当てられたと推測します。
[リソース クローザー] テーブルには、リソースをクローズするメソッドの記述を入力できます。テーブルには以下の列があります。
[常に解析すべきメソッド] オプションを使用すると、実行パス中で見つかったとき常に解析するメソッドを定義できます。これにより、特定のパスを解析したとき、通常は入らないメソッドを必ず解析するようにできます。
[有効] チェックボックスをオンにし、テーブルに以下の情報を入力します。
リリース 10.4.10 で導入された新しいパーサーはC# コードだけをサポートしているため、dotTEST は Visual Basic を古いパーサーで解析します。テスト スコープに Visual Basic コードだけが含まれている場合、自動的に古いパーサーが使用され、追加の設定は必要ありません。テスト スコープに Visual Basic と C# の両方が含まれている場合、自動的に新しいパーサーが使用され、Visual Basic コードは解析されません。1 回の実行で C# と Visual Basic の両方を解析するには、dottestcli.properties ファイルで次の設定を行います。
flowanalysis.newparser.enabled=false |
複数のプロジェクトから構成される大規模なソリューションを分析すると、メモリ使用量が増加し、パフォーマンスが低下する可能性があります。システムのメモリが不足した場合は、完了前にフロー解析がフリーズすることがあります。フロー解析が正常に完了するようにするには、テスト コンフィギュレーションの .properties ファイルで次のオプションを指定して、個々のプロジェクトを個別に分析するように dotTEST を構成します。
flowanalysis.analyze.project.by.project=true |
これにより、メモリ消費を大幅に削減し、パフォーマンスを向上させ、フロー解析が完了する前にフリーズするのを防ぐことができます。
このオプションを有効にすると、dotTEST は個々のプロジェクトを解析しますが、プロジェクト間の解析は実行しません。このため、
flowanalysis.analyze.project.by.project
オプションが無効の場合、解析結果は、同じスコープでレポートされた結果と矛盾することがあります。