¿Qué tan seguro es este plan de cifrado?

0

Estoy tratando de encontrar una buena manera de almacenar los datos encriptados de un usuario de tal manera que solo el usuario pueda acceder a ellos.

Tengo una clave maestra ubicada fuera de la raíz web, llamada $serverKey . Y cuando un usuario inicia sesión, puse otro lado clave del cliente con sessionStorage.setItem() . El $clientKey lo establece sha256 de su contraseña de texto sin formato (que, por supuesto, no se almacena en ningún lado). Cuando el usuario envía datos, uso openssl_encrypt() con $serverKey.$clientKey y los almaceno en mi base de datos.

Mi objetivo es que, para piratear los datos del usuario, tenga que obtener la clave maestra y la clave del cliente. ¿Cuáles son los agujeros en este plan? Me doy cuenta de que cambiar y olvidar las contraseñas causa problemas, pero ahora lo ignoro.

    
pregunta twharmon 25.08.2016 - 23:33
fuente

2 respuestas

1
  

de tal manera que solo el usuario pueda acceder a él.

No tiene sentido cifrar los datos que debe operar el servidor (a menos que esté explotando la maleabilidad). Los sistemas criptográficos completamente homomórficos son inviables ahora y no están tan bien estudiados, por lo que no es factible proteger los datos del usuario de una parte privilegiada.

Supongamos que intenta mitigar un ataque fuera de línea, cuando un adversario obtiene un volcado de la base de datos del servidor con los datos del usuario e intenta descifrarlo sin el conocimiento de las contraseñas del usuario. El adversario no puede modificar el código que se ejecuta en el servidor y no puede monitorear los datos que el servidor obtiene / da de / a otros usuarios.

Usas SHA-256 de los datos que tienen poca entropía, lo que significa que es fácil hacer un diccionario de fuerza bruta. Así que mi primer consejo es reemplazar el SHA-256 con algunos KDF (funciones hash intencionalmente resistentes a la fuerza bruta al costo del tiempo de ejecución y la memoria), por ejemplo, Detener KDF , y tener sal personal para cada usuario.

Cambiar las contraseñas no es un problema porque puedes volver a cifrar los datos.

    
respondido por el KOLANICH 26.08.2016 - 00:35
fuente
0

Dividamos esto en dos:

Encriptando los datos del usuario con su contraseña

Claro, por qué no, si los datos son privados. En la práctica, el servidor necesitará manejarlo en texto sin formato, pero los datos pueden dejarse encriptados mientras el usuario no haya iniciado sesión. Aunque en un foro de mensajes, los mensajes que deben ser leídos por otros usuarios no pueden estar sujetos a este tratamiento, por lo que prácticamente solo funciona para mensajes privados (dirigidos a un solo usuario o un grupo conocido de usuarios).

Como siempre, no desea usar ninguna contraseña directamente como clave, sino ejecutarla a través de alguna función de derivación de claves como PBKDF2 . Esto ralentizará la búsqueda de la contraseña por fuerza bruta y dará la posibilidad de generar claves más largas que la contraseña (en caso de que sea necesario).

En cuanto a los cambios de contraseña, la práctica habitual es generar una clave segura aleatoria, utilizada para cifrar los datos, y luego almacenar esta clave cifrada con (una clave basada en) la contraseña del usuario. De esta manera, cambiar la contraseña solo requiere volver a cifrar la clave maestra, no todos los datos.

Aunque el inconveniente aquí siempre es que si el servidor está comprometido, puede configurarse para guardar la contraseña del usuario en texto sin formato la próxima vez que inicie sesión, o simplemente guardar todos los datos sin cifrar.

Encriptando todos los datos con la clave del servidor

Aquí, me pregunto cuál es la amenaza esperada? ¿Un ataque de software que pierde toda la información (encriptada) o que el hardware del servidor se pierde? La protección contra el hardware fuera de lugar requeriría el cifrado de los datos con una clave que no se encuentra en el propio sistema , sino que tal vez se ingrese manualmente. La forma más sencilla de hacerlo sería utilizar alguna solución de cifrado de disco completo.

En cuanto a un ataque que de alguna manera filtra todos los datos, pero no permite que se modifique el código, seguro, el cifrado con una clave de servidor fija debería ayudar. Pero, ¿necesita hacerlo si los datos ya están cifrados con la clave del usuario? ¿Qué tan factible es que los datos encriptados se filtren pero no la clave del servidor, dado que el servidor va a necesitar esa clave para casi todas las operaciones relacionadas con los datos? Tengo que decir que no lo sé.

(Si está pensando en inyecciones SQL, corrija mejor sus prácticas en eso donde está el problema. Por otra parte, si está pensando en una vulnerabilidad que conduce a la ejecución de código arbitrario, el atacante acaba de obtener la clave del servidor , también.)

Combinando los dos

La forma obvia de combinar dos claves sería cifrar los datos dos veces, utilizando ambas claves, de modo que los datos almacenados sean C = E (K2, (E (K1, P)). Esto es lo que sucedería en el finalice si almacena datos encriptados en una unidad encriptada, pero es un desperdicio o trabajo.

Otra forma sería derivar la clave de cifrado real de las dos claves (servidor y usuario) utilizando un KDF (nuevamente). Aunque con entradas de apariencia aleatoria, creo que podría salirse con la combinación de dos claves de longitud fija con un hash fuerte como SHA-256, por lo que C = E (H (K1, K2), P).

    
respondido por el ilkkachu 26.08.2016 - 14:29
fuente

Lea otras preguntas en las etiquetas