Java AES без отступов - PullRequest
       23

Java AES без отступов

13 голосов
/ 01 октября 2011

Каковы некоторые из самых простых способов шифрования и дешифрования AES 16-байтового массива без автоматического заполнения?Я нашел решения, которые используют внешние библиотеки, но я хочу избежать этого, если это возможно.

Мой текущий код

SecretKeySpec skeySpec = new SecretKeySpec(getCryptoKeyByteArray(length=16)); // 128 bits
Cipher encryptor = Cipher.getInstance("AES");
encryptor.init(Cipher.ENCRYPT_MODE, skeySpec);
byte[] encrypted = encryptor.doFinal(plain);

Как я могу предотвратить заполнение?Данные plain всегда имеют фиксированную длину и включают собственные отступы.Как я могу позволить plain быть 16 байтами, не заставляя encrypted становиться 32 байтами?

Ответы [ 3 ]

17 голосов
/ 01 октября 2011

Смотрите мой комментарий.Извините, мне, наверное, следовало бы присмотреться в первый раз.

  1. Изменить "AES" на "AES/CBC/NoPadding"
  2. Изменить decryptor.init(Cipher.DECRYPT_MODE, skeySpec); на decryptor.init(Cipher.DECRYPT_MODE, skeySpec, encryptor.gerParameters());

Чтобы зашифровать только 16 байтов данных фиксированной длины, используя метод, который не требует сохранения вектора инициализации, измените "AES" на "AES/ECB/NoPadding"

Я выбираю ECB, потому что это значение по умолчанию .

Если вам необходимо зашифровать более 16 байтов, рассмотрите возможность использования чего-то другого, кроме ECB, которое имеет определенный недостаток обнаружения повторений

В этом примере растрового изображения это изображение имеет повторяющиеся белые блоки, поэтому вы можете определить контур изображения, просто посмотрев, где блоки становятся разными.

before encryption encrypted

ЕслиВы только зашифровываете один блок, это не имеет значения, только если вы шифруете несколько блоков, которые объединены, ECB становится показательным.

Related: https://security.stackexchange.com/questions/15740/what-are-the-variables-of-aes

6 голосов
/ 25 июня 2012

Согласен с @rossum, но есть еще кое-что:

Режиму CTR необходим вектор инициализации (IV).Это «счетчик» (это то, к чему относится «CTR»).Если вы можете хранить IV отдельно (его не нужно защищать), это сработает.При расшифровке данных вам понадобится одно и то же значение IV.

Если вы не хотите хранить IV, и вы можете гарантировать, что никакие два значения не будут зашифрованы одним и тем жеключ , можно использовать фиксированный IV (даже массив 0 с).

Выше очень важно, потому что шифрование более одного сообщения с тем же ключом/ IV комбинация разрушает безопасность.См. Раздел Вектор инициализации (IV) в этой статье Википедии: http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation

Реализация кода CES в AES может быть:

SecretKeySpec skeySpec = new SecretKeySpec(getCryptoKeyByteArray(length=16)); 
Cipher encryptor = Cipher.getInstance("AES/CTR/NoPadding");

// Initialisation vector:
byte[] iv = new byte[encryptor.getBlockSize()];
SecureRandom.getInstance("SHA1PRNG").nextBytes(iv); // If storing separately
IvParameterSpec ivParameterSpec = new IvParameterSpec(iv);

encryptor.init(Cipher.ENCRYPT_MODE, skeySpec, ivParameterSpec); 
byte[] encrypted = encryptor.doFinal(plain); 
2 голосов
/ 01 октября 2011

Режим CTR не требует заполнения: "AES/CTR/NoPadding".

...