Шифрование ЕЦБ Golang AES
попытка эмулировать алгоритм в Go, который в основном является шифрованием режима AES ECB.
вот что у меня пока
func Decrypt(data []byte) []byte {
cipher, err := aes.NewCipher([]byte(KEY))
if err == nil {
cipher.Decrypt(data, PKCS5Pad(data))
return data
}
return nil
}
у меня также есть алгоритм PKCS5Padding, который тестируется и работает, который сначала заполняет данные. Я не могу найти никакой информации о том, как переключить режим шифрования в пакете Go AES (это определенно не в документы).
у меня есть этот код на другом языке, поэтому я знаю, что этот алгоритм не работает вполне корректно.
EDIT: вот метод, как я интерпретировал на странице проблемы
func AESECB(ciphertext []byte) []byte {
cipher, _ := aes.NewCipher([]byte(KEY))
fmt.Println("AESing the data")
bs := 16
if len(ciphertext)%bs != 0 {
panic("Need a multiple of the blocksize")
}
plaintext := make([]byte, len(ciphertext))
for len(plaintext) > 0 {
cipher.Decrypt(plaintext, ciphertext)
plaintext = plaintext[bs:]
ciphertext = ciphertext[bs:]
}
return plaintext
}
это на самом деле не возвращает какие-либо данные, может я что-то напортачил при изменении его от encripting в decripting
4 ответов
ЕЦБ оставлен намеренно, потому что он небезопасен, проверьте вопрос 5597.
я использовал ваш код, поэтому я чувствую необходимость показать вам, как я его исправил.
Я делаю проблемы cryptopals для этой проблемы в Go.
Я проведу вас через ошибку, так как код в основном правильный.
for len(plaintext) > 0 {
cipher.Decrypt(plaintext, ciphertext)
plaintext = plaintext[bs:]
ciphertext = ciphertext[bs:]
}
цикл расшифровывает данные, но не помещает их нигде. Он просто сдвигает два массива, не производя никакого вывода.
i := 0
plaintext := make([]byte, len(ciphertext))
finalplaintext := make([]byte, len(ciphertext))
for len(ciphertext) > 0 {
cipher.Decrypt(plaintext, ciphertext)
ciphertext = ciphertext[bs:]
decryptedBlock := plaintext[:bs]
for index, element := range decryptedBlock {
finalplaintext[(i*bs)+index] = element
}
i++
plaintext = plaintext[bs:]
}
return finalplaintext[:len(finalplaintext)-5]
что делает это новое улучшение, это сохраняет расшифрованные данные в новый []байт называется finalplaintext. Если вы вернете это, вы получите данные.
важно сделать это таким образом, так как функция дешифрования работает только один размер блока одновременно.
Я возвращаю кусочек, потому что подозреваю, что он мягкий. Я новичок в криптографии и иду, поэтому любой может исправить/пересмотреть это.
ESB - Это очень простой режим работы. Шифруемые данные делятся на байтовые блоки одинакового размера. Для каждого блока применяется шифр, в данном случае AES, создание зашифрованного блока.
приведенный ниже фрагмент кода расшифровывает данные AES-128 в ECB (обратите внимание, что размер блока составляет 16 байт):
package main
import (
"crypto/aes"
)
func DecryptAes128Ecb(data, key []byte) []byte {
cipher, _ := aes.NewCipher([]byte(key))
decrypted := make([]byte, len(data))
size := 16
for bs, be := 0, size; bs < len(data); bs, be = bs+size, be+size {
cipher.Decrypt(decrypted[bs:be], data[bs:be])
}
return decrypted
}
Как упоминалось @OneOfOne, ECB небезопасен и очень прост в обнаружении, поскольку повторяющиеся блоки всегда будут шифрование на те же зашифрованные блоки. Это Crypto SE ответ дает очень хорошее объяснение, почему.
меня смутило несколько вещей.
сначала мне нужна была версия AES-256 вышеуказанного алгоритма, но, по-видимому, aes.Blocksize (который равен 16) не изменится, если данный ключ имеет длину 32. Так что достаточно дать ключ длиной 32, чтобы сделать алгоритм aes-256
во-вторых, расшифрованное значение по-прежнему содержит заполнение, а значение заполнения изменяется в зависимости от длины зашифрованной строки. Е. Г. когда есть 5 персонажей обивка обивка характер сама будет 5.
вот моя функция, которая возвращает строку:
func DecryptAes256Ecb(hexString string, key string) string {
data, _ := hex.DecodeString(hexString)
cipher, _ := aes.NewCipher([]byte(key))
decrypted := make([]byte, len(data))
size := 16
for bs, be := 0, size; bs < len(data); bs, be = bs+size, be+size {
cipher.Decrypt(decrypted[bs:be], data[bs:be])
}
// remove the padding. The last character in the byte array is the number of padding chars
paddingSize := int(decrypted[len(decrypted)-1])
return string(decrypted[0 : len(decrypted)-paddingSize])
}