2011-08-17 28 views
8

Estoy intentando comprender algún código de C#, me han entregado, que trata de la criptografía, y utiliza específicamente PasswordDeriveBytes de System.Security.Cryptography..NET: Diferencia entre PasswordDeriveBytes y Rfc2898DeriveBytes

En el .NET docs, se dice que PasswordDeriveBytes utiliza "una extensión del algoritmo PBKDF1", que es más tarde en el documento especificado como "el estándar PKCS # 5 v2.0", que es PBKDF2 (por lo que yo puedo decir) En todas partes en la red que he encontrado (incluso aquí en Stack Exchange), todos dicen "use Rfc2898DeriveBytes, porque Password * está en desuso y usa PBKDF1". Pero la única diferencia en los documentos en msdn.microsoft.com parece ser que la versión Rfc * menciona específicamente PBKDF2, donde Password * dice "extensión de PBKDF1" y "PKCS # 5 v 2.0".

Entonces, ¿alguien me puede decir cuál es la diferencia entre las dos clases (si corresponde) y por qué debería usar una en lugar de la otra para la derivación de la clave de contraseña PBKDF2?

Ahora, otro código, que trata con los mismos datos, utiliza explícitamente PBKDF2, y funciona, por lo que sugeriría que de hecho PasswordDeriveBytes también usa PBKDF2, o que PBKDF2 es simplemente compatible con PBKDF1 bajo ciertas circunstancias, pero quiero Sé con certeza que no es un efecto secundario de algo aleatorio, y que las cosas simplemente funcionan mágicamente (y eventualmente se romperán mágica y espectacularmente) sin que nadie realmente entienda por qué.

Respuesta

0

PKCS#5 v2.0 define tanto PBKDF1 y PBKDF2, el primero por razones de compatibilidad con versiones anteriores y también recomienda que utilice PBKDF2 para nuevas aplicaciones. No tengo idea de por qué este último es mejor que el anterior, pero las dos clases .NET parecen usar algoritmos diferentes pero interoperables. (. Posiblemente porque sólo la clave resultante se intercambia, no las entradas + KDF)

+0

Así que, como se sospecha, las cosas funcionan principalmente por casualidad, y no tanto por diseño ... – adamski

+0

No necesariamente, aún podría incluir qué esquema de cifrado/KDF es utilizado por los datos de salida y el "otro código" que la mención es una ruta de código utilizada después de que se haya determinado que el esquema de cifrado utiliza PBKDF2. Realmente no puedo decir "explícitamente usa PBKDF2". – millimoose

1

Aquí hay un post detallando las diferencias:

http://blogs.msdn.com/b/shawnfa/archive/2004/04/14/generating-a-key-from-a-password.aspx

PBKDF2 se pueden utilizar para generar las claves de cualquier longitud, que es muy útil para el cifrado basado en contraseña (puede generar cualquier longitud de clave según lo requiera el cifrado simétrico) pero significa menos para el almacenamiento seguro de contraseñas. También aplica la sal usando HMAC en lugar de concatenación como PBKDF1, que tiene mejores propiedades de seguridad en casos de sales débiles.

+0

Sí, no estaba preguntando sobre la diferencia entre 1 y 2, sino la diferencia entre dos clases .NET particulares. :) – adamski

+0

Uno de los cuales implementa 1, mientras que el otro implementa 2 :) – orip

+1

¿Qué son las "Extensiones"? – adamski

1

creo una gran respuesta a esto se encuentra aquí:

C# PasswordDeriveBytes Confusion

Pero a sumup:

implementación de PKCS original # 5 (también conocido como PBKDF1) de Microsoft incluye extensiones inseguras para proporcionar más bytes que la función hash puede proporcionar (ver informes de errores aquí y aquí).

Incluso si no se Buggy debe evitar indocumentados, extensiones propietarias a las normas (o puede que nunca sea capaz de descifrar los datos en el futuro. - al menos no fuera de Windows)

Os recomiendo a utilice el Rfc2898DeriveBytes más nuevo que implementa PBKDF2 (PKCS # 5 v2) que está disponible desde .NET 2.0.

1

Si usted instancia PasswordDeriveBytes y hacer una sola llamada al método GetBytes pasando un valor que es menor que el tamaño de salida del algoritmo de digerir que subyace entonces a volver un valor del algoritmo PBKDF1.

Si realiza dos llamadas a GetBytes para el mismo objeto, puede encontrar un error de conteo en la implementación.

PBKDF1 solo se describe para producir hasta el tamaño del algoritmo hash (por ejemplo, 20 bytes para SHA-1), pero la clase PasswordDeriveBytes ha creado una fórmula para admitir hasta 1000 veces el tamaño de salida hash. Por lo tanto, un gran valor producido por esta clase puede no ser fácilmente alcanzable en otra plataforma.


Si usted instancia Rfc2898DeriveBytes se obtiene una aplicación de streaming del algoritmo PBKDF2. La diferencia más obvia de PBKDF2 sobre PBKDF1 es que PBKDF2 permite la generación de una cantidad arbitraria de datos (el límite es (2^32-1)*hashOutputSize, o para SHA-1 85,899,345,900 bytes). PBKDF2 también utiliza una construcción más compleja (en particular, HMAC sobre digest directo) para hacer que la recuperación de la contraseña de entrada de un valor de salida sea más difícil.

La "transmisión" en la implementación es que la concatenación de GetBytes(5) y GetBytes(3) es la misma que GetBytes(8). A diferencia de PasswordDeriveBytes, esto funciona correctamente en Rfc2898DeriveBytes.


PBKDF1 fue creado originalmente para generar claves DES, publicado en PKCS #5 v1.5 en 1993. PBKDF2 fue publicado en PKCS # 5 v2.0 (que fue republicada como RFC2898) en 1999. Una cubierta de cremallera que debe ser encontrado al ftp://ftp.rsasecurity.com/pub/pkcs/pkcs-5v2/pkcs5v2-0.pdf (pero parece tener problemas para que ftp://ftp.dfn-cert.de/pub/pca/docs/PKCS/ftp.rsa.com/99workshop/pkcs5_v2.0.ppt tenga que hacer) resume aún más las diferencias. (El panel de diapositivas fue escrito por RSA Security, los creadores de PBKDF1 y PBKDF2, y son las personas que recomiendan PBKDF2 sobre PBKDF1).

Cuestiones relacionadas