kennytmのコメントに基づいて、私はRandom
を「中断する」という概念の証明を作成しました。エッジの周りは少し粗いかもしれませんが、次のもの(およびその後のすべての値)を予測するために必要な値は55個だけです。 【この記事(https://jazzy.id.au/2010にコメントで
public class Program
{
static void Main(string[] args)
{
const int INTERNAL_ARRAY_SIZE = 56;
const int INEXTP_START = 21;
var internalArray = new int[INTERNAL_ARRAY_SIZE];
var random = new Random();
// Read 56 values.
for (int x = 0; x < INTERNAL_ARRAY_SIZE - 1; x++)
{
internalArray[x + 1] = random.Next();
}
int inext = INTERNAL_ARRAY_SIZE - 1;
int inextp = INEXTP_START;
// Predict the next 10 values.
for (int x = 0; x < 10; x++)
{
int predictedRandomValue = PredictNextRandomValue(internalArray, ref inext, ref inextp);
int officialRandomValue = random.Next();
if (officialRandomValue == predictedRandomValue)
{
Console.WriteLine("Yes, they're the same.");
}
else
{
Console.WriteLine("No, they're different.");
}
}
}
private static int PredictNextRandomValue(int[] seedArray, ref int inext, ref int inextp)
{
const int MBIG = int.MaxValue;
int retVal;
int locINext = inext;
int locINextp = inextp;
if (++locINext >= 56) locINext = 1;
if (++locINextp >= 56) locINextp = 1;
retVal = seedArray[locINext] - seedArray[locINextp];
if (retVal == MBIG) retVal--;
if (retVal < 0) retVal += MBIG;
seedArray[locINext] = retVal;
inext = locINext;
inextp = locINextp;
return retVal;
}
}
:
次のコードは、最初の単一
Random
インスタンスから55個の値を読み出した後、次の10の値を予測します/09/22/cracking_random_number_generators_part_3.html)誰かが 'System.Random'を攻撃するために議論した概念を使って議論します。 –元の質問についてはわかりませんが、いずれのスレッドでも一様な分布が保証されていないように見えます。このRNGを使用するアプリケーションがマルチスレッド(例えばウェブサーバ)であり、アクセストークンを生成するために一度に1つのスレッドを使用すると仮定すると、これは実際には問題である可能性が高い。予測可能性にかかわらず、それは私には安全ではないようです(しかし、私は間違いなくセキュリティや暗号の専門家ではありません)。 –
私は57の値を観察することは残りのものを予測するのに十分だと思いますhttp://referencesource.microsoft.com/#mscorlib/system/random.cs,100。 – kennytm