找出随机数生成器在C ++中播种的内容

时间:2009-08-27 19:30:17

标签: c++ random unmanaged srand

我有一个非托管的c ++控制台应用程序,我正在使用srand()和rand()。我不需要这个来解决一个特定的问题,但很奇怪:原始种子传递给srand()存储在内存中我可以查询的地方吗?有没有办法弄清楚种子是什么?

4 个答案:

答案 0 :(得分:7)

不需要存储种子,只返回最后一个随机数。

以下是联机帮助页中的示例:

       static unsigned long next = 1;

       /* RAND_MAX assumed to be 32767 */
       int myrand(void) {
           next = next * 1103515245 + 12345;
           return((unsigned)(next/65536) % 32768);
       }

       void mysrand(unsigned seed) {
           next = seed;
       }

答案 1 :(得分:3)

如果你有一个简单的线性同余生成器,你有几个值,这就产生了一个方程组:

 v1 = ( seed * a + b ) % m
 v2 = (   v1 * a + b ) % m;
 v3 = (   v2 * a + b ) % m;
... 

如果你知道第一个值,你可以按顺序倒退:

seed = (v1 - b)/a (mod m)

你不知道种子唯一,你只知道mod m(通常很好,因为(0 <种子&lt; m)反正)如果v1 - b是负的你需要加m直到它再次为正

您也可以查看Chinese Remainder Theorem,但不是完全匹配。

答案 2 :(得分:0)

理论上,不是 - 种子值用于计算下一个随机值,并且该值(理论上)用于播种下一个随机数,依此类推。

安全方面,能够窥视种子(无论是原始的还是新的)是一个严重的安全问题所以我希望你不应该看到它,即使它必须存储在某个地方。

答案 3 :(得分:0)

我不知道您的装配熟练程度是什么,或者您是否可以访问非托管应用程序的源代码/调试符号,但除了那种欺骗之外,没有可行的方法来确定原始版本种子价值。随机数生成器的整个要点是提出一种方法来为您提供不可预测的数字 - 任何两个给定的rand()调用之间的关系都不应该是可以推断的。在密码强的伪随机数生成器中,根据生成的随机数猜测种子将被认为是一个严重的缺陷。

最简单的方法是在调试器下启动应用程序并设置一个调用srand()的断点 - 然后查看传递的参数。

接下来是反汇编应用程序并找出srand调用的情况。它完全有可能用当前时间播种 - 然后你可以尝试一堆猜测(你可以将它缩小到几千左右)并查看是否有任何给出应用程序使用的相同序列的随机数字。 (当然,这假设您有一些方法可以知道生成的随机值是什么)。也有可能种子总是像'0'一样愚蠢。