(19)【発行国】日本国特許庁(JP)
(12)【公報種別】特許公報(B2)
(11)【特許番号】
(24)【登録日】2022-10-06
(45)【発行日】2022-10-17
(54)【発明の名称】ソフトウェアコードをセキュアにするための方法
(51)【国際特許分類】
G06F 21/54 20130101AFI20221007BHJP
G06F 21/64 20130101ALI20221007BHJP
G06F 8/51 20180101ALI20221007BHJP
【FI】
G06F21/54
G06F21/64
G06F8/51
(21)【出願番号】P 2021175286
(22)【出願日】2021-10-27
(62)【分割の表示】P 2019541352の分割
【原出願日】2018-01-25
【審査請求日】2021-11-24
(32)【優先日】2017-01-26
(33)【優先権主張国・地域又は機関】EP
(73)【特許権者】
【識別番号】519271263
【氏名又は名称】タレス・ディス・フランス・エス・ア
(73)【特許権者】
【識別番号】519271274
【氏名又は名称】エス・エフ・エヌ・テー・ジャーマニー・ゲー・エム・ベー・ハー
(74)【代理人】
【識別番号】110001173
【氏名又は名称】弁理士法人川口國際特許事務所
(72)【発明者】
【氏名】エリク・ガロー
(72)【発明者】
【氏名】セバスチャン・ボルペ
(72)【発明者】
【氏名】ペーター・ガルバ
【審査官】吉田 歩
(56)【参考文献】
【文献】特開2011-170836(JP,A)
(58)【調査した分野】(Int.Cl.,DB名)
G06F 21/54
G06F 21/64
G06F 8/51
(57)【特許請求の範囲】
【請求項1】
複数の基本ブロックに編成されたコンピュータコード命令を備えたコンパイル済みのソフトウェアコード(SC)をセキュアにし、セキュアなソフトウェアコード(SSC)を生成する方法であって、
保護されるべきソフトウェアコードの部分を、プロセッサ(21)によって決定するステップ(S1)と、
命令の第1のシーケンスを、ソフトウェアコードの選択された基本ブロックに、プロセッサによって挿入するステップ(S2)であって、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、
保護されるべきソフトウェアコードの前記部分における完全性チェック値を計算し(E1)、
前記計算された完全性チェック値に基づいてインデクス値を計算する(E2)、ステップと、
メモリアドレスのインデクス付けされた配列を、ソフトウェアコードの選択された基本ブロックに、プロセッサによって挿入するステップ(S3)であって、セキュアなソフトウェアコードを実行したとき、選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスが、前記インデクス値によってインデクス付けされる、ステップと、
ランタイムにおいて計算された前記インデクス値によって、配列中でインデクス付けされたアドレスへのジャンプ命令を、ソフトウェアコードの選択された基本ブロックの最後に、プロセッサによって挿入するステップ(S4)と
を備え、
前記完全性チェック値が、開始アドレスと停止アドレスとの間のセキュアなソフトウェアコードの命令において計算され、前記方法はさらに、
セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第5のセキュアにするステップ(S5)であって、
完全性チェック値が計算されるべきソフトウェアコードの部分の開始および終了のソフトウェアコードにおける開始アドレスおよび終了アドレスを決定することと、
前記完全性チェック値、および、前記計算された完全性チェック値に基づいて前記インデクス値を計算することとを備えた、ステップと、
セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第6のセキュアにするステップ(S6)であって、
前記開始アドレスおよび停止アドレスを、第5のセキュアにするステップにおいて決定された前記開始アドレスおよび終了アドレスに設定することと、
第5のセキュアにするステップにおいて計算された前記インデクス値で、後続する基本ブロックのアドレスを、配列中に設定することとを備えた、ステップと
を備えた、方法。
【請求項2】
保護されるべきソフトウェアコードの部分が、ランダムに決定される、請求項1に記載の方法。
【請求項3】
完全性チェック値が、保護されるべきソフトウェアコードの前記部分、および選択された基本ブロックの少なくとも部分において計算される、請求項1に記載の方法。
【請求項4】
命令の第1のシーケンスが、ランタイムにおいて実行されたとき、チェックサム、マスク、ハッシュ関数、バイナリシフト、および算術演算のうちの1つ以上の演算を実施することによって、前記完全性チェック値を計算する命令の第2のシーケンスを備えた、請求項1に記載の方法。
【請求項5】
前記命令の第2のシーケンスが、完全性チェック関数を計算する命令の所定のシーケンスのセットにおいてランダムに選択される、請求項4に記載の方法。
【請求項6】
命令の第1のシーケンスが、ランタイムにおいて実行されたとき、前記インデクス値を計算するために、変換関数を、前記計算された完全性チェック値に適用する命令の第3のシーケンスを備え、前記変換関数は、チェックサム、マスク、ハッシュ関数、バイナリシフト、および算術演算のうちの1つ以上の演算を備えた、請求項1に記載の方法。
【請求項7】
変換関数が、所定の変換関数のセットにおいてランダムに選択される、請求項6に記載の方法。
【請求項8】
配列におけるアドレスが、セキュアなソフトウェアコードが実行されたときにおけるセキュアなソフトウェアコードの基本ブロックのアドレスである、請求項1に記載の方法。
【請求項9】
配列および命令の第1のシーケンスが、ソフトウェアコードの選択された基本ブロック内のランダムな位置に挿入される、請求項1に記載の方法。
【請求項10】
命令の第1のシーケンスが、挿入されたジャンプ命令の前で、選択された基本ブロックの最後に挿入される、請求項1に記載の方法。
【発明の詳細な説明】
【技術分野】
【0001】
本発明は、ソフトウェア保護の分野に関し、より詳細には、改ざん防止技術の分野に関する。本発明は、完全性チェックに基づく、コンパイル済みのコードの静的解析に耐性がある改ざん防止方法を開示する。
【背景技術】
【0002】
現在、ソフトウェアアプリケーションを作動させることにより、多くのサービスがユーザに提供される。このようなアプリケーションは、デスクトップコンピュータ、ラップトップ、店頭(point of sale)端末、スマートフォンなど、モバイルまたはモバイル以外の様々なデバイスで作動する。このようなアプリケーションは、ローカルで作動することも、LANやインターネットなどのネットワークを介して実装されることもできる。スマートカードや銀行のクレジットカードなどのいくつかのデバイスは、1つまたはいくつかのアプリケーションの作動専用になっている場合もある。このようなアプリケーションは通常、セキュアにされていない環境で作動させられ、そこでは、攻撃者は、アプリケーションを作動させているシステムの動作のいくつかを制御するか、または完全に制御することさえできる。この結果、これらのアプリケーションのほとんどは、アプリケーションによって取り扱われるデータが、このような攻撃者によって読み取られる、または変更されることを防ぐために、いくつかのセキュリティメカニズムを実装する必要がある。
【0003】
攻撃者は、システムによって実行される、コンパイル済みのコードをリバースエンジニアリングすることによって、ソフトウェアの動作を理解しようとする場合がある。攻撃者は、その後、悪意のある動作を実施するために、ソフトウェアによって取り扱われるセキュアな情報にアクセスしたり、および/または、ソフトウェアを変更する可能性がある。たとえば、攻撃者は、悪意のある金融取引を実施するために、銀行業務ソフトウェアを変更したり、ライセンスを購入せずに無料で、ライセンスで保護されたソフトウェアを作動させるために、それを変更したりできる。このようなリバースエンジニアリングは通常、コードアナライザやデバッガなどのツールを使用して実施され、これらのツールは、コード内の命令の実行の順序を示す制御フローグラフなど、コードの動作に関する情報をコンパイル済みのコードから抽出する。
【0004】
ソフトウェアコードのあらゆる変更を阻止するために、改ざん防止技術が開発された。改ざん防止技術は、たとえば、ソフトウェアコードの特定の領域でチェックサム値を計算し、次いで、取得した値を知られている参照値と比較することによって、コードのある部分において完全性チェックを実施することにしばしば依存する。値が一致しない場合、コードは改ざんされており、ソフトウェアの通常の実行を拒否するか、ふりをするかのいずれかにより、ソフトウェアの実行を阻止する必要がある。それにも関わらず、このような保護も、攻撃者によってリバースエンジニアリングされ、破壊される可能性がある。デバッガまたはコードアナライザにとって、変数の定数値への初期化と、改ざん防止プロセスによって実施される比較におけるこのような定数値の使用とを突き止めることは特に簡単である。この種の情報は、コードにおいて実装されている保護の種類を識別するために攻撃者によって使用される可能性があり、それで、これにより保護を破ることができる。たとえば、攻撃者は、完全性チェックが実施されるソフトウェアの領域の開始と終了を識別し、コードが変更されていないときに完全性チェックルーチンによってこの領域で計算されるチェックサム値を推定し、次いで、チェックサム値が計算されるソフトウェアの領域内であっても、ソフトウェアコードの他の変更に関係なく、常に有効なチェックサム値を提供するために、完全性チェックルーチンにパッチを当てることができる。
【発明の概要】
【発明が解決しようとする課題】
【0005】
その結果、ソフトウェアコードのある部分で完全性チェックを実施し、保護されたコードの静的解析によって、このような方法がどのように機能するかを攻撃者が理解することを困難にし、このような攻撃者が、保護されたソフトウェアコードを成功裏に変更することを阻止する方法に対するニーズがある。
【課題を解決するための手段】
【0006】
したがって、この目的のために、第1の態様によれば、本発明は、複数の基本ブロックに編成されたコンピュータコード命令を備えたコンパイル済みのソフトウェアコードをセキュアにする方法に関し、前記方法は、セキュアなソフトウェアコードを生成し:
・保護されるべきソフトウェアコードの部分を、プロセッサによって決定するステップと、
・命令の第1のシーケンスを、ソフトウェアコードの選択された基本ブロックに、プロセッサによって挿入するステップであって、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、保護されるべきソフトウェアコードの前記部分における完全性チェック値を計算し、前記計算された完全性チェック値に基づいてインデクス値を計算する、ステップと、
・メモリアドレスのインデクス付けされた配列を、ソフトウェアコードの選択された基本ブロックに、プロセッサによって挿入するステップであって、セキュアなソフトウェアコードを実行したとき、選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスが、前記インデクス値によってインデクス付けされる、ステップと、
・ランタイムにおいて計算された前記インデクス値によって、配列中でインデクス付けされたアドレスへのジャンプ命令を、ソフトウェアコードの選択された基本ブロックの最後に、プロセッサによって挿入するステップと
を備えている。
【0007】
保護されるべきソフトウェアコードの部分が改ざんされている場合、セキュアなソフトウェアコードの実行を中断させることにより、攻撃者による改ざんからソフトウェアコードを保護し、インデクス付けされた配列の他の候補ターゲットアドレスの中に、ジャンプ命令のターゲットを隠すことを可能にする。
【0008】
実施形態では、保護されるべきソフトウェアコードの部分は、ランダムに決定される。保護されるべきコードのすべての部分を1つずつマニュアルで選択する必要なく、この方法を複数回適用することにより、コードの大部分を保護することができる。
【0009】
実施形態では、完全性チェック値は、保護されるべきソフトウェアコードの前記部分、および選択された基本ブロックの少なくとも部分において計算される。これは、攻撃者が、完全性チェックが計算される選択された基本ブロックの部分に実行ブレークポイントを挿入することを阻止する。このような停止ポイントが、完全性チェックによって出力される値、または実行されるべき後続する基本ブロックのインデクスの値についての知識を獲得することを可能にする。
【0010】
実施形態では、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、チェックサム、マスク、ハッシュ関数、バイナリシフト、および算術演算のうちの1つ以上の演算を実施することによって、前記完全性チェック値を計算する命令の第2のシーケンスを備えている。
【0011】
実施形態において、前記命令の第2のシーケンスは、完全性チェック関数を計算する命令の所定のシーケンスのセットにおいてランダムに選択される。
【0012】
これは、ランタイムにおいて完全性チェック値がどのように計算されるかを攻撃者が理解することを困難にする。これは、攻撃者が、コードのさらなる解析なしで、後続する正しい基本ブロックの配列におけるインデクスが計算される完全性チェック値を計算するために、使用すべき完全性関数を予測することを不可能にする。
【0013】
実施形態では、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、前記インデクス値を計算するために、変換関数を、前記計算された完全性チェック値に適用する命令の第3のシーケンスを備え、前記変換関数は、チェックサム、マスク、ハッシュ関数、バイナリシフト、および算術演算のうちの1つ以上の演算を備えている。
【0014】
変換関数は、所定の変換関数のセットにおいてランダムに選択され得る。
【0015】
これは、ランタイムにおいて、後続する正しい基本ブロックのインデクスがどのようにして検索されるのかを攻撃者が理解することをより困難にする。これは、前記完全性チェック値から、後続する正しい基本ブロックの配列におけるインデクスを計算するために使用すべき変換関数を、コードのさらなる解析なしで、攻撃者が予測することを不可能にする。
【0016】
配列におけるアドレスは、セキュアなソフトウェアコードが実行されたときにおけるセキュアなソフトウェアコードの基本ブロックのアドレスである場合がある。
【0017】
これは、配列において、セキュアなソフトウェアコードの基本ブロックをやはり指している他のすべてのアドレスから、後続する基本ブロックのアドレスを、攻撃者が区別することをよりさらに困難にする。
【0018】
前記完全性チェック値は、開始アドレスと停止アドレスとの間のセキュアなソフトウェアコードの命令において計算されてもよく、第1の態様による方法は:
- セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第5のセキュアにするステップであって、
・完全性チェック値が計算されるべきソフトウェアコードの部分の開始および終了のソフトウェアコードにおける開始アドレスおよび終了アドレスを決定することと、
・前記完全性チェック値、および、前記計算された完全性チェック値に基づいて前記インデクス値を計算することとを備えた、ステップと、
- セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第6のセキュアにするステップであって、
・前記開始アドレスおよび停止アドレスを、第5のセキュアにするステップにおいて決定された前記開始アドレスおよび終了アドレスに設定することと、
・第5のセキュアにするステップにおいて計算された前記インデクス値で、後続する基本ブロックのアドレスを、配列中に設定することとを備えた、ステップと
を備え得る。
【0019】
実施形態では、配列および命令の第1のシーケンスは、ソフトウェアコードの選択された基本ブロック内のランダムな位置に挿入される。これは、潜在的な攻撃者にとって、セキュアなソフトウェアコードをさらにわかりにくくする。
【0020】
命令の第1のシーケンスは、挿入されたジャンプ命令の前で、選択された基本ブロックの最後に挿入され得る。完全性チェック値および後続する基本ブロックのインデクス値は、それで、ジャンプに対する後続する基本ブロックのアドレスを検索するために、それらが必要とされる直前に計算されるので、したがって、攻撃者がコードの動的解析によって検索するタイムウィンドウを制限する。
【0021】
第2の態様によれば、本発明は、プロセッサによる実行のためのセキュアなソフトウェアコードの命令でエンコードされた非一時的機械可読記憶媒体に関し:
・前記セキュアなソフトウェアコードは、複数の基本ブロックに編成されたコンピュータコード命令を備えたソフトウェアコードの変更バージョンであり、
・セキュアなソフトウェアコードの選択された基本ブロックは、セキュアなソフトウェアコードを実行したとき、選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスを備えた、メモリアドレスのインデクス付けされた配列を備え、前記非一時的機械可読記憶媒体は、セキュアなソフトウェアコードの選択された基本ブロックに挿入された、命令の第1のシーケンスを用いてエンコードもされ、命令の第1のシーケンスは、ランタイムにおいて実行されたとき:
・保護されるべきソフトウェアコードの部分における完全性チェック値を計算し、
・前記計算された完全性チェック値に基づいて、後続する基本ブロックのアドレスを配列中でインデクス付けするインデクス値を計算し、セキュアなソフトウェアコードの選択された基本ブロックは、その最後に、ランタイムにおいて計算された前記インデクス値によってインデクス付けされた配列のアドレスへのジャンプ命令も備えている。
【0022】
実施形態では、完全性チェック値は、保護されるべきソフトウェアコードの部分と、選択された基本ブロックの少なくとも部分とにおいて計算される。
【0023】
第3の態様によれば、本発明は、セキュアなソフトウェアコードの選択された基本ブロックの命令をプロセッサによって実行する方法に関し:
・前記セキュアなソフトウェアコードは、複数の基本ブロックに編成されたコンピュータコード命令を備えたソフトウェアコードの変更されたバージョンであり、
・セキュアなソフトウェアコードの選択された基本ブロックは、セキュアなソフトウェアコードを実行したとき、選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスを備えた、メモリアドレスのインデクス付けされた配列を備え、前記方法は:
・保護されるべきソフトウェアコードの部分における完全性チェック値を計算するステップと、
・前記計算された完全性チェック値に基づいて、後続する基本ブロックのアドレスを配列中でインデクス付けするインデクス値を計算するステップと、
・前記計算されたインデクス値によって配列中でインデクス付けされたアドレスへのジャンプ命令を、選択された基本ブロックの最後に実行するステップと
を備えている。
【0024】
完全性チェック値は、保護されるべきソフトウェアコードの部分と、選択された基本ブロックの少なくとも部分とにおいて計算され得る。
【0025】
第2の態様によるこのような非一時的機械可読記憶媒体、および第3の態様による方法は、第1の態様による方法のものと同じ利点を示す。
【0026】
前述の目的および関連する目的を達成するために、1つ以上の実施形態は、以下で十分に説明され、特に特許請求の範囲で指摘される特徴を備えている。
【0027】
以下の説明および添付の図面は、特定の例示的な態様を詳細に説明し、実施形態の原理が採用され得る様々な方法のほんのわずかを示している。他の利点および新規の特徴は、図面と併せて考慮されるとき、後続する詳細な説明から明らかになり、開示される実施形態は、このようなすべての態様およびそれらの均等物を含むことが意図される。
【図面の簡単な説明】
【0028】
【
図1】ソフトウェアをコンパイルするプロセスを示す図である。
【
図2】本発明の実施形態によるセキュアにするデバイスを概略的に示す図である。
【
図3】本発明の実施形態による実行デバイスを概略的に示す図である。
【
図4】本発明の実施形態によるコンパイル済みのソフトウェアコードをセキュアにする方法を概略的に示す図である。
【
図5】本発明の実施形態によるインデクス付けされた配列を示す図である。
【
図6】本発明の実施形態によるセキュアなソフトウェアコードの選択された基本ブロックの命令を実行する方法を概略的に示す図である。
【発明を実施するための形態】
【0029】
以下に詳述する説明では、本発明が実践され得る特定の実施形態を例示として示す添付図面に対する参照がなされる。これらの実施形態は、当業者が本発明を実践できるように十分詳細に説明されている。本発明の様々な実施形態は、異なるが、必ずしも相互に排他的ではないことを理解されたい。たとえば、1つの実施形態に関連して本明細書で説明される特定の特徴、構造、または特性は、本発明の精神および範囲から逸脱することなく、他の実施形態内で実装され得る。それに加えて、開示された各実施形態内の個々の要素の位置または配置は、本発明の精神および範囲から逸脱することなく変更され得ることを理解されたい。したがって、以下に詳述する説明は限定的な意味で解釈されるべきではなく、本発明の範囲は添付の特許請求の範囲によってのみ定義され、請求項が権利を与えられる均等物の全範囲とともに、適切に解釈される。
【0030】
本発明は、コンパイル済みのソフトウェアコードSCに、保護されるべきソフトウェアコードの部分に対する少なくとも1つの完全性チェックを含めることにより、および、コードの後続する命令へのジャンプ命令を、ジャンプ命令ターゲットが完全性チェックの結果に依存するような様式で、コードに挿入することにより、このソフトウェアコードをセキュアにすることを目的とする。これは、コンパイル済みのセキュアなソフトウェアコードSSCを作り出し、これによって、攻撃者が、コードの実行を中断させることなく、コードアナライザまたはデバッガを用いて、コンパイル済みのセキュアなソフトウェアコードを解析して、完全性チェックおよびジャンプ命令ターゲットに関する十分な知識を得て、保護されるべきソフトウェアコードの部分を変更することを困難にする。
【0031】
コンパイルは、CやFortranなどの高級プログラミング言語で記述されたソースコード11を、
図1に示すように、コードが実行されることになっているシステムのハードウェア実装を考慮に入れたマシンコード15などの低級言語で記述されたオブジェクトコードに変換する。コンパイルは、シンタックス解析12、制御フローグラフ生成13、およびアセンブリコード生成14などの中間ステップを実施することがよくある。コンパイル済みのコードの実行可能ファイルをビルドするために、通常、コンパイルは、オブジェクトコードを含む多数のファイルを単一の実行可能ファイルにともにリンクするリンクステップによって後続される。
【0032】
コンパイル済みのコードは、命令の基本ブロックに集められた命令を備えている。このような基本ブロックは、最小限の命令シーケンスと見なすことができる。基本ブロックは、開始に1つのエントリポイントを、終了に1つのエグジットポイントを有する。基本ブロックの第1の命令が実行されるたびに、基本ブロック内の命令の出現順に、残りの命令が必ず1回実行される。基本ブロックは、ランタイムにおいて実行される次の基本ブロックのエントリポイントへのジャンプ命令を最後に備え得る。
【0033】
本発明の第1の態様は、実行前にコンパイル済みのソフトウェアコードSCをセキュアにするための改ざん防止方法である。このようなセキュアにする方法は、複数の基本ブロックに編成されたコンピュータコード命令を備えたコンパイル済みのソフトウェアコードSCを処理し、セキュアなソフトウェアコードSSCを作り出すセキュアにするデバイス20によって実施される。その後、取得されたセキュアなソフトウェアコードSSCは、実行デバイス30によって、セキュアに実行され得る。
【0034】
このようなセキュアにするデバイス20は、プロセッサを含む任意の電子デバイスであり得る。たとえば、これは、開発環境がインストールされたパーソナルコンピュータPCであり得る。
図2は、第1のプロセッサ21、第1のRAMメモリ22、イーサネットまたはWifiネットワークアダプタのような第1の通信ユニット23、第1のディスプレイ24、ハードドライブのような第1の大容量記憶手段25、および第1のユーザ入力手段26を備えた、このようなセキュアにするデバイスの例示的な実施形態を説明する。セキュアにされるべきソフトウェアコードSCは、セキュアにするデバイスの第1の大容量記憶手段25に記憶され得る。セキュアにするデバイス20が、第1の態様による方法をソフトウェアコードSCに適用した後に得られるセキュアなソフトウェアコードSSCは、第1の大容量記憶装置25に記憶されることもできる。
【0035】
図3は、実行デバイス30の例示的な実施形態を説明する。たとえば、実行デバイス30は、パーソナルコンピュータPC、スマートフォンやタブレットのようなモバイルデバイス、または、銀行や店頭における公共端末であり得る。これは、スマートカードまたはクレジットカードに含まれる単純なチップでもよい。これは、第2のプロセッサ31、第2のRAMメモリ32、イーサネットまたはWifiネットワークアダプタのような第2の通信ユニット33、第2のディスプレイ34、ハードドライブのような第2の大容量記憶手段35、および第2のユーザ入力手段36を備え得る。実行デバイス30の第2のプロセッサ31によって実行されるべきセキュアなソフトウェアコードSSCは、実行デバイスの第2の大容量記憶手段35に記憶されてもよい。電子デバイス30は、実行デバイスのものと類似または異なる任意のタイプのものであり得る。両デバイスは、x86、ARM、PowerPCのような同じハードウェアアーキテクチャを共有することも、または異なるアーキテクチャを有することもある。
【0036】
セキュアにする方法の主なステップ
以下の段落では、
図4に示すように、ソフトウェアコードSCをセキュアにし、セキュアなソフトウェアコードSSCを作り出す、本発明の第1の態様による方法のステップを説明する。これらのセキュアにするステップは、セキュアにするデバイス20の第1のプロセッサ21によって実施され、ステップ番号が後続する文字「S」ですべてラベル付けされている。
【0037】
必要なとき、第1の態様による方法が完了した後、セキュアなソフトウェアコードSSCを実行したときに実行デバイス30によって実施されるステップが参照される。このような実行ステップには、ステップ番号が後続する文字「E」でラベル付けされている。
【0038】
セキュアにする方法の主なステップ:第1のセキュアにするステップ
第1のセキュアにするステップS1では、保護されるべきソフトウェアコードの部分が、ソフトウェアコードSCにおいて決定される。これは、攻撃者によるあらゆる変更を阻止するために、完全性チェックが実施されるコードの部分である。保護されるべきソフトウェアコードのこのような部分は、人間のオペレータによって第1のプロセッサ21に指定され得る。あるいは、これは、第1のプロセッサ21自体によってランダムに決定されるか、第1のプロセッサ21によって実行される第1の解析プログラムによって計算され得る。ソフトウェアコードのこのような部分は、命令の1つ以上の基本ブロックを備え得る。
【0039】
以下のステップにおいて、目的は、命令をソフトウェアコードに挿入することであり、それらの命令は、攻撃者による静的解析に抵抗できるように、実行されたとき、保護されるべきソフトウェアコードの決定された部分において完全性チェックを実施する。このような完全性チェックが、保護されるべきソフトウェアコードの部分においてチェックサム値を計算し、次いで、それを参照値と比較することのみである場合、攻撃者がこのような比較を見つけ、参照値についての知識を獲得して、保護されるべきソフトウェアコードの部分において攻撃者が何を変更しようと、常に比較の結果を成功させるために、この比較の結果を検証する命令のシーケンスを変更することは非常に簡単であろう。
【0040】
代わりに、完全性チェックによって計算された値に基づいて、ソフトウェアコードの既存の基本ブロックのリストの中から、別の基本ブロックをターゲットとし、そのターゲットがオンザフライで選択されるジャンプ命令を、ソフトウェアコードの基本ブロックの最後に挿入することが提案される。セキュアにするデバイス20によって実行されるセキュアにする方法は、実行デバイス30の第2のプロセッサ31によって実施されたとき、セキュアなソフトウェアコードの実行フローを、保護されるべきコードの部分が、攻撃者によって変更されていないにのみ、次の正しい基本ブロックにジャンプさせ;保護されるべきコードの部分が改ざんされている場合、別の不適切な基本ブロックにジャンプさせ、したがって、コードの実行の予測不能な振舞に導く命令を、ソフトウェアコードに挿入するように設計されている。このようなセキュアなソフトウェアコードは、取得されるべき値がセキュアなソフトウェアコードに格納されていないため、保護されるべきソフトウェアコードの部分において完全性チェックを実施したとき取得されるべき予想されるチェックサム値を、攻撃者が推測することを非常に困難にする。また、基本ブロックのリストのうち、セキュアなソフトウェアコードのどの基本ブロックが、ジャンプ命令で終わる現在のブロックの後に実行されるべき後続する正しいブロックであるかを、攻撃者が静的解析によって決定することも困難にする。したがって、攻撃者は、完全性チェックの結果とは無関係に、ジャンプのターゲットとして後続する正しい基本ブロックをマニュアルで強制することにより、改ざん防止保護をバイパスすることができない。
【0041】
セキュアにする方法の主なステップ:第2のセキュアにするステップ
より正確には、第2のセキュアにするステップS2において、セキュアにするデバイス20の第1のプロセッサ21は、ソフトウェアコードの選択された基本ブロックに、命令の第1のシーケンスを挿入し得る。この命令の第1のシーケンスは、セキュアなソフトウェアコードの選択された基本ブロックの命令を実行したとき、実行デバイス30が、選択された基本ブロックの直後に実行されるべき後続する適切な基本ブロックのアドレスを検索することを可能にすることを目的とする。
【0042】
この命令の第1のシーケンスは、この命令の第1のシーケンスを備えたセキュアなソフトウェアコードSSCが、実行デバイス30の第2のプロセッサ31によって実行されたとき、実行ステップE1、E2、およびE3で説明されるアクションが実施されるようになっており、これら実行ステップは、以下および
図6で説明される。
【0043】
このような選択された基本ブロックは、人間のオペレータによって第1のプロセッサ21に指定され得る。あるいは、セキュアなソフトウェアコードSSCを実行するときの計算時間を最小化するために、第1のプロセッサ21自体によりランダムに決定されるか、または第1のプロセッサ21により実行される第2の解析プログラムによって決定され得る。
【0044】
命令の第1のシーケンスは、SSCランタイムにおいて、実行デバイス30によって実行されたとき、
・保護されるべきソフトウェアコードの前記部分における完全性チェック値を計算し、
・前記計算された完全性チェック値に基づいてインデクス値を計算する。
【0045】
セキュアにする方法の主なステップ:第3のセキュアにするステップ
第3のセキュアにするステップS3では、セキュアにするデバイス20の第1のプロセッサ21は、ソフトウェアコードの選択された基本ブロックに、
図5に説明されたメモリアドレスのインデクス付けされた配列を挿入し得、ここでは、セキュアなソフトウェアコードを実行するとき、選択された基本ブロックの後に実行されるべき実際の後続する基本ブロックのアドレスが、命令の第1のシーケンスによって計算された前記インデクス値によってインデクス付けされる。
【0046】
命令の第1のシーケンスおよびインデクス付けされた配列は、命令の第1のシーケンスによって計算されたインデクス値が、保護されるべきソフトウェアコードの部分が改ざんされていない場合にのみ、後続する基本ブロックのアドレスをインデクス付けする配列のインデクス値と等しくなるような様式で設計される。
【0047】
配列の使用は非限定的な実施形態であり、テーブルやマトリクスのような、値のインデクス付けされたストレージ、つまり、インデクス値と、対応する格納された値との間のマッチング、を可能にする他の任意のデータ構造が、配列を使用する代わりに使用され得る。
【0048】
セキュアにする方法の主なステップ:第4のセキュアにするステップ
第4のセキュアにするステップS4では、セキュアにするデバイス20の第1のプロセッサ21は、ソフトウェアコードの選択された基本ブロックの最後に、ランタイムにおいて計算された前記インデクス値によってインデクス付けされた配列のアドレスへのジャンプ命令を挿入する。
【0049】
セキュアにする方法の例示的な実施形態
以下の段落では、セキュアにするデバイス20によって実施される本発明の第1の態様によるセキュアにする方法の例示的かつ非限定的な実施形態について説明する。
【0050】
上記で説明したように、第1のセキュアにするステップS1では、ソフトウェアコードSC内で保護されるべきソフトウェアコードの部分が決定される。
【0051】
次に、第2のセキュアにするステップS2において、命令の第1のシーケンスが、選択された基本ブロックに挿入される。上記で説明したように、この命令の第1のシーケンスは、ランタイムにおいて実行されたとき、完全性チェック値を計算する命令を含んでいる。命令の第1のシーケンスは、ランタイムにおいて実行されたとき、チェックサム、マスク、ハッシュ関数、バイナリシフト、および算術演算のうちの1つ以上の演算を実施することにより、前記完全性チェック値を計算する命令の第2のシーケンスを備え得る。この完全性チェック値は、セキュアなソフトウェアコードの開始アドレスと停止アドレスとの間のソフトウェアコードの命令において計算され得る。このような開始アドレスおよび停止アドレスは、第1のセキュアにするステップにおいて決定された、保護されるべきソフトウェアコードの少なくとも部分を含む、ソフトウェアコードの部分を定義するように設計される。
【0052】
完全性チェック値は、たとえば、MD5またはSHA-1を使用して計算されたチェックサムまたはダイジェストであり得る。
【0053】
実施形態において、前記命令の第2のシーケンスは、完全性チェック関数を計算する命令の所定のシーケンスのセットにおいて、ランダムに選択される。その結果、このような完全性チェックが実施される手法は多様化する。それは、難読化することもできるので、攻撃者がセキュアなソフトウェアコードにおいて簡単に識別し、開始アドレスと停止アドレスとの間で同じ完全性チェック値を自分で計算することを阻止する。
【0054】
代替実施形態では、完全性チェック値は、保護されるべきソフトウェアコードの前記部分と、選択された基本ブロックの少なくとも部分とにおいて計算される。完全性チェックは、命令の第1のシーケンス、および/またはインデクス付けされた配列、および/またはブロックの最後におけるジャンプ命令を備えた、選択された基本ブロックの部分において計算され得る。これは、ソフトウェアコードの保護を無効にするために、選択された基本ブロックのこのような部分を、攻撃者が変更することを阻止する。完全性チェック値は、ジャンプ命令の直前にある命令においても計算され得る。こうすることが、攻撃者が、完全性チェックによって出力される値について、次いで、選択された基本ブロックの後に実行される後続する基本ブロックのアドレスについて知識を獲得できる、実行ブレークポイントを、攻撃者がジャンプの前に挿入することを阻止する。
【0055】
命令の第1のシーケンスは、計算された完全性チェック値に基づいてインデクス値を計算する命令も含む。
【0056】
そのために、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、前記インデクス値を計算するために、前記計算された完全性チェック値に変換関数を適用する、命令の第3のシーケンスを備え得る。変換関数は、たとえば、完全性チェック値のチェックサムまたはハッシュ、またはインデクス値を出力するために完全性チェック値のほんの少数の所定のビットを選択するマスクであり得る。変換関数はまた、完全性チェック値のビットのバイナリシフト、または完全性チェック値に対する算術演算の実施も含み得る。
【0057】
変換関数は、所定の変換関数のセットにおいて、セキュアにするデバイスの第1のプロセッサによってランダムに選択され得る。
【0058】
その後、第3のセキュアにするステップS3の一部として、選択された基本ブロックに、インデクス付けされた配列が挿入される。
【0059】
配列のすべてのインデクス値が、変換関数のターゲットセットに含まれるように、配列のインデクス値が選択され得る。そうすることによって、配列のすべてのインデクス値は、変換関数の適用の結果となる。
【0060】
インデクス付けされた配列の目的は、選択された基本ブロックの後に実行されるべき実際の後続する基本ブロックのアドレスを、特定のインデクスに格納することであり、これにより、実行デバイスが、選択された基本ブロックの命令において第1のシーケンスを実行したとき、保護されるべきソフトウェアコードの部分が改ざんされていない場合、配列の後続する基本ブロックのアドレスのインデクスに等しいインデクス値を計算する(以下に説明されるステップE2)。
【0061】
ただし、第3のセキュアにするステップS3を実施するセキュアにするデバイスによって選択された基本ブロックに、インデクス付けされた配列が挿入されたとき、命令の第1のシーケンスの実行から生じる完全性チェック値、および前記完全性チェック値に基づいて計算されたインデクス値は、まだ知られていない。
【0062】
結果として、方法のこのステップにおいて、セキュアにするデバイスの第1のプロセッサは、選択された基本ブロックに、配列における所定のインデクス、たとえば配列の第1の位置に、後続する基本ブロックのアドレスを備えたインデクス付けされた配列を挿入し得る。
【0063】
その後、第4のセキュアにするステップS4において、セキュアにするデバイスの第1のプロセッサは、選択された基本ブロックの最後に、命令の第1のシーケンスの実行から生じるインデクス値によって配列中でインデクス付けされたアドレスへのジャンプ命令を挿入する。
【0064】
選択された基本ブロックの最後の命令が既にジャンプ命令であった場合、この既存のジャンプ命令は削除されてよく、第4のセキュアにするステップS4において選択された基本ブロックの最後に挿入されたジャンプ命令がそれに置き換わる。
【0065】
プロセスのこのステップにおいては、命令の第1のシーケンスを実行するときに取得されるインデクス値は知られておらず、ほぼ確実に、後続する基本ブロックのアドレスの配列におけるインデクスではない可能性がある。さらに確実には、別の基本ブロックのアドレスの配列におけるインデクスである。それで、プロセスのこのステップから生じるソフトウェアコードを実行すると、通常の実行制御フローで選択された基本ブロックの直後に実行されるはずのない基本ブロックへ実行フローをジャンプさせ、予測不能な実行の振舞に導く。
【0066】
この問題を解決するために、この方法は、セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第5のセキュアにするステップS5を備え得、この間、セキュアにするデバイス20の第1のプロセッサ21は、ソフトウェアコードが実行可能ファイルになるためにアセンブルされた後、その解析を実施し、最終的なセキュアなソフトウェアコードに非常に近い状態で、このソフトウェアコードを解析することを可能にする。第5のセキュアにするステップS5は:
・保護されるべきソフトウェアコードの少なくとも部分を含む、完全性チェック値が計算されるべきソフトウェアコードの部分の開始および終了の、ソフトウェアコードにおける実際の開始アドレスおよび終了アドレスを決定することと、
・選択された基本ブロックに挿入された命令の第1のシーケンスによって計算されるように、完全性チェック値を計算することと、
・選択された基本ブロックに挿入された命令の第1のシーケンスによって計算されるように、変換関数を完全性チェック値に適用することによってインデクス値を計算することとを備え得る。
【0067】
このようなステップにおいて、特にこの命令の第2のシーケンスが、命令の所定のシーケンスのセットにおいてランダムに選択されたとき、完全性チェック値は、命令の第2のシーケンスにしたがって計算されるものとする。同様に、インデクス値は、所定の変換関数のセットにおいて、変換関数がランダムに選択されたとき、選択された変換関数を適用することによって計算されるものとする。
【0068】
この方法は、セキュアなソフトウェアコードをコンパイルおよびリンクしたときに、またはその後に実施される、第6のセキュアにするステップS6も備え得、この間、セキュアにするデバイス20の第1のプロセッサ21は、セキュアなソフトウェアコードを配信するために、ソフトウェアコードに最終的な変更を実施する。
【0069】
第6のセキュアにするステップS6は:
・完全性チェック値が計算されるソフトウェアコードの部分を定義する開始アドレスおよび停止アドレスを、第5のセキュアにするステップS5において決定された開始アドレスおよび終了アドレスに設定すること。このようなアドレスは、第1の実行ステップE1の間に完全性チェック値を計算するために使用される。
・配列の、実際の後続する基本ブロックのアドレスを、第5のセキュアにするステップS5において計算されたインデクス値に設定すること。これは、実行ステップE2の間に計算されるのと同じインデクス値である、
を備え得る
【0070】
この配列は、セキュアなソフトウェアコードの基本ブロックの他の多くのアドレスを、それが実行されたときに、他のインデクスにおいて備え得る。このようなアドレスは、セキュアなソフトウェアコードの他の基本ブロックの中からランダムに選択された、後続する可能性のある基本ブロックのアドレスであり得る。このような場合、第6のセキュアにするステップS6の間、実際の後続する基本ブロックのアドレスを、第5のセキュアにするステップにおいて計算されたインデクス値に設定したとき、実際の後続する基本ブロックのアドレスが、配列において、第5のセキュアにするステップにおいて計算されたインデクス値によって配列で既にインデクス付けされている別の基本ブロックのアドレスとスワップされ得る。
【0071】
そうすることによって、攻撃者は、配列のアドレスが、後続する基本ブロックのアドレスになりえないことを決定することができない(これは、このようなアドレスが、基本ブロックのアドレスではない場合、または、配列における関連付けられたインデクスが、変換関数の可能な結果ではなかった場合に、可能であり得る)。攻撃者が、セキュアなソフトウェアコードに対して静的解析を実施した場合、彼は、選択された基本ブロックの最後において、単にジャンプ命令を突き止めることができるだけであり、セキュアなソフトウェアコードを正しく実行させ続けるために、配列に格納された複数のアドレスの中から、どのアドレスが、ジャンプのターゲットとして指定されるべきかを決定できないだろう。
【0072】
実施形態では、配列および命令の第1のシーケンスは、挿入されたジャンプ命令の前で、ソフトウェアコードの選択された基本ブロック内のランダムな位置に挿入され得る。あるいは、挿入されたジャンプ命令の前で、選択された基本ブロックの最後に挿入され得る。命令の第1のシーケンスは、選択された基本ブロックの既存の命令と干渉しないような様式で、この既存の命令とインターレースされ得る。
【0073】
セキュアにされたソフトウェアコード実行
上記のステップが、セキュアなソフトウェアコードを作り出すセキュアにするデバイスによって実施された後、このようなセキュアなソフトウェアコードは、実行デバイス30の第2のプロセッサ31によって、セキュアに実行され得る。選択された基本ブロックを実行したとき、実行デバイスは、命令の第1のシーケンス:
・第1の実行ステップE1の間、第2のプロセッサ31は、保護されるべきソフトウェアコードの少なくとも前記部分において完全性チェック値を計算する。
・第2の実行ステップE2の間、第2のプロセッサ21は、前記計算された完全性チェック値に基づいてインデクス値を計算する、
を実行する。
【0074】
保護されるべきソフトウェアコードの部分が改ざんされていない場合:
・計算された完全性チェック値は、計算されたインデクス値が、選択された基本ブロックの実行直後に実行されるべき後続する正しい基本ブロックのアドレスの配列におけるインデクスであるようになり、
・選択された基本ブロックの最後におけるジャンプ命令が、実行フローを、この後続する正しい基本ブロックの先頭にジャンプさせる。
【0075】
そうではなくて、保護されるべきソフトウェアコードの部分が改ざんされている場合:
・計算された完全性チェック値は、計算されたインデクス値が、選択された基本ブロックの実行直後に実行されるべき後続する正しい基本ブロックのアドレスとほぼ確実に異なるアドレスの配列におけるインデクスであるようになり、
・選択された基本ブロックの最後におけるジャンプ命令は、実行フローをこのアドレスへジャンプさせ、実行の予測不能な振舞に導く。
【0076】
第1の態様による方法の複数回適用
本発明の第1の態様による方法は、ソフトウェアコードの、場合によっては互いに重複するいくつかの部分を保護するために、複数回適用され得る。この場合、第1のセキュアにするステップS1の間、方法の各適用に対する保護されるべきコードの部分は、すべてのソフトウェアコードまたはソフトウェアコードのすべての機密部分が保護されるように、第1の解析プログラムによって決定され得る。変換関数が、所定の変換関数のセットの中からランダムに毎回選択される場合、保護されるべきソフトウェアコードの各部分に対して、異なる変換関数が選択され得る。
【0077】
他の態様
第2の態様では、本発明は、セキュアにするデバイス20の第1のプロセッサ21が、上述した第1の態様による方法の少なくともステップS1からS4を実施した後に取得されるセキュアにするソフトウェアコードの命令でエンコードされた非一時的機械可読記憶媒体にも関する。前記セキュアなソフトウェアコードは、それで、第1の態様による前記方法が適用される非セキュアなソフトウェアコードの変更されたバージョンであり、複数の基本ブロックに編成されたコンピュータコード命令を備えている。前記記憶媒体にエンコードされた命令では、セキュアなソフトウェアコードの選択された基本ブロックは、セキュアなソフトウェアコードを実行したとき選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスを備えた、メモリアドレスのインデクス付けされた配列を備えている。
【0078】
非一時的機械可読記憶媒体は、セキュアなソフトウェアコードの選択された基本ブロックに挿入された、命令の第1のシーケンスでもエンコードされ、命令の第1のシーケンスは、ランタイムにおいて実行されたとき、上記で説明された実行ステップE1からE2:
・保護されるべきソフトウェアコードの部分における完全性チェック値を計算することと、
・前記計算された完全性チェック値に基づいて、後続する基本ブロックのアドレスを配列中でインデクス付けするインデクス値を計算することを実施し、セキュアなソフトウェアコードの選択された基本ブロックは、ランタイムにおいて計算された前記インデクス値によって配列中でインデクス付けされたアドレスへのジャンプ命令も備えている。
【0079】
第3の態様では、本発明はまた、実行デバイス30の第2のプロセッサ31によって実行されるような、セキュアなソフトウェアコードの命令を実行する方法にも関する。前記セキュアなソフトウェアコードは、それで、上記の第1の態様による方法が適用された複数の基本ブロックに編成されたコンピュータコード命令を備えた非セキュアなソフトウェアコードの変更されたバージョンである。前記セキュアなソフトウェアコードの選択された基本ブロックは、セキュアなソフトウェアコードを実行したとき、選択された基本ブロックの後に実行されるべき後続する基本ブロックのアドレスを備えた、メモリアドレスのインデクス付けされた配列も備えている。セキュアなソフトウェアコードの命令を実行する方法は、上記で説明された実行ステップE1からE2:
・第1の実行ステップE1の間、第2のプロセッサ31は、保護されるべきソフトウェアコードの部分における完全性チェック値を計算し;
・第2の実行ステップE2の間、第2のプロセッサ31は、前記計算された完全性チェック値に基づいて、後続する基本ブロックのアドレスを配列中でインデクス付けするインデクス値を計算する;
を備えている。
【0080】
この方法は、第3の実行ステップE3を備え、この間、第2のプロセッサ31は、選択された基本ブロックの最後に、前記計算されたインデクス値によってインデクス付けされた配列のアドレスへのジャンプ命令を実行する。
【0081】
結果として、提案された方法は、保護されるべきソフトウェアコードの部分において完全性チェックを実施し、保護された部分が改ざんされているのであれば、セキュアなソフトウェアコードの実行をインタラプトするジャンプによって、この完全性チェックを保護することを可能にする。さらなる保護のために、提案された方法は、ジャンプ命令のターゲットである実行されるべき後続する基本ブロックをソフトウェアコードに隠すので、したがって、攻撃者が、保護されたコードの静的解析によって、このような方法がどのように機能するかを理解し、保護されたコードを変更することを阻止する。