web-dev-qa-db-ja.com

AES「キー」および「IV」値を安全に処理する方法

AES(System.Security.Cryptography)を使用してSQLサーバーのBLOBまたはメモフィールドを単純に暗号化および復号化する場合、サーバーの「キー」および「IV」値はどこに保存しますか? (ファイル、Regkey、Dbase、...)

そして、それらのAESの「キー」および「IV」値を保護するとどうなりますか?

バックグラウンドの質問はもっとあります:「彼ら」がサーバーをハックしてdbaseを取得した場合、おそらく彼らは暗号化を行うプログラムにも到達できます(同じサーバー上にあり、それを助けることはできません)... 「それら」が非常に優れている場合、「キー」と「IV」の値が保存されている場所に気付くでしょう...(。NET 4.5 ILSPY)、すべてを再び復号化できます。

ご意見をお聞かせください? AESの「キー」と「IV」の値をすべてどのように処理しますか?

追伸:これはpwdフィールドに関するものではありません...したがって、ハッシュに関するものではありません...その純粋なデータ暗号化です。

31
ChiYoung

IVは他の回答で完全にカバーされているため、キーの保存にのみ焦点を当てます。

最初...

ソフトウェアレベルで単一のサーバーで実行できなかったことを除けません。

ソフトウェアで行われたものはすべて、ソフトウェアで元に戻すことができます。暗号化、非表示、およびロックを必要な数だけ金庫に入れることができますが、アプリケーションはキーにアクセスできる必要があります。アプリケーションにアクセス権がある場合、アプリケーションと同じレベルのアクセス権を持つユーザーもアクセスできます。

開発者は長い間この問題に対処してきましたが、特効薬はありません。

これらはすべて単一のサーバー環境(アプリケーションとdbase)でセットアップされているため、2番目のサーバーにキーを送信/取得することはできません。また、この「特別な」ケースでは、マシンレベルまたはユーザーレベルのRSAキーコンテナでキーを暗号化できません。

私は2つの可能な解決策を考えることができます。

オプション1:

キーをディスクに保存し、OSレベルで、アプリケーションが実行されているアカウントのみがキーが含まれているファイルを読み取れるようにファイルアクセスを構成します。ファイルは、フラットファイル、または保護されている暗号化されたコンテナアプリケーションが知っているパスワード(決定はあなた次第ですが、暗号化されたコンテナの方が良いです)。

長所:

  • 人間の介入なしで再起動します。

短所:

  • OSセキュリティ権限を実行する必要があり、エラーの余地はありません。
  • 管理者アクセス権を持つ攻撃者がキーにアクセスできます。

これに似たもう1つのオプションは、キーを保存するファイルの代わりに [〜#〜] dpapi [〜#〜] を使用することです(「特殊な場合")。これはWindowsに組み込まれたAPIであり、ユーザー(またはアプリケーション)が実行しているWindowsアカウントのパスワードを使用して、データを安全に保存します。データを保存したWindowsアカウントのみがデータを取得できます。

DPAPIの特に優れた機能の1つは、管理者がユーザーのパスワードを(コンピューター管理を介して)リセットすると、 そのユーザーへのアクセスはDPAPIデータが失われる です。攻撃者は、パスワードをリセットせずに最初の場所にデータを保存するために使用された実際のアカウントを侵害する必要があります。

オプション2:

アプリケーションの起動時にパスフレーズを入力する必要があり、そのパスフレーズから暗号化キーを取得します。キーを取得したら、パスフレーズを破棄し、メモリにのみキーを保持します。

長所:

  • キーがディスク上にあることはありません。
  • サーバーがルート化されている場合でも、キーに到達するのは簡単な作業ではありません。

短所:

  • 自動再起動はできません。
  • パスフレーズは、サポートを処理する誰とでも共有する必要があります。
  • メモリに保存されているデータmay特定の状況では透過的にディスクに書き込まれることに留意する必要があります。

または、これら2つのシステム間で妥協を行うこともできます。この場合、パスフレーズを使用してメモリに保持される暗号化キーを導出し、アプリケーションが正常に再起動されるたびにキーが一時的にディスクまたは暗号化コンテナに書き込まれます。再起動が完了すると、アプリケーションはキーをロードし、一時ストレージから削除します(必要に応じて、キーが保存されないようにキーを保存したディスクの場所を上書きしてください)。

27
Syon

経験則は次のとおりです。

  • キーは常に秘密である必要があります(データベースの近くにある必要はありません)
  • IVはレコードごとに異なる必要があります。
  • IVは「ランダムと区別がつかず」、予測不可能である必要があります。できれば、AESキーと同じソースから取得する必要があります。他のオプションは、秘密鍵で何らかの値(レコードごとに異なる)を暗号化することです。
  • IVは秘密である必要はありません

したがって、使用できるスキームは次のとおりです。

  1. フィールドID(一意、int)、IV(一意、16バイト)、暗号化(可変バイト、NULL可能)を持つテーブルを作成します
  2. データベースに新しいレコードを書き込むには、新しい一意のIVを作成し、空の暗号化データを使用してデータベースに新しいレコードを作成します(衝突を防ぐため)
  3. secretキーとステップ2のIV(CBCまたはCTRモード-CTRの方が良い)でデータを暗号化し、レコードを更新します。

ステップ2は、前のレコードからIVを取得し、同じ秘密キーで暗号化することで実行できます。AESのプロパティにより、これは事実上ランダムなIVになります。

これは、AESで取得できる限り安全です。つまり、CCA/CPAは安全です。防止できないのは改ざんだけです

13
DarkWanderer

IVをキーと同じように秘密にしておく必要はありません。同じキーで暗号化されたまったく同じ2つのblobが、まったく異なる2つの出力を生成することを確認するだけです同じメッセージが2回送信されたことを伝えないでください)。多くの暗号化システムは、IVをメッセージの最初のバイトにします。

暗号化キーは管理が難しいものです。できることは、データベース自体とアプリケーションを分離し、「「彼ら」がサーバーをハッキングし、dbaseを取得する場合」(SQLインジェクション攻撃により、データベースのテーブル)彼らはまだフィールド自体を解読できません。

11

ここでは、Webサーバーとdbサーバーを分離すると役立ちます。暗号化キーへのアクセスを(アクセス許可に関して)ロックダウンし、SecureStringとしてメモリに保持します。それ以上のことはできません。強力なパスワードを選択し、最新のセキュリティ慣行に従ってください。

良い投稿もあります 暗号化キーMVCアプリケーションの保存場所

1
DavidN

暗号化された情報があまり多くない場合、暗号化されたレコードからパスワードと情報を定期的に更新します。たとえば、毎日または1時間ごとなどです。

0