我的alg密码分析

2024-04-25 09:28:37 发布

您现在位置:Python中文网/ 问答频道 /正文

import string,random,platform,os,sys
def rPass():
    sent =  os.urandom(random.randrange(900,7899))
    print sent,"\n"
    intsent=0
    for i in sent:
        intsent += ord(i)
    print intsent
    intset=0
rPass()

我需要帮助计算出这个算法的字节码部分可能的总输出。不要担心for循环和ord的东西,那是为了下线。-新手密码员出来了。在


Tags: importforstringosdefsysrandomurandom
1条回答
网友
1楼 · 发布于 2024-04-25 09:28:37

我不必担心循环和ord的东西,所以让我们把它扔掉,看看其余的。在

另外,我不明白“我需要帮助计算出这个算法的unicode部分可能的总输出”,因为该算法没有unicode部分,或者实际上在代码中的任何地方都没有unicode部分。但我可以帮你计算出整个事件的总可能产出。我们将逐步简化它。在

第一个:

li=[]
for a in range(900,7899):
    li.append(a)

这完全等同于:

^{pr2}$

同时:

li[random.randint(0,7000)]

因为li正好是6999个元素的长度,这与random.choice(li)完全相同。在

把最后两个放在一起,这意味着它相当于:

random.choice(range(900,7899))

…相当于:

random.randrange(900,7899)

等等,那random.shuffle(li, random.random)呢?好吧(忽略了random.random已经是第二个参数的默认值),这个选择已经是随机的,但不是加密的,添加另一个洗牌并不能改变这一点。如果有人试图用数学方法预测你的RNG,用同样的RNG再加一次简单的洗牌不会使预测变得更困难(同时基于结果添加更多的工作可能会使定时攻击更容易)。在

事实上,即使您使用li的一个子集而不是全部,也不可能使您的代码更加不可预测。你将有一个小范围的价值观暴力通过,没有任何好处。在

所以,你要做的就是:

sent = os.urandom(random.randrange(900, 7899))

可能的输出是:900到7899字节之间的任何字节字符串。在

长度是随机的,并且大致均匀分布,但它不是随机的,在密码不可预知的意义上。幸运的是,这不太重要,因为攻击者可以看到他正在处理的字节数,而不必预测它。在

内容是随机的,既有均匀分布的,也有密码不可预测的,至少在系统的urandom的程度上是这样的。在

关于这件事只能这么说。在

然而,事实上,你让阅读、写作、维护和思考变得更加困难,这给你带来了一个很大的劣势,对你的攻击者没有任何补偿的劣势。在

所以,只需要使用一个衬垫。在


我想在接下来的问题中,你会问900-7898字节的随机数据有多少个可能的值。在

那么,900字节有多少个值?256**900。901要多少?256**901。所以,答案是:

sum(256**i for i in range(900, 7899))

…大约是2**63184,或者10**19020。在

所以,63184位的安全措施听起来相当不错,对吧?可能没有。如果你的算法没有缺陷的话,100位比你需要的还要多。当然,这是你的算法的一个缺陷,因为它是盲目的。在

另外,请记住,加密的全部要点是你希望破解比合法解密慢2**N,对于一些大的N。因此,使合法解密慢得多会使你的方案更糟糕。这就是为什么每个实际工作的加密方案都使用几百位的密钥、salt等(是的,公钥加密对其密钥使用数1000位,但这是因为它的密钥不是随机分布的。一般来说,使用这些密钥所做的一切都是为了加密随机生成的几百位的会话/文档密钥。)


最后一件事:我知道你说过要忽略ord,但是

首先,您可以将整个部分写成intsent=sum(bytearray(sent))。在

但是,更重要的是,如果你对这个缓冲区所做的一切都是求和的话,那么你使用了大量的熵来生成一个熵小得多的单个数字。(这一点你一想就应该很明显了。如果有两个独立的字节,则有65536种可能;如果将它们相加,则有只有512。)

另外,通过生成几千个单字节随机数并将它们相加,基本上是正态分布或高斯分布的非常接近的近似值。(如果你是一个D&D玩家,想想看3D6给出10和11的频率比3和18要多……而且3D6比2D6更准确……然后考虑6000D6。)但是,通过使字节数从900到7899,你就可以把它拉平,使之成为从700*127.5到7899*127.5的均匀分布。不管怎样,如果你能描述你想要得到的分布,你很可能可以直接生成它,而不会浪费所有的铀熵和计算。在

