剽窃 他人の作品や論文を盗んで,自分のものとして発表すること. プログラムが剽窃される事例もある. Aさんのプログラム Xさんのプログラム

Slides:



Advertisements
Similar presentations
API 呼び出し列の差分を利用した Android アプリケーション比較ツールの 試作 井上研究室 神田 哲也.
Advertisements

Software Engineering Laboratory, Department of Computer Science, Graduate School of Information Science and Technology, Osaka University 保守支援を目的とした コードクローン情報検索ツール.
シーケンス図の生成のための実行履歴圧縮手法
TF-IDF法とLSHアルゴリズムを用いた 関数単位のコードクローン検出法
AGMアルゴリズムを用いた ギャップを含むコードクローン情報の生成
Myoungkyu Song and Eli Tilevich 発表者: 石尾 隆(大阪大学)
研究の背景 コードクローン ソースコード中に存在する一致または類似したコード片
リファクタリングのための 変更波及解析を利用した テスト支援ツールの提案
プログラム変更支援を目的とした コードクローン情報付加手法の提案と実装
動的スライスを用いたバグ修正前後の実行系列の差分検出手法の提案
川口真司 松下誠 井上克郎 大阪大学大学院情報科学研究科
プログラム実行履歴を用いたトランザクションファンクション抽出手法
アイテムセットマイニングを利用した コードクローン分析作業の効率向上
コードクローン検出技術と その利用法 神谷年洋‡, 植田泰士†, 肥後芳樹†, 楠本真二†, 井上克郎†
コードクローン分析ツールGeminiを用いたコードクローン分析手順
コードクローンの分布情報を用いた特徴抽出手法の提案
ギャップを含むコードクローンの フィルタリング手法の提案
コードクローンに含まれるメソッド呼び出しの 変更度合の分析
コードクローンに含まれるメソッド呼び出しの 変更度合の調査
ソードコードの編集に基づいた コードクローンの分類とその分析システム
コードクローンの集約によるリファクタリング支援システムの提案と実装
ネットワーク共生環境を築く情報技術の創出 テーマ4:高信頼性・高安全性を有するネットワーク共生環境の構築技術の創出
オブジェクト指向プログラミング言語に対応した コードクローン検出技法の提案と実験
コードクローンの分類に基づいた メソッド引き上げ手順の提案とその有効性評価
動的依存グラフの3-gramを用いた 実行トレースの比較手法
オブジェクト指向プログラムにおける エイリアス解析手法の提案と実現
動的スライスを用いたバグ修正前後の実行系列の差分検出手法
オブジェクト指向メトリクスを用いた 開発支援法に関する研究
クローンセットに対する主要編集者の分析法の提案と調査
クローン検出ツールを用いた ソースコード分析ツールの試作
コードクローン検出ツールを用いた ソースコード分析システムの試作と プログラミング演習への適用
リファクタリング支援のための コードクローンに含まれる識別子の対応関係分析
プログラム動作理解支援を目的とした オブジェクトの振舞いの同値分割手法
ソースコードの特徴量を用いた機械学習による メソッド抽出リファクタリング推薦手法
コードクローン統合分析ツール ICCA 肥後 芳樹† ,吉田 則裕† ,神谷 年洋‡,楠本 真二† ,井上 克郎†
コードクローンの動作を比較するためのコードクローン周辺コードの解析
コードクローンに対する一貫性のない変更に起因する欠陥の検出
柔軟に変更可能な字句解析機構を持つ コードクローン検出ツールの開発
プログラム実行履歴を用いたコードクローン検出手法
コードクローン検出に基づくデザイン パターン適用支援手法の提案と実現
コードクローン編集者数に着目した開発履歴の分析
多様なプログラミング言語に対応可能な コードクローン検出ツール CCFinderSW
Geminiを用いた効果的なコードクローン分析方法
○ 後藤 祥1,吉田 則裕2 ,井岡 正和1 ,井上 克郎1 1大阪大学 2奈良先端科学技術大学院大学
ソフトウェア保守のための コードクローン情報検索ツール
コードクローンの理解支援を目的としたコードクローン周辺コードの解析
コードクローン分類の詳細化に基づく 集約パターンの提案と評価
コーディングパターンの あいまい検索の提案と実装
JAVAバイトコードにおける データ依存解析手法の提案と実装
コードクローン間の依存関係に基づく リファクタリング支援環境の実装
オブジェクトの協調動作を用いた オブジェクト指向プログラム実行履歴分割手法
第7回OACISシンポジウム 大阪大学におけるソフトウェア工学研究と産学連携活動
プログラムスライスを用いた凝集度メトリクスに基づく 類似メソッド集約候補の順位付け手法
大阪大学 大学院情報科学研究科 コンピュータサイエンス専攻 井上研究室
コードクローン間の依存関係に基づく リファクタリング支援手法の提案と実現
オープンソースソフトウェアに対する コーディングパターン分析の適用
メソッドの同時更新履歴を用いたクラスの機能別分類法
ユビキタスコンピューティングの ための ハンドオーバー機能付きRMIの実装
コードクローン間の依存関係に基づく リファクタリング支援手法の提案と実現
欠陥検出を目的とした類似コード検索法 吉田則裕,石尾隆,松下誠,井上克郎 大阪大学 大学院情報科学研究科
容易に使用可能な grep風コードクローン検索ツール
エイリアス関係を考慮した Javaプログラム用静的スライシングツール
動的スライスを用いたバグ修正前後の実行系列の差分検出手法の提案
コードクローン解析に基づく デザインパターン適用候補の検出手法
メソッド抽出リファクタリングが 行われるメソッドの特徴調査
Geminiを用いた効果的なコードクローン分析方法
オブジェクト指向言語における セキュリティ解析アルゴリズムの提案と実現
Josh : バイトコードレベルでのJava用 Aspect Weaver
コードクローンを対象とした リファクタリングの有効性に関する調査
Presentation transcript:

