4

I wrote my SecretKey to a file using the following code. Similarly, I have to write my ivParameterSpec to another file. How can I do this?

SecretKey key = KeyGenerator.getInstance("AES").generateKey();
ObjectOutputStream secretkeyOS = new ObjectOutputStream(new FileOutputStream("publicKeyFile"));
secretkeyOS.writeObject(key);
secretkeyOS.close();

AlgorithmParameterSpec paramSpec1 = new IvParameterSpec(iv);
session.setAttribute("secParam", paramSpec1);
ObjectOutputStream paramOS = new ObjectOutputStream(new FileOutputStream("paramFile"));
paramOS.writeObject(paramSpec1);
paramOS.close();
8
  • iv is 16bit byte array Commented Oct 8, 2013 at 11:06
  • I think, this answer to write a byte array to a file should help you. stackoverflow.com/questions/4350084/byte-to-file-in-java Commented Oct 8, 2013 at 11:23
  • no, it's not possible. paramspec1 is not a byte array Commented Oct 8, 2013 at 11:31
  • Why do you want to save the object? Save the iv and create a new Spec from this when you need it to decrypt or so Commented Oct 8, 2013 at 11:35
  • 3
    The IV is the part that defines the IvParameterSpec. If you store the iv and load it again. new IvParameterSpec(loaded_iv) this new parameter spec IS EQUAL to the other one. Your code is not working, because an IvParameterSpec is not serializable because it is not intended to be stored Commented Oct 8, 2013 at 11:53

1 Answer 1

6

Don't try to store the IvParameterSpec object. It is not serializable, because it is not intended to be stored. The IV is the important part. Store this and create a new IvSpec from the IV. I have changed example code from here for AES encryption to store the IV and use the loaded IV to decrypt the ciphertext so you can see a possible workflow.

Please be aware that this is a minimal example. In a real usecase you would store and load the key as well and exception handling should also be reconsidered :-D

public class Test {
    public static void main(String[] args) throws Exception {
        String message = "This string contains a secret message.";

        // generate a key
        KeyGenerator keygen = KeyGenerator.getInstance("AES");
        keygen.init(128);
        byte[] key = keygen.generateKey().getEncoded();
        SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");

        byte[] iv = { 0, 1, 0, 2, 0, 3, 0, 4, 0, 5, 0, 6, 0, 7, 0, 8 };
        IvParameterSpec ivspec = new IvParameterSpec(iv);

        // initialize the cipher for encrypt mode
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
        cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivspec);

        // encrypt the message
        byte[] encrypted = cipher.doFinal(message.getBytes());
        System.out.println("Ciphertext: " + hexEncode(encrypted) + "\n");

        // Write IV
        FileOutputStream fs = new FileOutputStream(new File("paramFile"));
        BufferedOutputStream bos = new BufferedOutputStream(fs);
        bos.write(iv);
        bos.close();

        // Read IV
        byte[] fileData = new byte[16];
        DataInputStream dis = null;

        dis = new DataInputStream(new FileInputStream(new File("paramFile")));
        dis.readFully(fileData);
        if (dis != null) {
            dis.close();
        }

        // reinitialize the cipher for decryption
        cipher.init(Cipher.DECRYPT_MODE, skeySpec, new IvParameterSpec(fileData));

        // decrypt the message
        byte[] decrypted = cipher.doFinal(encrypted);
        System.out.println("Plaintext: " + new String(decrypted) + "\n");
    }

    [...]
}
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.