2009-01-04 18 views
6

Actualmente estoy escribiendo un generador de contraseñas simple (C#). Para eso necesito algunos números al azar.¿Qué tan aleatorio es System.Random en .NET 3?

¿Está bien simplemente usar la clase Random que se envía con .NET o hay algún problema conocido con eso?

+0

Un poco de tema, pero esta es una buena historia de lo equivocado que puede pasar cuando no se tienen buenos generadores aleatorios .. http://www.cigital.com/papers/download/developer_gambling.php – StefanE

Respuesta

13

No tiene nada de malo, es lo suficientemente bueno para generar contraseñas simples. Un ejemplo sencillo (source):

Random RandomClass = new Random(); 
int RandomNumber = RandomClass.Next(); // Random number between 1 and 2147483647 
double RandomNumber = RandomClass.Next(1,10); // Random number between 1 and 10 

double RandomDouble = RandomClass.NextDouble(); // Random double between 0.0 and 1.0 

El artículo How To: Generate a Random Password (C#/VB.NET) tiene un ejemplo muy amplia de generar buena, fácil de leer contraseñas con la complejidad especificada. Puede ser excesivo para usted, pero podría proporcionar una buena fuente para copiar ideas.


Si necesita algo más para la criptografía, hay otro espacio de nombres para que:

System.Security.Cryptography 

En concreto, puede utilizar esto:

System.Security.Cryptography.RNGCryptoServiceProvider.GetBytes(yourByte) 

Un ejemplo es Using Crypto for your Random Numbers in VB.NET y otro es Crypto Random Numbers.

Si usted está pensando en rodar su propia, el sitio Developer Guidance Share tiene alguna información para hablar de ella.

+1

Usando 'System.Random 'generar contraseñas nunca está bien. – CodesInChaos

1

Si buscas algunos detalles sobre cómo hacer que System.Random trabaje para ti, este artículo CodeBetter merece la pena leerlo. Ofrece una buena visión general de lo que está haciendo la función aleatoria y cómo hacerla "más aleatoria" usando un GUID hash como semilla. Si solo necesitas generar contraseñas iniciales aleatorias para las cuentas de usuario (supongo que aquí), entonces esto debería ser más que suficiente, las herramientas de criptografía probablemente serían exageradas en este caso.

+1

@Glenn Slaven: es un gran artículo, ¡pero no se trata de hacer que Syste.Random sea "más aleatorio"! Se trata de una solución para llamar al constructor Random con una semilla de tiempo cuando se ha escapado muy poco tiempo (como en un ciclo cerrado). –

+2

Hay varias historias informáticas sobre programadores que pensaban que podían hacer que un generador de Núm. Aleatorio fuera "más aleatorio" haciendo "cosas" al resultado, y rompiendo por completo su psuedo-aleatoriedad. –

10

System.Random es no como fuente "criptográficamente fuerte" de aleatoriedad. El resultado de la función Random es completamente predecible, suponiendo que el atacante conoce (o puede adivinar) el valor de "semilla" que se utilizó para crear el System.Random. Si simplemente llama a System.Random() nuevo, ese valor inicial es simplemente una representación de la hora actual del sistema (algo que un atacante a menudo puede adivinar fácilmente).

Incluso si la hora inicial no se conoce exactamente, un atacante puede verificar todos los valores potenciales en un rango de tiempo dado por fuerza bruta.

Los generadores aleatorios en el espacio de nombres System.Security.Cryptography están diseñados para su uso en este tipo de situaciones y obtienen su imprevisibilidad de una cantidad de fuentes mucho más seguras.

0

¡Hay un RFC para todo! - Randomness Requirements for Security (RFC 4086).

También puede gastar grandes cantidades de dinero en hardware para crear una semilla aleatoria. Creo que un Geiger counter es el estándar para soluciones profesionales. La mayoría de los sitios de póquer usan esto hoy en día.