2017-01-17 8 views
0

ありがとう、私を助けてくれてありがとう!(AES暗号化)コードの脆弱性、どうすればよいですか? [コード提供] [Java]

THIS POSTがLESS情報については、編集された は、編集部分を見る

まあ..私はこの問題について研究を私たちが過ごす持っていると私は、コードの作業を一枚になってしまった

しかし、暗号化間違いを犯す場所ではなく、自分のコードが実際に安全であるかどうか尋ねたいと思っていました。 JFPicard

- 私は私のコードが...

import java.nio.file.Files; 
import java.nio.file.Paths; 

import java.util.Base64; 

import javax.crypto.*; 
import javax.crypto.spec.SecretKeySpec; 
import java.security.SecureRandom; 


public class EncryptFile{ 
    private static final String FILE_IN = "./EncryptFile.java"; 
    private static final String FILE_ENCR = "./EncryptFile_encr.java"; 
    private static final String FILE_DECR = "./EncryptFile_decr.java"; 
    public static void main(String []args){ 
     try 
     { 
      Encryption("passwordisnottheactual", Files.readAllBytes(Paths.get(FILE_IN))); 
      Decryption("passwordisnottheactual"); 

     }catch(Exception e){ 
      System.out.println(e.getMessage()); 
     } 
    } 
    private static void Encryption(String Key, byte[] byteArray) throws Exception 
    { 
     // Decode the base64 encoded Key 
     byte[] decodedKey = Base64.getDecoder().decode(Key); 
     // Rebuild the key using SecretKeySpec 
     SecretKey secretKey = new SecretKeySpec(decodedKey, 0, decodedKey.length, "AES"); 

     // Cipher gets AES Algorithm instance 
     Cipher AesCipher = Cipher.getInstance("AES"); 

     //Initialize AesCipher with Encryption Mode, Our Key and A ?SecureRandom? 
     AesCipher.init(Cipher.ENCRYPT_MODE, secretKey, new SecureRandom()); 
     byte[] byteCipherText = AesCipher.doFinal(byteArray); 

     //Write Bytes To File 
     Files.write(Paths.get(FILE_ENCR), byteCipherText); 


    } 
    private static void Decryption(String Key) throws Exception 
    { 
     //Ddecode the base64 encoded string 
     byte[] decodedKey = Base64.getDecoder().decode(Key); 
     //Rebuild key using SecretKeySpec 
     SecretKey secretKey = new SecretKeySpec(decodedKey, 0, decodedKey.length, "AES"); 

     //Read All The Bytes From The File 
     byte[] cipherText = Files.readAllBytes(Paths.get(FILE_ENCR)); 

     //Cipher gets AES Algorithm Instance 
     Cipher AesCipher = Cipher.getInstance("AES"); 

     //Initialize it in Decrypt mode, with our Key, and a ?SecureRandom? 
     AesCipher.init(Cipher.DECRYPT_MODE, secretKey, new SecureRandom()); 

     byte[] bytePlainText = AesCipher.doFinal(cipherText); 
     Files.write(Paths.get(FILE_DECR), bytePlainText); 
    } 
} 

EDIT

単純なJava AESの暗号化/復号化の例の可能な複製であるので、プログラムにそれを実装したいので、それは私にとって本当に重要です

この回答はIVParameterSpecを使用してください。 このコード行が実際に安全かどうか、悪い場合は

AesCipher.init(Cipher.DECRYPT_MODE, secretKey, new SecureRandom()); 

私はnew SecureRandom()毎回、 を使用しているため、私は誰もがこのようなSecureRandomオブジェクトを使用して見ていません。

+3

あなたのコードを見直すつもりはないので、http://codereview.stackexchange.com/を試してみてください。 –

+0

可能性の重複[単純なJava AESの暗号化/復号化の例を](http://stackoverflow.com/questions/15554296/simple-java-aes-encrypt-decrypt-example) – JFPicard

答えて

2
  1. 暗号化キー
    • パスワードでは、文字列として渡しますがEncryption関数Base64ではそれを復号し、それはコーディングエラーです。
    • パスワードを使用する場合は、PBKDF2(別名Rfc2898DeriveBytes)機能を使用して暗号化キーを取得する必要があります。
    • 鍵の派生を使用する場合、暗号化のためにsaltと繰り返し回数を利用できる必要があります。暗号化されたデータの接頭辞には、しばしば提供されます。
  2. 暗号化モード
    • ませ暗号化モードが指定されていません。
    • ランダムIVのCBCモードを使用します。
    • 復号化に使用するために、暗号化されたデータの先頭にIVを付加します。
  3. パディング
    • AESブロック暗号であり、そのようなものとして、ブロックサイズの倍数に入力データサイズを必要とします。
    • PKCS#7(néePKCS#5)パディングを指定すると、パディングが暗号化に追加され、解読時にパディングが削除されます。
    • 解読時に「パディング」エラーが返されず、「パディング・オラクル」攻撃を提供できます。
  4. 明示
    • すべて暗号化パラメータとサイズを指定します。
    • 実装のデフォルトには依存しないでください。データが正しく復号されたかどうかを知る必要がある場合
  5. 暗号化認証
    • 考えてみましょう。変更が必要な場合、後で互換性経路が存在するように
      • はバージョンインジケータを追加バージョニング

またはすべての本以上を扱うRNCryptorを使用することを検討してください。

更新:(コメントのためのTHXアンディ)
GCMモードが利用可能であり、プラットフォームや図書館間の相互運用性は、GCMは間違いなく、より良い暗号化モードで問題がない場合。 GCMには認証とパディングが組み込まれており、より堅牢で簡単なセキュリティソリューションになります。

+0

私はCBC '上' AES/GCM'をお勧めします' - CBCは機密性を提供しますが、完全性の保証はなく、GCM認証タグのオーバーヘッドは軽微です(AES-NIチップでは、かなり性能があります)。 – Andy

+0

私は、GCMモードがいくつかの面で優れていることに同意します。ただし、プラットフォームやライブラリ間の可用性は不十分です。 – zaph

+0

本当に好奇心が強い - HWの実装を検討しているの?私は過去4年間にJavaを実行してもGCMを処理できないものは考えられません。 OPはNIO2を使用しているので、少なくともJavaの7.私は、GCMの可用性のあなたの評価に校長に同意するが、それはここでは制限要因だったとは思いませんでした。 – Andy

関連する問題