プログラム全体ではなく、 C++ コードサンプルに対して静的解析プロジェクトを行うことを考えています。一般に、静的解析には単純な中間表現が必要ですが、そのような表現は、プログラム コード全体がないと正確に作成できません。
それでも、 Java用のそのようなツールがあることは知っています。それは基本的に欠落している情報を「推測」し、静的分析を行うことができます。
部分的な C++ コードを何らかの中間形式 (LLVM バイトコードなど) に変換するために使用できる同様のものはありますか?
プログラム全体ではなく、 C++ コードサンプルに対して静的解析プロジェクトを行うことを考えています。一般に、静的解析には単純な中間表現が必要ですが、そのような表現は、プログラム コード全体がないと正確に作成できません。
それでも、 Java用のそのようなツールがあることは知っています。それは基本的に欠落している情報を「推測」し、静的分析を行うことができます。
部分的な C++ コードを何らかの中間形式 (LLVM バイトコードなど) に変換するために使用できる同様のものはありますか?
原則として、あなたが推測するなら、あなたは間違っていると推測します。このような推測に基づく静的分析装置からの苦情は誤検知であり、高い拒否率を引き起こす傾向があります。
推測を主張する場合は、任意のC++フラグメントを解析できるツールが必要になります。(「このメソッドの静的分析を推測します...」)。ほとんどのC++パーサーは、フラグメントではなく、完全なソースファイルのみを解析します。
また、部分的なシンボルテーブルを作成する方法も必要です。(「IはFOOの引数としてリストされていますが、型情報がなく、FOOの呼び出しに続くステートメントで宣言されているIと同じではありません」)。
C ++フロントエンドを備えたDMSソフトウェアリエンジニアリングツールキットは、フラグメントの解析を提供でき、部分的なシンボルテーブルの踏み台として使用できます。
DMSは、DMSに提供される明示的な言語定義によって決定されるように、コードの一般的な解析/分析/変換を提供します。C ++フロントエンドは、完全で堅牢なC ++フロントエンドを提供し、DMSがC ++を解析し、ASTを構築し、C ++ルックアップルールがエンコードされている属性文法(AG)を使用してそのようなASTのシンボルテーブルを構築できるようにします。AGは、ASTノード上でエンコードされた機能スタイルの計算です。C ++シンボルテーブルビルダーは、本質的に大きな関数型プログラムであり、その部分はC++のBNF文法規則に関連付けられています。
一般的な解析機構の一部として、言語定義(C ++フロントエンドなど)が与えられると、DMSは、組み込みのパターン言語を使用して、その言語の任意の(非)終端記号を解析できます。したがって、DMSは、式、メソッド、宣言など、またはその他の整形式のコードフラグメントを解析し、ASTを構築できます。整形式でないフラグメントが提供されている場合、現在、フラグメントの解析で構文エラーが発生します。DMSのエラー回復を拡張して、もっともらしいAST修正を生成し、任意の要素を解析することが可能です。
シンボルテーブル構築機構の多くは、構築されるシンボルテーブルの他の部分に依存しているため、部分的なシンボルテーブルはより困難です。ただし、これはすべてAGとしてコード化されているため、解析されたフラグメントに関連するAGの部分、たとえば、メソッドのsymoblテーブル構築ロジックを実行できます。AGは、欠落しているシンボル定義に関する「仮定」で動作できるように、おそらく大幅に変更する必要があります。これらは事実上制約になります。もちろん、欠落しているシンボルはいくつかの原因のいずれかである可能性があり、可能なシンボルテーブルの構成になってしまう可能性があります。検討:
{ int X;
T*X;
}
Tが何であるかがわからないため、句のタイプ(およびその構文カテゴリーでさえ)を一意に判別することはできません。(DMSはT * Xを解析します。一致する解釈が複数ある可能性があるため、あいまいな解析を報告します。LR(1)パーサーでC ++を解析できない理由を参照してください。 )
この部分的な解析と部分的なシンボルテーブルについては、すでにいくつかの作業を行っています。ここでは、DMSを実験的に使用して、一部の条件付きステータスが未定義のプリプロセッサ条件付きコードをキャプチャしました。これにより、条件付きシンボルテーブルエントリが作成されます。検討:
#if foo
int X;
#else
void X(int a) {...}
#endif
...
#if foo
X++;
#else
X(7);
#endif
条件付きシンボルを使用すると、このコードはチェックと入力できます。Xのシンボルテーブルエントリは、「X ==> int if foo else ==> void(int)」のようになります。
制約のある大きなプログラムフラグメントについて推論するというアイデアは素晴らしいと思いますが、それは本当に難しいと思います。静的分析を行うために、制約に関する十分な情報を解決しようとすることは永遠に続くでしょう。
SciTools による 4 C++の理解は、ソース コードを解析し、さまざまな指標を提供する製品です。ツールとしてはソース コード ブラウザのようなものですが、Visual Studio の Intellisense も同様に優れているため、個人的には使用しません。
その本当の力は、C および Perl APIが付属していることです。したがって、それを使用して、独自の静的分析ツールを作成できます。はい、欠落しているコード ファイルをうまく処理します。また、4 つの C++ が Windows やその他のオペレーティング システムで動作することも理解してください。
中間コードに関する最後の質問についてですが、Understand 4 C++ は「中間」形式を提供しませんが、その API を使用すると、抽象構文ツリー上に多くの機能を提供する抽象化レイヤーが提供されます。ソースコードを分析します。私はこの API と、ネイティブ C API をラップするマネージ C++ API (私が作成し、 codeplex で公開しています) を使用して、自分の仕事で多くのツールを作成しました。
LLVMバイトコードについては知りませんが、PcLintと呼ばれる古い格言があります
http://www.gimpel.com/html/index.htm
コードの一部を投稿できるオンライン テスト モジュールもあります。