oracle 这个字符串是 Base64 吗?我怎么知道使用的是什么编码?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4312492/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Is this string Base64? How can I tell what is the encoding used?
提问by Uphill_ What '1
This is a puzzle to me and I am really annoyed that I cannot solve it! So, if anyone has some free time I would like to here some suggestions on how to solve it!
这对我来说是一个难题,我真的很生气我无法解决它!所以,如果有人有空闲时间,我想在这里提供一些有关如何解决它的建议!
I use a software that stores the password in an oracle database. The password field is of type Varchar2(100 char). It seems to me that the software encodes the passwords and stores the encoded string in the database.
我使用将密码存储在 oracle 数据库中的软件。密码字段的类型为 Varchar2(100 char)。在我看来,该软件对密码进行编码并将编码后的字符串存储在数据库中。
My password is '1234' and the encoded string is 'cRDtpNCeBiql5KOQsKVyrA0sAiA='. All the passwords in the database are 28 characters long.
我的密码是“1234”,编码的字符串是“cRDtpNCeBiql5KOQsKVyrA0sAiA='。数据库中的所有密码都是 28 个字符长。
The puzzle that I have assigned to myself is to find the encoding and/or encryption of the string. My first check was on Base64
我给自己分配的难题是找到字符串的编码和/或加密。我的第一次检查是在 Base64 上
So here is my first test in python (idle):
所以这是我在 python 中的第一个测试(空闲):
>>> import base64
>>> encoded = 'cRDtpNCeBiql5KOQsKVyrA0sAiA='
>>> decoded = base64.b64decode(encoded)
>>> decoded
'q\x10\xed\xa4\xd0\x9e\x06*\xa5\xe4\xa3\x90\xb0\xa5r\xac\r,\x02 '
>>> print decoded
qí?О*????r?
,
,
Here is my second test:
这是我的第二个测试:
>>> myString = '1234'
>>> encoded = base64.b64encode(myString)
>>> encoded
'MTIzNA=='
>>> decoded = base64.b64decode('MTIzNA==')
>>> decoded
'1234'
So, my first thought is that this is not Base64 encoded. After I checked wikipedia (https://en.wikipedia.org/wiki/Base64) it seems that Base64 encoded strings are not of fixed size. My second thought is that the string was encrypted and then encoded into Base64 and that is why I get the weird-looking decoded string.
所以,我的第一个想法是这不是 Base64 编码的。在我检查维基百科(https://en.wikipedia.org/wiki/Base64)之后,似乎 Base64 编码的字符串不是固定大小的。我的第二个想法是该字符串被加密,然后编码为 Base64,这就是为什么我得到看起来很奇怪的解码字符串。
Any ideas?
有任何想法吗?
回答by kichik
It is actually Base64 encoded. However, it is not the password itself that is encoded, but its SHA-1 hash.
它实际上是 Base64 编码的。然而,被编码的不是密码本身,而是它的 SHA-1 哈希。
from sha import sha
print 'cRDtpNCeBiql5KOQsKVyrA0sAiA='.decode('base64').encode('hex')
print sha('1234').hexdigest()
or for newer versions of Python:
或者对于较新版本的 Python:
from hashlib import sha1
print 'cRDtpNCeBiql5KOQsKVyrA0sAiA='.decode('base64').encode('hex')
print sha1('1234').hexdigest()
Base64 encodes 3 bytes as 4 characters. As you have 27 characters with one padding, you can see that there are 20 encoded bytes (27*3/4
). When something security related is 20 bytes (or 160 bits) long, it's usually a SHA-1. When it's 16 bytes (128 bits), it's usually MD5.
Base64 将 3 个字节编码为 4 个字符。由于您有 27 个字符和一个填充,您可以看到有 20 个编码字节 ( 27*3/4
)。当与安全相关的内容长度为 20 字节(或 160 位)时,它通常是 SHA-1。当是 16 字节(128 位)时,通常是 MD5。
BTW, it's always a good idea to add random salt to the mix so two identical passwords wouldn't stick out in the database. On Linux, the crypt
module helps you with that and throws in a few more security measures.
顺便说一句,在混合中添加随机盐总是一个好主意,这样两个相同的密码就不会出现在数据库中。在 Linux 上,该crypt
模块可以帮助您解决这个问题,并提供更多安全措施。
Edit: to answer another comment - it's very easy to get the original from the "encrypted" password. There's a technique that got famous a few years back called Rainbow Tables. There are even online versionsof it. Just type in your hash in hex (7110eda4d09e062aa5e4a390b0a572ac0d2c0220
) and it'll give you 1234
in a second.
编辑:回答另一条评论-从“加密”密码中获取原件非常容易。有一种技术在几年前就很出名,叫做彩虹表。甚至还有它的在线版本。只需在十六进制 ( 7110eda4d09e062aa5e4a390b0a572ac0d2c0220
) 中输入您的哈希值,它就会1234
在一秒钟内给您。
回答by Micha? Niklas
While len(decoded) = 20
then I guess that this is Base64 encoded SHA1 hash.
虽然len(decoded) = 20
那么我想,这是Base64编码的SHA1哈希。
You can create such coded passwords by:
您可以通过以下方式创建此类编码密码:
import hashlib
import base64
passwd = '1234'
hp = base64.b64encode(hashlib.sha1(passwd).digest())
print hp
print len(hp)
As for such storing passwords: it is not very good while many crackers can use "rainbow" tables with precomputed MD5, SHA1 and other hashes and they can get password based on such hash. To prevent it "salt" should be used: hash(salt+passwd)
, such salt can be random string saved in database per user or for example user login (something that never can be changed).
至于这样的存储密码:不太好,很多破解者可以使用预先计算好的MD5、SHA1等哈希值的“彩虹”表,根据这样的哈希值获取密码。为了防止它,应该使用“盐”:hash(salt+passwd)
这样的盐可以是每个用户保存在数据库中的随机字符串,或者例如用户登录(永远不能改变的东西)。