小弟我在參考別的大大使用vb 編寫的解密程式
內容如下 :
`
Imports System
Imports System.Security.Cryptography
Imports System.Text
Module Program
Sub Main(args As String())
Dim FileNum As Integer
Dim strTemp As String
Dim Key As String = "1158CB77"
Dim hexString As String = "A755DDB424D77F7FBBDFC6B457587092"
Dim des As New DESCryptoServiceProvider()
'DESCryptoServiceProvider des = New DESCryptoServiceProvider()
des.Mode = CipherMode.ECB
des.IV = Encoding.ASCII.GetBytes(Key)
des.Padding = PaddingMode.None
des.Key = Encoding.ASCII.GetBytes(Key)
Dim y = 2
Dim s(hexString.Length / 2) As Byte
Dim j = 0
'Console.WriteLine(Len(hexString) / 2)
For i As Integer = 0 To (Len(hexString) / 2 - 1)
s(i) = Byte.Parse(Mid(hexString, j + 1, 1).ToString() + Mid(hexString, j + 2, 1).ToString(), System.Globalization.NumberStyles.HexNumber)
'Console.WriteLine(s(i))
j += 2
Next
Dim desencrypt As ICryptoTransform = des.CreateDecryptor()
Dim h() As Byte = {s(0), s(1), s(2), s(3), s(4), s(5), s(6), s(7), s(8), s(9), s(10), s(11), s(12), s(13), s(14), s(15)}
' {167 ,85 ,221 ,180 ,36 ,215 ,127 ,127 ,187 ,223 ,198 ,180 ,87 ,88 ,112 ,146}
Dim re As String = Encoding.ASCII.GetString(desencrypt.TransformFinalBlock(h, 0, h.Length))
Console.WriteLine(re) '1114420095
End Sub
End Module
`
想請教一下最後面的TransformFinalBlock,是怎麼把{167,85,221,180,36,215,127,127,187,223,198,180,87,88,112,146}
變成1114420095的。
小弟我嘗試使用python去翻譯,但都弄不出一個所以然
程式碼如下 :
#!/usr/bin/python
# -*- coding: utf-8 -*-
import binascii
from pyDes import des, CBC, PAD_PKCS5, ECB
def des_encrypt(secret_key, s):
iv = secret_key
k = des(secret_key, ECB, iv, pad=None, padmode=None)
#print(k)
en = k.encrypt(s, padmode=PAD_PKCS5)
#print(en)
return binascii.b2a_hex(en)
def des_decrypt(secret_key, s):
iv = secret_key
k = des(secret_key, ECB, iv, pad=None, padmode=None)
de = k.decrypt(binascii.a2b_hex(s), padmode=PAD_PKCS5)
return de
secret_str = des_encrypt('1158CB77', '1114420095')
print ('密文:', secret_str)#b'a755ddb424d77f7f6e52fb9e82cc897f'
clear_str = des_decrypt('1158CB77', secret_str)
print ('明文:', clear_str)#b'1114420095'
test='A755DDB424D77F7FBBDFC6B457587092'
clear_str = des_decrypt('1158CB77', test)
print ('test:', clear_str) #None
請前輩們指教一下...
VB 那邊的加密應該是採用 pad 補零的方式
PY 這邊可以把 padmode 改為 PAD_NORMAL
,並設定 pad 填補字元為 '\0'
這樣結果就和 VB 程式一樣了
def des_decrypt(secret_key, s):
iv = secret_key
k = des(secret_key, ECB, iv, pad='\0', padmode=PAD_NORMAL)
de = k.decrypt(binascii.a2b_hex(s))
return de
test='A755DDB424D77F7FBBDFC6B457587092'
clear_str = des_decrypt('1158CB77', test)
print ('test:', clear_str) # test: b'1114420095'
加密結果也是
def des_encrypt(secret_key, s):
iv = secret_key
k = des(secret_key, ECB, iv, pad='\0', padmode=PAD_NORMAL)
en = k.encrypt(s)
return binascii.b2a_hex(en)
secret_str = des_encrypt('1158CB77', '1114420095')
print ('密文:', secret_str) #b'a755ddb424d77f7fbbdfc6b457587092'
clear_str = des_decrypt('1158CB77', secret_str)
print ('明文:', clear_str) #b'1114420095'
現在想想其實有跡可循 ((馬後炮
在測試的過程中,我試過把 padmode 改成 None
結果為 b'1114420095\x00\x00\x00\x00\x00\x00'
由此可以推測 hexString A755DDB424D77F7FBBDFC6B457587092
加密前應該有經過補零的動作
所以解回來才會多了一些零
def des_decrypt(secret_key, s):
iv = secret_key
k = des(secret_key, ECB, iv, pad=None, padmode=None)
de = k.decrypt(binascii.a2b_hex(s))
return de
test='A755DDB424D77F7FBBDFC6B457587092'
clear_str = des_decrypt('1158CB77', test)
print ('test:', clear_str) # test: b'1114420095\x00\x00\x00\x00\x00\x00'
16進位:a7 55 dd b4 24 d7 7f 7f 6e 52 fb 9e 82 cc 89 7f
10進位:167 85 221 180 36 215 127 127 187 223 198 180 87 88 112 146
這樣看懂了嗎?
test='A755DDB424D77F7FBBDFC6B457587092'
test=b'a755ddb424d77f7f6e52fb9e82cc897f'
這兩個字串是不同的。
你用的套件有寫:
# For Python3, you'll need to use bytes, i.e.:
# data = b"Please encrypt my data"
# k = pyDes.des(b"DESCRYPT", pyDes.CBC, b"\0\0\0\0\0\0\0\0", pad=None, padmode=pyDes.PAD_PKCS5)
16進位:a7 55 dd b4 24 d7 7f 7f 6e 52 fb 9e 82 cc 89 7f
轉換不是這個嗎...
10進位:167 85 221 180 36 215 127 127 110 82 251 158 130 204 137 127
不好意思,真的不太懂樓主說的...
10進位:167 85 221 180 36 215 127 127 187 223 198 180 87 88 112 146
經過python加密後的密文是 :a755ddb424d77f7f6e52fb9e82cc897f
但是原始密文是 :A755DDB424D77F7FBBDFC6B457587092
求前輩指教...
ㄜ...果然不該在睡覺前看複雜的問題。
我用 PyCryptodome 加密的結果和 pyDes 一模一樣。
所以應該是出在 TransformFinalBlock 這個是不是有理解錯誤
感謝前輩的解答
不過小碼農米爾 Mir大大解出了我所需的資訊
提醒一下,IV 不應該固定(例如直接用 secreKey),一般 IV 都是亂數產生,然後跟密文一起發送出去。也就是 {IV: 初始向量, cipher: 密文}。
如果 IV固定的話,那麼相同的區塊會產生相同的密文,導致有可能被分析出一些資訊。
參考:初始向量
另外,塊鏈結模式有很多種,建議了解一下。各有優缺點,安全性也不同。
最後是 padding 的問題,雖然說這邊是 zero-padding 。但是 zero-padding 對於加密二進位資料時可能會無法判別原始資料長度。
Zero padding may not be reversible if the original file ends with one or more zero bytes, making it impossible to distinguish between plaintext data bytes and padding bytes.
我習慣是用 PKCS7。
除非是維護舊專案,已經有很多舊資料了,要把 VB 的程式碼改用 python 處理。
不然建議是用正確的方式加解密。(目前比較大的問題就是 IV 那邊)