001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.wicket.pageStore.crypt;
018
019import java.security.AlgorithmParameters;
020import java.security.GeneralSecurityException;
021import java.security.SecureRandom;
022import java.util.Arrays;
023
024import javax.crypto.Cipher;
025import javax.crypto.KeyGenerator;
026import javax.crypto.SecretKey;
027import javax.crypto.spec.IvParameterSpec;
028
029import org.apache.wicket.WicketRuntimeException;
030
031/**
032 * Default encryption and decryption implementation.
033 */
034public class DefaultCrypter implements ICrypter
035{
036        protected Cipher getCipher() throws GeneralSecurityException
037        {
038                return Cipher.getInstance("AES/CBC/PKCS5Padding");
039        }
040
041        @Override
042        public SecretKey generateKey(SecureRandom random)
043        {
044                try
045                {
046                        KeyGenerator generator = KeyGenerator.getInstance("AES");
047                        generator.init(256, random);
048                        return generator.generateKey();
049                }
050                catch (GeneralSecurityException ex)
051                {
052                        throw new WicketRuntimeException(ex);
053                }
054        }
055
056        @Override
057        public byte[] encrypt(byte[] decrypted, SecretKey key, SecureRandom random)
058        {
059                try
060                {
061                        Cipher cipher = getCipher();
062                        cipher.init(Cipher.ENCRYPT_MODE, key, random);
063
064                        AlgorithmParameters params = cipher.getParameters();
065                        byte[] iv = params.getParameterSpec(IvParameterSpec.class).getIV();
066
067                        byte[] ciphertext = cipher.doFinal(decrypted);
068
069                        byte[] encrypted = Arrays.copyOf(iv, iv.length + ciphertext.length);
070                        System.arraycopy(ciphertext, 0, encrypted, iv.length, ciphertext.length);
071
072                        return encrypted;
073                }
074                catch (GeneralSecurityException ex)
075                {
076                        throw new WicketRuntimeException(ex);
077                }
078        }
079
080        @Override
081        public byte[] decrypt(byte[] encrypted, SecretKey key)
082        {
083                try
084                {
085                        byte[] iv = new byte[16];
086                        byte[] ciphertext = new byte[encrypted.length - 16];
087                        System.arraycopy(encrypted, 0, iv, 0, iv.length);
088                        System.arraycopy(encrypted, 16, ciphertext, 0, ciphertext.length);
089
090                        Cipher cipher = getCipher();
091                        cipher.init(Cipher.DECRYPT_MODE, key, new IvParameterSpec(iv));
092                        byte[] decrypted = cipher.doFinal(ciphertext);
093
094                        return decrypted;
095                }
096                catch (GeneralSecurityException ex)
097                {
098                        throw new WicketRuntimeException(ex);
099                }
100        }
101}