Siempre he usado una cadena de sal por entrada adecuada al cifrar las contraseñas para el almacenamiento de la base de datos. Para mis necesidades, almacenar la sal en la base de datos junto a la contraseña hash siempre ha funcionado bien.
Sin embargo, algunas personas recomiendan que la sal se almacene por separado de la base de datos. Su argumento es que si la base de datos se ve comprometida, un atacante aún puede construir una tabla de arco iris teniendo en cuenta una cadena de sal particular para descifrar una cuenta a la vez. Si esta cuenta tiene privilegios de administrador, es posible que ni siquiera necesite descifrar ninguna otra.
Desde una perspectiva de seguridad, ¿vale la pena almacenar sales en un lugar diferente? Considere una aplicación web con el código del servidor y la base de datos en la misma máquina. Si las sales se almacenan en un archivo plano en esa máquina, lo más probable es que si la base de datos se ve comprometida, el archivo de sales también lo estará.
¿Hay alguna solución recomendada para esto?
fuente
Respuestas:
El objetivo de las tablas de arco iris es que se crean de antemano y se distribuyen en masa para ahorrar tiempo de cálculo para los demás: se tarda tanto tiempo en generar tablas de arco iris sobre la marcha como simplemente descifrar la combinación de contraseña + sal directamente (ya que efectivamente, lo que se está haciendo al generar tablas de arco iris es ejecutar previamente los cálculos para forzar el hash), por lo que el argumento de que al conocer la sal alguien podría "generar una tabla de arco iris" es falso.
No tiene sentido almacenar las sales en un archivo separado siempre que sean por usuario: el objetivo de la sal es simplemente hacerlo para que una tabla de arco iris no pueda romper todas las contraseñas en la base de datos.
fuente
Proporcionaré una versión ligeramente diferente de esto.
Siempre guardo la sal mezclada con el hash de contraseña salada.
Por ejemplo, colocaré la primera mitad de la sal antes del hash salado de la contraseña, y la última mitad de la sal después del hash salado de la contraseña. La aplicación conoce este diseño, por lo que puede obtener estos datos y obtener el hash de sal y contraseña salada.
Mi razonamiento para este enfoque:
Si los datos de contraseña / hash se ven comprometidos y caen en manos de un atacante, el atacante no sabrá cuál es la sal de mirar los datos. De esta manera, un atacante prácticamente no puede realizar un ataque de fuerza bruta para obtener una contraseña que coincida con el hash, ya que no conoce el hash para empezar y no tiene forma de saber qué partes de los datos son partes de la sal, o partes del hash de contraseña salada (a menos que él conozca la lógica de autenticación de su aplicación ).
Si el hash de contraseña salada se almacena tal cual, entonces se puede realizar un ataque de fuerza bruta para obtener una contraseña que cuando se salada y hash produce los mismos datos que el hash de contraseña salada.
Sin embargo, por ejemplo, incluso si el hash de la contraseña salada se almacenó tal cual, pero se colocó previamente con un solo byte aleatorio, siempre que el atacante no sepa que este primer byte debe descartarse, esto también aumentaría la dificultad de ataque Su aplicación debería descartar el primer byte de los datos cuando se utiliza para autenticar a su usuario.
La conclusión de esto ...
1) Nunca almacene los datos que utiliza su aplicación de autenticación en su forma exacta.
2) Si es posible, mantenga su lógica de autenticación en secreto para mayor seguridad.
Ve un paso más allá ...
Si no puede mantener en secreto la lógica de autenticación de su aplicación, mucha gente sabe cómo se almacenan sus datos en la base de datos. Y suponga que ha decidido almacenar el hash de contraseña salada mezclado junto con la sal, con algo de sal que antecede al hash de contraseña salada, y el resto de la sal añadiéndola.
Al generar la sal al azar, también puede decidir al azar qué proporción de su sal almacenará antes / después del hash de contraseña salada.
Por ejemplo, genera una sal aleatoria de 512 bytes. Agregue la sal a su contraseña y obtenga el hash SHA-512 de su contraseña salada. También genera un número entero aleatorio 200. Luego almacena los primeros 200 bytes de la sal, seguidos del hash de la contraseña salada, seguido del resto de la sal.
Al autenticar la entrada de contraseña de un usuario, su aplicación pasará la cadena y asumirá que el primer 1 byte de los datos es el primer 1 byte de la sal, seguido del hash salado. Este pase fallará. La aplicación continuará utilizando los primeros 2 bytes de los datos como los primeros 2 bytes de la sal, y se repetirá hasta que se encuentre un resultado positivo después de usar los primeros 200 bytes como los primeros 200 bytes de la sal. Si la contraseña es incorrecta, la aplicación continuará probando todas las permutaciones hasta que no se encuentre ninguna.
Los pros de este enfoque:
Mayor seguridad: incluso si se conoce su lógica de autenticación, se desconoce la lógica exacta en tiempo de compilación. Es prácticamente imposible realizar un ataque de fuerza bruta, incluso con el conocimiento de la lógica exacta. El aumento de la longitud de la sal aumentará aún más la seguridad.
Los contras de este enfoque:
Dado que la lógica exacta se infiere en tiempo de ejecución, este enfoque requiere mucha CPU. Cuanto más larga sea la sal, más intensivo será este enfoque.
La autenticación de contraseñas incorrectas implicará el mayor costo de CPU. Esto puede ser contraproducente para solicitudes legítimas, pero aumenta la seguridad contra los atacantes.
Este enfoque se puede implementar de varias maneras y se puede hacer aún más seguro mediante el uso de sales de ancho variable y / o hashes de contraseña salada.
fuente
A menudo, se anteponen al hash y se almacenan en el mismo campo.
No es necesario almacenarlos por separado: el punto es usar una sal aleatoria para cada contraseña para que una sola tabla de arco iris no se pueda usar contra todo el conjunto de hashes de contraseñas. Con sales aleatorias, un atacante debe aplicar fuerza bruta a cada hash por separado (o calcular una tabla de arcoíris para todas las sales posibles, mucho más trabajo).
Si tuviera una ubicación de almacenamiento más segura, tendría sentido simplemente almacenar los hash allí.
fuente
Basado en el libro de desarrollo de aplicaciones web ASP.NET MVC 4 de William Penberthy:
fuente
El objetivo de una sal es hacer que todas las tablas del arco iris sean inútiles y requieren que se haga un nuevo conjunto de ellas. Se tarda tanto en adivinar una cuerda como en hacer una mesa arcoiris. Por ejemplo, el hash SHA-256 de "contraseña" es
5e88 4898 da28 0471 51d0 e56f 8dc6 2927 7360 3d0d 6aab bdd6 2a11 ef72 1d15 42d8
. Después de agregar una sal, como "badpassword", la nueva cadena que se va a codificar es "passwordbadpassword" que, debido al efecto de avalancha, cambia drásticamente la salida a457b f8b5 37f1 802e f9c8 2e46 b8d3 f8b5 721b 7cbb d485 f0bb e523 bfbe 73e6 58d6
.Normalmente, la sal solo se almacena en la misma base de datos que la contraseña, también porque si una base de datos está pirateada, es probable que la otra también lo esté.
fuente