プログラム実行履歴を用いたコードクローン検出手法 ○ 井岡 正和(阪大) ,吉田 則裕(奈良先端大) ,   井上 克郎(阪大)

剽窃 他人の作品や論文を盗んで,自分のものとして発表すること. プログラムが剽窃される事例もある. Aさんのプログラム Xさんのプログラム Yさんのプログラム Aさん Bさん

剽窃の検出 (コードクローンベース) コードクローンとは,ソースコード中に存在する一致または類似したコード片 ソースコード中のコードクローンを検出することで,剽窃をチェック可能 コードクローン 剽窃 Aさんのプログラム Bさんのプログラム

コードクローン検出手法 String-based Token-based Tree-based Semantics-based コードクローン検出に関する研究が数多く行われている. String-based 文字列が連続して一致する部分を検出 Token-based トークン列が連続して一致する部分を検出 CCFinder [1] Tree-based 構文木から類似した部分木を検出 Semantics-based プログラム依存グラフから同形部分グラフを検出 多様な検出 高速 [1] T. Kamiya, et al.: CCFinder: A Multilinguistic Token-based Code Clone Detection System for Large Scale Source Code, IEEE Trans. Softw. Eng., 2002.

CCFinderの処理概要 1. static void foo() throws RESyntaxException { ソースコード 字句解析 変換処理 トークン列 検出処理 変換後トークン列 クローン情報 出力整形処理 クローンペア位置情報 1. static void foo() throws RESyntaxException { 2. String a[] = new String [] { "123,400", "abc", "orange 100" }; 3. org.apache.regexp.RE pat = new org.apache.regexp.RE("[0-9,]+"); 4. int sum = 0; 5. for (int i = 0; i < a.length; ++i) 6. if (pat.match(a[i])) 7. sum += Sample.parseNumber(pat.getParen(0)); 8. System.out.println("sum = " + sum); 9. } 10. static void goo(String [] a) throws RESyntaxException { 11. RE exp = new RE("[0-9,]+"); 12. int sum = 0; 13. for (int i = 0; i < a.length; ++i) 14. if (exp.match(a[i])) 15. sum += parseNumber(exp.getParen(0)); 16. System.out.println("sum = " + sum); 17. } 字句解析 変換処理 トークン列 検出処理 変換後トークン列 クローン情報 出力整形処理 字句解析 変換処理 トークン列 検出処理 変換後トークン列 クローン情報 出力整形処理 字句解析 変換処理 トークン列 検出処理 変換後トークン列 クローン情報 出力整形処理 1. static void foo() throws RESyntaxException { 2. String a[] = new String [] { "123,400", "abc", "orange 100" }; 3. org.apache.regexp.RE pat = new org.apache.regexp.RE("[0-9,]+"); 4. int sum = 0; 5. for (int i = 0; i < a.length; ++i) 6. if (pat.match(a[i])) 7. sum += Sample.parseNumber(pat.getParen(0)); 8. System.out.println("sum = " + sum); 9. } 10. static void goo(String [] a) throws RESyntaxException { 11. RE exp = new RE("[0-9,]+"); 12. int sum = 0; 13. for (int i = 0; i < a.length; ++i) 14. if (exp.match(a[i])) 15. sum += parseNumber(exp.getParen(0)); 16. System.out.println("sum = " + sum); 17. }

プログラムの難読化 プログラムを変更し,理解しにくくすること. 多くの難読化ツールがある. 文字列改変 構造改変 名前変換 構造改変 メソッド分散 多くの難読化ツールがある. 例: ProGuard,DashO,Allatori

難読化例 – 名前変換 クラス名やメソッド名等を意味のないものに変換(a,b等) Sample → A print → a etc. class Sample { private void print(String msg) { // 処理 } public void something() { print(“Hello”); class Ex { class A { private void a(String a) { // 処理 } public void b() { a(“Hello”); class B { Sample → A print → a etc.

難読化例 – メソッド分散 あるメソッドを別のクラスへ移動 SampleのprintメソッドがExに移動 class Sample { private void print(String msg) { // 処理 } public void something() { print(“Hello”); class Ex { class Sample { public void something() { Ex.print(this, “Hello”); } class Ex { public static void print(Sample a, String msg) { // 処理 SampleのprintメソッドがExに移動

既存コードクローン検出手法の問題点 難読化後のプログラムと難読化前のプログラムをクローンとして検出できない可能性がある. あるクローンの一部が改変されると,クローンとして検出できない可能性がある. 動作は同じ メソッド抽出 呼び出し クローン クローン CF1 CF2 CF1 CF2

研究目的 動作が似ているプログラムをコードクローンとして検出する. クローン クローン CF1 CF2 動作は同じ 呼び出し 難読化前 難読化後 プログラム 動作が同じものをコードクローンとして扱いたい

提案手法 プログラム実行履歴を用いてコードクローンを検出する. プログラム実行履歴中のメソッド呼び出し列を比較し,似ている箇所をクローンとして検出 ログイン マイリスト表示 書籍追加 実行履歴1 ログイン 書籍一覧 書籍詳細 実行履歴2 フォーム表示(); ログイン処理(); ユーザ設定取得(); トップページ表示();

メソッドA(型X);メソッドB();・・・ コードクローン検出の流れ 入力: プログラム実行履歴 手順3. フェイズ比較 出力: 実行履歴     クローンセット P1 P2 P1 P2 手順1. フェイズ分割 フェイズ1 フェイズ2 フェイズn ・・・ フェイズm メソッドA(型X);メソッドB();・・・ 手順2. 正規化 P1 P2 フェイズ1 フェイズ2 フェイズn ・・・ フェイズm 0(1);0;・・・

手順1. フェイズ分割 (1/2) 実行履歴は,プログラム実行時のすべてのメソッド呼び出しを含んでいるため非常に長い. 計算コストが大きい. → 実行履歴を意味のある処理(フェイズ)に分割 渡邊らのフェイズ分割手法 [2] を用いる. [2] 渡邊ら: 協調動作するオブジェクト群の変化に基づく実行履歴の自動分割,   情報処理学会論文誌, 2010.

手順1. フェイズ分割 (2/2) スタックトレースの深さから,機能の区切り目を見つけフェイズに分割する. スタックトレースの深さ ログイン 書籍一覧 書籍詳細 スタックトレースの深さ スタックトレース: 特定のメソッドが呼ばれるまでに経てきたメソッドの一覧 メソッド呼び出しのタイムスタンプ

手順2. 正規化 手順2-1. メソッド呼び出し列の正規化 手順2-2. メソッド呼び出し文の正規化 繰り返しの回数に意味を持たないことが多い. → 2回以上の呼び出しの繰り返し → 2回の呼び出し 手順2-2. メソッド呼び出し文の正規化 難読化等によってメソッドのシグネチャが意味を持たないことが多い. → メソッド名等の代わりに呼び出し内の出現位置情 報を使ってインデックスを振る.

手順2-2. メソッド呼び出し文の正規化 直前のメソッド呼び出しと現在のメソッド呼び出しを用いて正規化を行う. メソッド呼び出しの改変の影響を少し受ける. 列: メソッドA(型X,型Y); メソッドB(型Z,型Z); メソッドC(型W,型Z);   → 0(1,2); 3(4,4); 2(3,1); メソッドA(型X,型Y); フェイズ内のメソッド呼び出しの増減にあまり影響がでないように正規化 案1: false positiveが多くなる可能性がある 案2: 難読化によるメソッド挿入が行われると,挿入前後をクローンとして検出できない可能性がある 1 2

手順2-2. メソッド呼び出し文の正規化 直前のメソッド呼び出しと現在のメソッド呼び出しを用いて正規化を行う. メソッド呼び出しの改変の影響を少し受ける. 列: メソッドA(型X,型Y); メソッドB(型Z,型Z); メソッドC(型W,型Z);   → 0(1,2); 3(4,4); 2(3,1); メソッドA(型X,型Y); メソッドB(型Z,型Z); フェイズ内のメソッド呼び出しの増減にあまり影響がでないように正規化 案1: false positiveが多くなる可能性がある 案2: 難読化によるメソッド挿入が行われると,挿入前後をクローンとして検出できない可能性がある 1 2 3 4 4

手順2-2. メソッド呼び出し文の正規化 直前のメソッド呼び出しと現在のメソッド呼び出しを用いて正規化を行う. メソッド呼び出しの改変の影響を少し受ける. 列: メソッドA(型X,型Y); メソッドB(型Z,型Z); メソッドC(型W,型Z);   → 0(1,2); 3(4,4); 2(3,1); メソッドB(型Z,型Z); メソッドC(型W,型Z); フェイズ内のメソッド呼び出しの増減にあまり影響がでないように正規化 案1: false positiveが多くなる可能性がある 案2: 難読化によるメソッド挿入が行われると,挿入前後をクローンとして検出できない可能性がある 1 1 2 3 1

手順3. フェイズ比較 動的計画法を用いた類似文字列マッチングアルゴリズム [3] を使用 → 全フェイズの比較後,類似度が高いものから 1メソッド呼び出しを1文字に対応付けて適用 類似文字列マッチング アルゴリズム フェイズ間の類似度 + メソッド呼出の対応関係 フェイズX フェイズY → 全フェイズの比較後,類似度が高いものから   フェイズを対応付けてクローンとして出力 [3] R. B. Yates, et al.: Modern Information Retrieval. Addison Wesley, 1999.

ケーススタディ – 準備 (1/2) 目的 難読化前後で同一のコンポーネントを識別できるか. 再利用事例を確認できるか. ① ② A B A 比較 ① ② A A’ 比較 A B’ 比較 B B’ 比較 A’ B 比較

ケーススタディ – 準備 (2/2) 対象 難読化ツール ICCA [4]: 統合コードクローン分析環境 Geminiコンポーネント Javaファイル数: 120 実行系列長: 21560(難読化前)、21294(難読化後) ファイルに保存したクローン情報からクローン解析を行う. Virgoコンポーネント Javaファイル数: 26 実行系列長: 15686(難読化前)、15676(難読化後) クローンセット情報からクローン解析を行う. 難読化ツール ProGuard [5] を標準設定で使用 我々の開発グループで開発した [4] ICCA: http://sel.ist.osaka-u.ac.jp/icca/ [5] ProGuard: http://proguard.sourceforge.net/

ケーススタディ① – 概要 GeminiコンポーネントとVirgoコンポーネントの難読化前後の類似度を計測 ソフトウェアαのクラスA,ソフトウェアβのクラスBの類似度 メソッドA,メソッドBの類似度 上の式のクラスA,BをメソッドA,Bに置き換えた式

ケーススタディ① – 結果 (1/2) クラス・メソッド間の類似度の累積グラフ クラス・メソッド間の類似度が高いものが多い. 類似度0.9以下のものが約30%のみ

ケーススタディ① – 結果 (2/2) Virgoコンポーネントについて,クラス・メソッド間の対応付けがすべて正しいことを確認 → 難読化前後で同一コンポーネントを識別できた. クラス・メソッド間の類似度があまり高くないものは,難読化によるインライン化等の影響

ケーススタディ② – 概要 3つのケースでフェイズ間の類似度を調査 ケース1: GeminiコンポーネントとVirgoコンポーネント

ケーススタディ② – 結果 (1/2) 各ケースにおける,類似フェイズの検出結果 ケース1: GeminiコンポーネントとVirgoコンポーネント ケース2: GeminiコンポーネントとVirgoコンポーネントを難 読化したもの ケース3: Geminiコンポーネントを難読化したものとVirgoコ ンポーネント 検出数 最大類似度 最小類似度 平均類似度 ケース1 75 1.00 0.227 0.612 ケース2 0.192 ケース3 61 0.048 0.632

ケーススタディ② – 結果 (2/2) 共通ライブラリ内のメソッドのみで構成されるフェイズを除外して,類似フェイズを調査 類似度1位 Geminiコンポーネント Virgoコンポーネント(難読化) ファイルから クローン情報を 取得して解析 クローンセットから クローン情報を 取得して解析 Virgoコンポーネントは,Geminiコンポーネントより後に開発 → 再利用

関連研究 岡本らが提案した動的バースマーク [6] 本研究では, プログラムのAPI呼び出しの系列や頻度を比較 アプリケーション単位の剽窃を検出 アプリケーション単位の検出が主流 本研究では, メソッド単位の剽窃を検出可能 類似実行系列を特定可能 代表的なものとして, [6] 岡本ら: API 呼び出しを用いた動的バースマーク. 電子情報通信学会論文誌, 2006.

まとめと今後の課題 プログラム実行履歴を用いたコードクローン検出手法の提案 今後の課題 手順1. フェイズ分割 手順2. 正規化 手順3. フェイズ比較 今後の課題 追加実験 類似アプリケーション 剽窃の事例