使用SecretKeySpec / StreamCorruptedException存储密钥

时间:2015-11-01 12:23:52

标签: java aes store

我在这里阅读了Java 256-bit AES Password-Based Encryption和其他几个条目。

我也看过这个:http://pastebin.com/YiwbCAW8

我在做什么: 我想用AES保护文件(users.dat),我只使用一串输出和输入流。

对象 - >密码 - >缓冲 - > FileOutputStream中

fileinputstream - >缓冲 - >密码 - >对象

因此,当我重新启动应用程序时,我想加载存储在该文件中的数据(users.dat)。

我在阅读文件时总是会遇到此异常( users.dat )。在先阅读 users.dat 之前,我从 key.dat

中读取了秘密字节
java.io.StreamCorruptedException: invalid stream header: 7E000274
at java.io.ObjectInputStream.readStreamHeader(ObjectInputStream.java:806)
at java.io.ObjectInputStream.<init>(ObjectInputStream.java:299)
at edu.hm.wedoit.usermanagement.impl.UserManagementImpl.loadUsers(UserManagementImpl.java:256)
at edu.hm.wedoit.usermanagement.impl.UserManagementImpl.<init>(UserManagementImpl.java:105)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:408)
at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:147)
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:125)
at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:270)
//.... more spring 

第一 如果没有密钥文件,我创建密钥并将其写入本地文件(key.dat)(未加密):

        try(BufferedOutputStream bos = new BufferedOutputStream( new FileOutputStream(keyFile)))
    {
byte[] secretBytes = secret.getEncoded();
bos.write(secretBytes)
}
//catch

-32115-4061-70-102115-33-123-6494159-6-86115 (从简单的for循环输出,这些是写入文件的字节)

Keycreation代码:

            SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256");
        KeySpec spec = new PBEKeySpec("wedoit".toCharArray(), SALT, 65536, 128); 
//note I only use 128 here because 256 doesnt work despite having local_policy.jar / US_export_policy.jar in {jdk}/lib/security 

        SecretKey tmp = factory.generateSecret(spec);
        secretBytes = tmp.getEncoded();
        secret = new SecretKeySpec(secretBytes, "AES");
        saveSecret(secret); //saves the bytes to a simple file via object / ciper / buffered / fileoutputstream 

Secdond 如果密钥文件存在,则在启动时,我从文件中读取字节。

-32115-4061-70-102115-33-123-6494159-6-86115(与上面的输出相同)

    try(BufferedInputStream bis = new BufferedInputStream(new FileInputStream(keyFile)))
    {
        byte[] secretBytes = new byte[16];
bis.read(secretBytes);
return secretBytes;
}
//catch

对我来说,似乎写入/读取密钥文件似乎有效

secretBytes = loadKey(); 
secret = new SecretKeySpec(secretBytes, "AES"); // I thought the key will be reconstructed here?

所以这里有一些我用于密码初始化的代码。

        encryptionCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    byte[] ivbyte = encryptionCipher.getParameters().getParameterSpec(IvParameterSpec.class).getIV();

    encryptionCipher.init(Cipher.ENCRYPT_MODE, secret, new IvParameterSpec(ivbyte));

    decryptionCipher = Cipher.getInstance("AES/CBC/PKCS5Padding");

    decryptionCipher.init(Cipher.DECRYPT_MODE, secret, new IvParameterSpec(ivbyte));

更新 我使用try-with-resource(输入/输出)。

        try(ObjectInputStream ois = new ObjectInputStream(
            new CipherInputStream(new BufferedInputStream(new FileInputStream(userdbFile)),decryptionCipher)))
    {

        // .... ois.readObject();....
    }
//...catch...

我做错了什么?

编辑稍微更新一下以澄清情况,我正在谈论的文件。到目前为止,感谢您的评论!

已经澄清:(搬到这里)

我注意到一些奇怪的东西,但我不知道它是否重要(连续调用,输出不同):

编辑:感谢评论中的jon

,似乎无法导入
System.out.println(secret.getEncoded()); // [B@5c7e77fe
System.out.println(secret.getEncoded()); // [B@78b23edb
System.out.println(secret.getEncoded()); // [B@1e64a539

0 个答案:

没有答案