001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.io.crypto.aes; 019 020import java.io.IOException; 021import java.io.OutputStream; 022import java.security.Key; 023import java.security.SecureRandom; 024import java.util.Properties; 025import javax.crypto.spec.IvParameterSpec; 026import org.apache.commons.crypto.stream.CryptoOutputStream; 027import org.apache.hadoop.hbase.io.crypto.Encryptor; 028import org.apache.yetus.audience.InterfaceAudience; 029import org.apache.yetus.audience.InterfaceStability; 030 031import org.apache.hbase.thirdparty.com.google.common.base.Preconditions; 032 033@InterfaceAudience.Private 034@InterfaceStability.Evolving 035public class CommonsCryptoAESEncryptor implements Encryptor { 036 037 private String cipherMode; 038 private Properties properties; 039 private Key key; 040 private byte[] iv; 041 private boolean initialized = false; 042 private SecureRandom rng; 043 044 public CommonsCryptoAESEncryptor(String cipherMode, Properties properties, SecureRandom rng) { 045 this.cipherMode = cipherMode; 046 this.properties = properties; 047 this.rng = rng; 048 } 049 050 @Override 051 public void setKey(Key key) { 052 this.key = key; 053 } 054 055 @Override 056 public int getIvLength() { 057 return CommonsCryptoAES.IV_LENGTH; 058 } 059 060 @Override 061 public int getBlockSize() { 062 return CommonsCryptoAES.BLOCK_SIZE; 063 } 064 065 @Override 066 public byte[] getIv() { 067 return iv; 068 } 069 070 @Override 071 public void setIv(byte[] iv) { 072 Preconditions.checkNotNull(iv, "IV cannot be null"); 073 Preconditions.checkArgument(iv.length == CommonsCryptoAES.IV_LENGTH, "Invalid IV length"); 074 this.iv = iv; 075 } 076 077 @Override 078 public OutputStream createEncryptionStream(OutputStream out) { 079 if (!initialized) { 080 reset(); 081 } 082 try { 083 return new CryptoOutputStream(cipherMode, properties, out, key, new IvParameterSpec(iv)); 084 } catch (IOException e) { 085 throw new RuntimeException(e); 086 } 087 } 088 089 @Override 090 public void reset() { 091 if (iv == null) { 092 iv = new byte[getIvLength()]; 093 rng.nextBytes(iv); 094 } 095 initialized = true; 096 } 097}