2016-04-10 11 views
0

イメージに約500MBの大きなファイルを暗号化する必要があるWebアプリケーションを開発しています。コードは正常に動作しますが、それ以降はサーバーでエラーが発生します。java.lang.OutOfMemoryError:Javaヒープスペース。私はnetbeansとglassfishサーバーを使用しています。ヒープサイズも増やしました。java.lang.OutOfMemoryError:com.sun.crypto.provider.CipherCore.updateのJavaヒープスペース

byte j[] = key.getBytes(); 
    SecretKeySpec kye = new SecretKeySpec(j, "AES"); 
    Cipher enc = Cipher.getInstance("AES"); 
    enc.init(Cipher.ENCRYPT_MODE, kye); 
    FileOutputStream output = new FileOutputStream("xyz.mkv"); 
    CipherOutputStream cos = new CipherOutputStream(output, enc); 
    byte[] buf = new byte[104857600]; 
    int read; 
    while ((read = file.read(buf)) != -1) { 
     cos.write(buf, 0, read); 
    } 
    output.flush(); 
    buf = null; 
    file.close(); 
    cos.close(); 

私は何がうまくいかないのか分かりません。お手伝いください。 は、ここでは、スタックトレース..です

Warning: StandardWrapperValve[DocEncrypt]: Servlet.service() for  
servlet DocEncrypt threw exception 
java.lang.OutOfMemoryError: Java heap space 
at java.util.Arrays.copyOf(Arrays.java:3236) 
at com.sun.crypto.provider.CipherCore.update(CipherCore.java:666) 
at com.sun.crypto.provider.AESCipher.engineUpdate(AESCipher.java:371) 
at javax.crypto.Cipher.update(Cipher.java:1832) 
at javax.crypto.CipherOutputStream.write(CipherOutputStream.java:158) 
+1

スタックトレースを表示してください。 –

+0

@StephenCスタックトレースを追加しました。 –

答えて

1

stacktraceとソースコードに基づいて、暗号スタックは、write呼び出しで書き込み中のブロックと同じサイズのバッファを内部的に割り当てているように見えます。

本当に大きなバッファを使用することを選択しました。すなわち104,857,600バイトである。したがって、暗号スタック自体は非常に大きなバッファを割り当てる必要があります。

ソリューション:

  1. あなたはヒープサイズを増やすことができます。
  2. :バッファサイズをもっと妥当なものに減らすことができます。私は1MiB以下をお勧めします。 (それよりも大きく、バッファを大きくすることによるパフォーマンス上の利点は小さいです...)
+0

それは問題を解決しますが、私はこのアルゴリズムのパフォーマンスをより良くすることができます。 –

+0

Javaでより速い方法は考えられません。暗号化は高価です。ネイティブ(サードパーティ製の)ライブラリやスタンドアロンのネイティブユーティリティ。 –

+0

助けてくれてありがとう。 –

0

短い答えは、あなたはJava仮想マシンFEの最大メモリ割り当てプールを増やす必要があります:-Xmx2048mを、あなたのアプリケーションを起動したとき。

詳しくは、this amswerを参照してください。

+0

おそらく。また、記憶が少なくても、自分がやろうとしていることをやり遂げることができる可能性があります。たとえば、100Mbのバッファが...流行しているようです。 –

+0

hmmですが、より小さなバッファを使用すると何かが変更されます(メモリ単位)?それはちょうどほぼ同じになるより小さなバイト[]配列を作成するでしょう。私はGCがとにかく追いつくのに十分速いとは思わない。 – grebesche

+0

それはもちろんです。より小さいバッファを使用すると、バッファのヒープ・ノードが小さくなります。それは重要なGCの速度ではありません。最初の概算では、到達可能なすべてのオブジェクトの合計サイズで、スペースを使い果たしたときを決定します。 –