值得注意的是,很少有加密应用程序可以利用这么多的熵。即使是像生成SSL证书这样的操作也使用128-1024位的顺序,而不是64K位。在


你说:

trying to kill the password.

如果你试图加密一个密码以便它可以,比如说,存储在磁盘上或通过网络发送,这几乎总是错误的方法。您希望使用某种密码的零知识证明存储散列,或者使用质询响应而不是发送数据等。如果您想构建“保持登录功能”,请通过实际让用户登录来实现这一点(创建并存储会话身份验证令牌,而不是存储密码)。请参阅Wikipedia文章password了解基本信息。在

有时,您需要加密和存储密码。例如,也许你正在为用户构建一个“密码锁”程序来存储一堆密码。或者是一个设计糟糕的服务器(或者70年代设计的协议)的客户机。或者别的什么。如果您需要这样做,您需要一个相对较小的密钥的一层加密(请记住,一个典型的密码本身只有大约256位长,实际信息少于64位,因此使用一个密钥数千倍的时间绝对没有任何好处)。使其更安全的唯一方法是使用更好的算法,但实际上,加密算法几乎永远不会是最好的攻击面(除非您自己尝试过设计);将您的精力放在基础设施最薄弱的区域,而不是最强的区域。在


你会问:

Also is urandom's output codependent on the assembler it's working with?

好吧…没有它工作的汇编程序,我想不出其他任何你可以参考的有意义的东西。在

urandom所依赖的只是操作系统的熵池和PRNG。正如the docs所说,urandom只读取/dev/urandom(Unix)或调用CryptGenRandom(Windows)。在

如果您想知道它在您的系统上是如何工作的,man urandom或者在MSDN中查找{}。但是所有主要的操作系统都能产生足够的熵,并能很好地混合,所以你基本上不必担心这个问题。实际上,它们都有一些有效的熵池,一些加密安全的PRNG来“扩展”这个池,以及一些内核设备(linux、Windows)或用户空间守护程序(osx),它们可以从不可预知的事情(如用户操作)中收集熵,并将其混合到池中。在

那么,这依赖于什么呢?假设你没有任何应用程序浪费大量的信息量,你的机器没有被破坏,你的操作系统也没有重大的安全缺陷……它基本上不依赖任何东西。或者,换言之,它取决于这三个假设。在

引用linux man page/dev/urandom对于“除了长期存在的GPG/SSL/SSH密钥之外的所有内容”来说已经足够了。(在许多系统上,如果有人试图运行一个程序,像您的代码一样,读取数千字节的urandom,或者试图杀死熵种子守护进程,或者其他什么,它都会被记录下来,希望用户/系统管理员可以处理它。)


hmmmm python goes through an interpreter of its own so i'm not sure how that plays in

显然,在syscall前后调用urandom(8)/dev/urandom读取8个字节比在C问题中做的要多但是实际的系统调用是一样的。因此urandom设备甚至无法分辨两者之间的区别。在

but I'm simply asking if urandom will produce different results on a different architecture.

嗯,是的,很明显。例如,Linux和osx使用完全不同的CSPRNGs和不同的累积熵的方法。但关键是,即使是在同一台机器上,或者在同一台机器上的不同时间,它也应该是不同的。只要它在每个平台上都能产生“足够好”的结果,这就是一切。在

For instance would a processor\assembler\interpreter cause a fingerprint specific to said architecture, which is within reason stochastically predictable?

如上所述,解释器最终会进行与编译代码相同的系统调用。在

至于一个汇编程序…可能没有任何汇编程序涉及任何地方。Python解释器、随机设备、熵收集服务或驱动程序等的相关部分很可能是用C编写的。即使它们是在汇编中手工编码的,汇编中编码的全部要点是几乎可以直接控制生成的机器代码,所以不同的汇编程序不会有任何区别。在

在某种意义上,处理器可能会留下“指纹”。例如,我敢打赌,如果你知道RNG算法,并直接控制它的状态,你就可以编写代码,根据时间来区分x86和x86_64,甚至可能是i7的一代与另一代。但我不知道那对你有什么好处。算法仍然会从相同的状态生成相同的结果。而针对RNGs的实际攻击是攻击算法、熵累加器和/或熵估计器。在

不管怎样,我愿意赌一大笔钱,你依靠urandom比依靠你自己想出的任何东西更安全。如果您需要更好的(但您没有),请实现或者,更好的是找到一个经过良好测试的-FortunaBBS的实现,或者购买一个硬件熵产生设备。在

相关问题 更多 >