viernes, 17 de agosto de 2018

Ataques Web - Exposición de datos sensibles

Muchas aplicaciones Web no protegen adecuadamente los datos sensibles, tales como números de tarjeta de crédito o credenciales de autenticación. Los atacantes pueden robar o modificar tales datos para llevar a cabo fraudes, robos de identidad u otros delitos. Los datos sensibles requieren de métodos de protección adicionales tales como el cifrado de datos, asi como tambien de precauciones especiales en un intercambio de datos con el navegador.


Como detectarlo


Lo primero que debe determinar es el conjunto de datos sensibles que requerirán protección extra. Por ejemplo, contraseñas, números de tarjeta de crédito, registros médicos, e información personal deberían protegerse. Para estos datos:

  1. ¿Se almacenan en texto claro a largo plazo, incluyendo sus respaldos? 
  2. ¿Se transmiten en texto claro, interna o externamente? El tráfico por internet es especialmente peligroso. 
  3. ¿Se utiliza algún algoritmo criptográfico débil o antiguo? 
  4. ¿Se generan claves criptográficas débiles, o falta una adecuada rotación o gestión de claves? 
  5. ¿Se utilizan tanto cabezales como directivas de seguridad del navegador cuando son enviados o provistos por el mismo?

Como prevenirlo


Los riesgos completos de utilizar cifrado de forma no segura, uso de SSL, y protección de datos. Dicho esto para los datos sensibles, se debe realizar como mínimo lo siguiente:

  1. Considere las amenazas de las cuales protegerá los datos (ejemplo atacante interno, usuario externo), asegúrese de cifrar los datos sensibles almacenados o en tráfico de manera de defenderse de estas amenazas. 
  2. No almacene datos sensibles innecesariamente. Descartelos apenas sea posible. Datos que no se poseen no pueden ser robados. 
  3. Asegúrese de aplicar algoritmos de cifrados fuertes y estándar así como claves fuertes o gestionelas de forma segura. Considere utilizar módulos criptográficos validados como FIPS 140. 
  4. Asegúrese que las claves se almacenan con un algoritmo especialmente diseñado para protegerlas como ser bcrypt, PBKDF2 o scrypt. 
  5. Deshabilite el autocompletar en los formularios que recolectan datos sensibles. 
  6. Deshabilite también el cacheado de páginas que contengan datos sensibles.

viernes, 3 de agosto de 2018

Ataques Web - Demostración - XSS Reflected

Este tipo de vulnerabilidad compromete la seguridad del usuario y no la del servidor. Consiste en inyectar código HTML o Javascript en una web, con el fin de que el navegador de un usuario ejecute el código inyectado en el momento de ver la página alterada cuando accede a esta. La forma conocida como reflejada comúnmente se produce en sitios que reciben información vía GET (aunque también puede darse el caso vía POST), como por ejemplo:

buscador.php?d=cadena_a_buscar


Si sufriera este tipo de vulnerabilidad se podría inyectar código en el navegador del siguiente modo:

buscar.php?d=<script type="text/javascript">script();</script>


De esta forma el código insertado no se mostraría de forma persistente, pero aun así un usuario malintencionado podría crear una URL que ejecute el código malicioso para posteriormente enviárselo a una persona y que al ejecutarlo ésta pueda sustraer cookies o incluso su contraseña (Pishing).

Para ejemplificar este tipo de vulnerabilidad DVWA presenta una página en la que se solicita un nombre a través de un formulario. Una vez enviado, el script muestra la cadena de texto “Hello nombre_enviado”.

En el nivel de seguridad low el código fuente vulnerable es el que se muestra a continuación:

código fuente vulnerable

Esta porción de código sólo valida que el nombre introducido no sea una cadena vacía.

valida que el nombre introducido no sea una cadena vacía


Así pues, para probar la vulnerabilidad de esta página se inyectará el siguiente código HTML que incluye un script Javascript:

<script>alert("Pagina vulnerable en nivel low")</script>

que mostrará una ventana de alerta con el mensaje “Página vulnerable en nivel low”.

mensaje Página vulnerable en nivel low

A continuación se introduce código HTML mostrar una imagen en lugar de una cadena de texto como sería de esperar:

<img src="http://spf.fotolog.com/photo/31/9/87/de_viginin/1236543937498_f.jpg" alt="Pato" />

introduce código HTML mostrar una imagen en lugar de una cadena de texto

En el nivel de seguridad medium se realiza un pequeño filtrado de la cadena de texto recibida a través del formulario haciendo uso de la función str_replace() para, en caso de ser encontrada, reemplazar la cadena <script> por una cadena vacía.

nivel de seguridad medium


DVWA muestra en este nivel el mismo formulario que en el nivel low:

muestra en este nivel el mismo formulario


Se usará el mismo mensaje de alerta Javascript usado para el nivel low, con la diferencia que en esta ocasión el tag HTML se escribirá en mayúsculas (y de este modo evitar que la función str_replace() encuentre coincidencia y sustituya el tag por una cadena vacía):

<SCRIPT>alert("Pagina vulnerable en nivel medium")</SCRIPT>

Aunque también hubiera bastado con añadir el tipo de script al tag <script> para que no se produjera coincidencia:

<script type="text/javascript">alert("Pagina vulnerable en nivel medium")</script>

pagina vulnerable en nivel medium

Como la única etiqueta HTML filtrada es <script>, se podría insertar cualquier código HTML
 imaginable. Por ejemplo, un hipervínculo a la página www.as.com:

<a href="http://www.as.com/">As.com</a>

hipervínculo a la página www.as.com


Aunque este ejemplo pueda parecer inocuo, ejemplifica perfectamente las posibilidades que podría llegar a permitir esta vulnerabilidad, como por ejemplo añadir un enlace a un script que se encargará de robar cookies…

Prevención


Para evitar este tipo de vulnerabilidad se recomienda filtrar siempre la información procedente del usuario antes de hacer uso de ella. Generalmente con filtrar los caracteres “<” y “>” sería suficiente, aunque se recomienda también filtrar los nombres de las etiquetas que pueden resultar peligrosas en este tipo de ataque como <script>, <object>, <applet>, <embed> y <form>.

Asimismo se pueden realizar comprobaciones para comprobar que el tipo de dato introducido y la longitud de cada campo se correspondan con lo esperado.

Por su parte, DVWA en el nivel de seguridad high hace uso de la función htmlspecialchars() para convertir caracteres especiales en entidades HTML.




Para que comprender mejor su funcionalidad se muestran algunos ejemplos:
  • & (et) se convierte en &amp; 
  • “ (comillas dobles) se convierte en &quot; cuando ENT_NOQUOTES no está establecido. 
  • ‘ (comilla simple) se convierte en &#039; (o &apos;) sólo cuando ENT_QUOTES está establecido. 
  • < (menor que) se convierte en &lt; 
  • > (mayor que) se convierte en &gt; 

Otra contramedida enfocada a los propios usuarios de páginas web es la de tener el navegador lo más actualizado posible. Por ejemplo el navegador Internet Explorer a partir de su versión 8, introduce como novedad un filtro Anti XSS que detecta posibles manipulaciones de la página mediante la inyección de código en un parámetro de la URL.

lunes, 30 de julio de 2018

Ataques Web - Demostración - Sql Injection Blind

Este tipo de ataque es similar al SQL Injection que se acaba de estudiar, con la diferencia que la página web no devuelve ningún mensaje de error al producirse resultados incorrectos tras una consulta a la base de datos. Esta falta de muestreo de resultados se produce por el tratamiento total de los códigos de error, y la imposibilidad de modificar, a priori, información alguna de la base de datos, teniendo respuesta únicamente en caso de que la consulta sea correcta.

La falta de mensajes de error no quiere decir que no sea vulnerable una página web. ¿Cómo se sabe que una web es vulnerable a SQL Injection Blind? Pues basta con probar un poco más y siempre que la inyección esté bien ejecutada se mostrará el contenido esperado.

Sentencias condicionales tipo Or 1=1 o having 1=1 ofrecen respuestas siempre correctas (true o verdadero) por lo cual suelen ser usadas por los programadores como formas de comprobación.

En el nivel de seguridad low el código fuente vulnerable es el que se muestra a continuación, la única diferencia con el nivel low de SQL Injection es el tratamiento de errores:

nivel de seguridad low el código fuente vulnerable


DVWA vuelve a mostrar una página similar a la de SQL Injection, donde escribir el ID de un usuario de la base de datos, y al igual que antes, devuelve el nombre y apellido asociado a dicha ID:

devuelve el nombre y apellido asociado a dicha ID


Se prueba con una comilla simple para ver que realmente no se devuelve ningún error y efectivamente al pulsar en “Submit” se vuelve a llevar a la pantalla original en blanco:

prueba con una comilla simple para ver que realmente no se devuelve ningún error

Tras ver que no se devuelve ningún error se pasa a probar a inyectar una consulta de tipo condicional, en este caso se va a insertar ' OR 'x'='x, lo que devolverá un listado con los usuarios:
se pasa a probar a inyectar una consulta de tipo condicional

A continuación se inyectará una consulta más compleja, anidando a la original:
1' and 'test' = 'b' union select database(), user() #
Que debe devolver la base de datos en que se está trabajando y el usuario utilizado:


inyectar una consulta más compleja
En el nivel de seguridad medium el código difiere del anterior en que la id recibida desde el formulario HTML es filtrada a través de la función mysql_real_scape() como se muestra a continuación:




Al igual que en el nivel medium de SQL Injection, DVWA vuelve a restringir el uso de caracteres especiales, por lo que se vuelve a usar la inyección de nivel low ' OR 'x'='x como ejemplo:

nivel medium de SQL Injection

En SQL Injection Blind, como ya se ha mencionado, en caso de error en la consulta no se devuelve nada, ni tan siquiera un mensaje de error advirtiendo del problema:

SQL Injection Blind

Se inyecta otra consulta condicional pero en esta ocasión sin los caracteres especiales:
1 OR 0=0----

Esta consulta devolverá un listado con los nombres y apellidos de los usuarios:
listado con los nombres y apellidos

Como último ejemplo se extraerán todos los campos de la tabla users inyectando:

1 and 1=0 union select table_name, column_name from information_schema..columns where table_name = 0x7573657273

Donde el número hexadecimal de SQL (0x7573657273) representa el nombre de la tabla en que se va a buscar. Este número puede ser muy importante dado a que a priori nadie conoce las tablas que se han creado en el sistema.

úmero hexadecimal de SQL representa el nombre de la tabla


Prevención


Dado que SQL Injection y SQL Injection Blind son a efectos prácticos la misma vulnerabilidad (pero en el caso Blind, sin mensaje de error devuelto en las consultas), las recomendaciones para evitar este tipo de ataques son las mismas:
  • Filtrado en tiempo de ejecución y bajo demanda.
  • Hacer uso de las funciones addcslashes(), mysql_real_escape_string() y stripslashes(), ya explicadas anteriormente, a la hora de filtrar los datos recibidos para realizar la consulta.
  • Uso de la librería mysqli.

viernes, 27 de julio de 2018

Ataques Web - Demostración - XSS Almacenado

XSS stored, también llamado XSS directo o persistente, consiste en embeber código HTML o Javascript en una aplicación web pudiendo llegar incluso a modificar la propia interfaz de un sitio web (defacement). Al igual que en el caso de XSS reflejcted, esta vulnerabilidad compromete la seguridad del usuario y no la del servidor.

La diferencia frente a XSS reflected es que este tipo de vulnerabilidad es persistente (de ahí que se le conozca también por ese nombre) ya que el código malicioso insertado generalmente es almacenado en una base de datos.

A modo de ejemplo, se considera el siguiente sitio web:

Un blog de noticias sobre Informática donde cada artículo permite la inclusión de comentarios por parte de sus usuarios. Una vez enviado un comentario, el contenido de éste será insertado en la base de

datos e inmediatamente visible en la página del artículo.

Tras descubrir cómo inyectar código en la web, las posibilidades que ofrece esta vulnerabilidad al atacante son diversas:


  • Inyectar código que robe las cookies del resto de usuarios.
  • Inyectar código que redirecciona la página web a una página externa.
  • Realizar un deface a la interfaz con el propósito de estropear el diseño web.
  • Troyanizar un gran número de navegadores de usuarios, tomando un control remoto sobre muchos navegadores.

    En el nivel de seguridad low el código fuente vulnerable es el que se muestra a continuación:

    nivel de seguridad low el código fuente vulnerable

    Este script recoge la información enviada a través del siguiente formulario, en el que los visitantes de la web pueden dejar un mensaje con su nombre (a modo de libro de visitas). Ambos campos son filtrados con la función trim() y mysql_real_escape_string() antes de ser insertados en la base de datos.

    Así mismo, el campo correspondiente al mensaje pasa por la función stripslashes() para eliminar las barras en caso de que el mensaje contenga comillas escapadas. Sin embargo no se realizar ningún filtrado para eliminar código HTML que pudiera contener el mensaje…




    no se realizar ningún filtrado para eliminar código HTML

    Una vez que se pulsa en el botón de envío del formulario, el nombre y el mensaje quedan grabados en la base de datos y al volver a cargar la página se mostrarán bajo dicho formulario:



    volver a cargar la página se mostrarán bajo dicho formulario

    Para comprobar si es vulnerable a XSS en el campo textarea mtxMessage esta vez introduciremos un tag HTML con el que lanzar una ventana de alerta Javascript:

    <script> alert("Vulneravilidad low")</script>

    El resultado de esta acción es que el mensaje se ha guardado correctamente en la base de datos y en cada carga de la página del libro de visitas se muestra la alerta esperada:


    vulnerabilidad low

    Un usuario mal intencionado podría, por ejemplo, provocar un deface del sitio web, modificando la estructura de la página pudiendo llegar en algunos casos a hacer ilegible su contenido.
    Por ejemplo, inyectar:

    </div></div></div></div><div>Qué lástima

    provocaría un cambio en la estructura HTML de la página web y, por consiguiente, del aspecto general de la página web:



    cambio en la estructura HTML de la página web


    En el nivel de seguridad medium el código difiere nivel low en el uso de la función strip_tags() para eliminar los tags HTML que pudiera contener el mensaje y el uso de str_replace() para eliminar la etiqueta <script> del campo correspondiente al nombre:



     eliminar la etiqueta <script>


    Mediante la combinación de las funciones strip_tags() y htmlspecialchars() el ataque a través de este campo textarea ha quedado sin efecto como se comprueba en la siguiente figura:



    campo textarea ha quedado sin efecto


    Por su parte, el campo input correspondiente al nombre no es seguro. El único filtro antes de ser insertado a la base de datos es el realizado con la función str_replace() para eliminar coincidencias con el tag <script>. Esta medida se muestra insuficiente debido a que podría hacer uso del mismo tag con la adición del parámetro type, con lo que ya no se produciría coincidencia y pasaría el filtro. Es más, podría incluso inyectarse cualquier otro tag HTML.

    Sin embargo, el código HTML del formulario no permite la inserción de más de 10 caracteres.

    <input type="text" maxlength="10" size="30" name="txtName">

    Esta limitación no supone un problema puesto que, como vimos en la vulnerabilidad CSRF, Firebug permite la edición inline del código fuente de una página web, por lo que a través de esta herramienta eliminaremos ese parámetro del campo input y, por consiguiente, se podrá inyectar cuanto texto permita el tipo de campo definido en la base de datos.

    <SCRIPT language="javascript">window.location="http://webexterna.com";</SCRIPT>




    vulnerabilidad CSRF, Firebug


    Como se observa en la siguiente figura, la entrada con el código inyectado fue insertada en la base de datos:


    código inyectado fue insertada en la base de datos

    Una vez inyectado el código, cada vez que algún usuario intenta cargar la página web, es redireccionado a la página principal del buscador Google España.
    google logo


    Si el filtrado no permitiera la inserción del tag <script> en ninguna de sus formas, se podría haber inyectado la etiqueta <meta> para provocar este mismo efecto:

    <html><meta http-equiv="refresh" content="0;url=http://www.google.es/"></html>

    Prevención


    Para evitar este tipo de vulnerabilidad se recomienda filtrar siempre la información procedente del usuario antes de hacer uso de ella. Generalmente con filtrar los caracteres “<” y “>” sería suficiente, aunque se recomienda también filtrar los nombres de las etiquetas que pueden resultar peligrosas en este tipo de ataque como <script>, <object>, <applet>, <embed> y <form>.

    Por su parte, DVWA en el nivel de seguridad high hace uso de las funciones stripslashes(), mysql_real_escape_string() y htmlspecialchars().


    nivel de seguridad high hace uso de las funciones stripslashes(), mysql_real_escape_string() y htmlspecialchars()



    Las medidas de seguridad para filtrar la información recibida del formulario son las mismas que en el caso de la vulnerabilidad XSS reflejected con la diferencia de que también ejecuta la función mysql_real_escape_string() antes de insertar la información en la base de datos.

    Otra contramedida enfocada a los propios usuarios de páginas web es la de tener el navegador lo más actualizado posible. Por ejemplo el navegador Internet Explorer a partir de su versión 8, introduce como novedad un filtro Anti XSS que detecta posibles manipulaciones de la página mediante la inyección de código en un parámetro de la URL.

    miércoles, 25 de julio de 2018

    Manejo de Roles y Permisos en Jenkins

    Manejo de Roles y Permisos en Jenkins


    Prerrequisitos



    Para poder tener un buen sistema de usuarios y roles, es necesaria la instalación de los siguientes plugins:

    Matrix Authorization Strategy Plugin -
    http://wiki.jenkins-ci.org/display/JENKINS/Role+Strategy+Plugin


    Creación de Roles



    Para ir a la Gestión de Roles dentro de Jenkins hay que ingresar en: “manager Jenkins” -> “Manage and Assign Roles” - > “Manage Roles”:
    Se puede definir roles a nivel global, a nivel de proyecto o a nivel de slave, pero para una primer instancia solo es necesario generar roles a nivel global.




    Veremos tres roles definidos admin, developer y líder, estos serán designados según categoría de cada usuario. Permitiendo a los developer ver resultados y ejecutar cualquier tarea en Jenkins, el rol líder puede hacer lo mismo que el developer además de poder crear, configurar y borrar tareas. El rol admin tiene todos los permisos.

    Asignar Roles a los usuarios



    Para poder asignar roles hay que ir a: “manager Jenkins” -> “Manage and Assign Roles” - > “Assing Roles”:

    Solo es necesario poner el nombre de usuario y luego agregarlo a la lista, para posteriormente a agregarse a la lista poder asignarle el rol correspondiente.

    Existen usuarios genéricos, donde se les puede definir el rol, para todos los usuarios que complan con la misma condición:

    Anonymous: Es el usuario genérico que se utiliza para cualquier usuario que ingrese al sistema sin estar logueado.

    Authenticated: Es el usuario que por medio del LDAP se autentica al servidor Jenkins y no tiene ningún permiso especial asignado.

    martes, 24 de julio de 2018

    Base de Datos SQL Derby - JPA

    Les muestro como configure una base de datos Derby, que es una base de datos relacional, de SQL y simple, que se levanta en memoria y que se puede guardar en archivos dentro del disco rígido local. 

    En principio se debe generar la siguiente estructura:



    El contenido del archivo persistence.xml es el siguiente:

    <?xml version="1.0" encoding="UTF-8"?>
    <persistence xmlns="http://java.sun.com/xml/ns/persistence"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
    version="2.0">
    <persistence-unit name="insta">
    <provider>org.hibernate.ejb.HibernatePersistence</provider>
    <class>com.program.entity.Comments</class>
    <class>com.program.entity.Likes</class>
    <properties>
    <property name="javax.persistence.jdbc.driver" value="org.apache.derby.jdbc.EmbeddedDriver" />
    <!-- if you don't have a database already created append ;create=true 
    to end of the jdbc url -->
    <property name="javax.persistence.jdbc.url" value="jdbc:derby:basededatos" />
    <property name="javax.persistence.jdbc.user" value="root" />
    <property name="javax.persistence.jdbc.password" value="root" />
    <!-- if you just created the database, maybe you want hibernate to create 
    a schema for you <property name="hibernate.hbm2ddl.auto" value="create"/> -->

    <!-- <property name="hibernate.hbm2ddl.auto" value="create" /> -->
    </properties>
    </persistence-unit>
    </persistence>

    En javax.persistence.jdbc.url se puede agregar ";create=true" la primera vez como para que cree la base de datos cada vez que se inicia. Una vez que esta creada se debe quitar como para que no borre la base y la vuelva a crear.

    En el pom.xml se debe agregar las librerias para poder usar Derby:

      <dependency>
       <groupId>org.hibernate</groupId>
       <artifactId>hibernate-entitymanager</artifactId>
       <version>3.6.8.Final</version>
     </dependency>
     <dependency>
       <groupId>org.apache.derby</groupId>
       <artifactId>derby</artifactId>
       <version>10.13.1.1</version>
       <scope>runtime</scope>

     </dependency>

    En las entidades se debe utilizar maven como siempre, muestro un ejemplo:

    package com.instadany.entity;

    import javax.persistence.Column;
    import javax.persistence.Entity;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;

    @Entity
    public class Likes {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    public int id;

    @Column
    public String idinsta;

    }

    lunes, 23 de julio de 2018

    Ataques Web - Demostración - CSRF

    Las vulnerabilidades CSRF se producen cuando un sitio web permite a un usuario autenticado realizar acciones consideradas como “sensibles” sin comprobar que realmente es el usuario quien las está invocando conscientemente. En su lugar, la aplicación simplemente comprueba que la petición proviene del navegador autorizado de dicho usuario.

    De este modo, y dado que los navegadores ejecutan simultáneamente código enviado por múltiples sitios web, existe el riesgo de que un sitio web (sin el conocimiento del usuario) envíe una solicitud a un segundo sitio web y éste interprete que la acción ha sido autorizada por el propio usuario.

    Antes de ser víctima del ataque CSRF, el usuario se identifica con el usuario “admin” y la contraseña “password” para acceder al sistema. Como se observa en las siguientes figuras, en caso de producirse la autenticación en el sistema se muestra un mensaje de bienvenida, por lo que la víctima ya es “confiable” para el sitio web mientras la cookie almacenada en su navegador web con la ID de inicio de sesión no caduque o el usuario cierre la sesión (con lo que ésta sería eliminada).

    login dvwa

    El formulario vulnerable a CSRF se corresponde con la página de DVWA de cambio de contraseña para los usuarios del sistema.


    Para llevar a cabo el ataque utilizaremos la configuración proxy propia del navegador y también el programa que provee OWASP, OWASP CSRFTester Herramienta gratuita (distribuida bajo licencia LGPL) para desarrolladores con la que poder comprobar si los formularios web son vulnerables a este tipo de ataque.

    Para configurar el proxy necesitamos ir a la configuración del Chrome, luego acceder a “Cambiar la configuración del proxy”

    Cambiar la configuración del proxy

    Ir a configuracion de LAN , e ingresar como lo indica la imagen, y luego aceptar.

    Cambiar la configuración del proxy lan

    En primer lugar se activará el proxy que incluye la aplicación FoxyProxy para que capture todo el tráfico web en un puerto determinado, el mismo en que estará escuchando la aplicación OWASP CSRFTester. En este caso el puerto es el 8008.

    Puesto que el cambio de contraseña lo realizará el navegador web de la víctima, el hecho de que el atacante desconozca su contraseña es irrelevante. Simplemente se necesita enviar el formulario para capturar los datos clave que se requieren para llevar a cabo este ataque y que recogerá la aplicación OWASP CSRFTester. Para cada petición se muestran detalles como el método de envío empleado por el formulario (GET o POST) y los parámetros transmitidos por URL.
    En nuestro ejemplo son:
    • password_new: contraseña nueva.
    • password_conf: rescritura de la contraseña para comprobar que el usuario la ha escrito correctamente. En caso de no coincidir ambas no se realiza el cambio de contraseña.
    • Change: parámetro de control para confirmar la petición de cambio de contraseña. Si no es definida en la petición no se realizará el cambio aunque las contraseñas coincidan.

    Los parámetros password_new y password_conf son los que se deberán modificar para que la víctima realice un cambio de contraseña (por otra que desconozca) sin su consentimiento.

    la víctima realice un cambio de contraseña

    Para ello la aplicación OWASP CSRFTester cuenta con una herramienta que genera automáticamente el fichero HTML que realizará la petición de cambio de contraseña basada en la confianza que el sitio web tiene en el usuario autenticado en el sistema.
    cambio de contraseña basada en la confianza que el sitio web

    CSRFTester ofrece otras opciones, como por ejemplo la de realizar la petición de cambio de contraseña de una manera más inadvertida insertando, por ejemplo, una imagen. Obviamente esta imagen no será mostrada al usuario (puesto que el origen no es una imagen) y lo que producirá precisamente es que se genere la solicitud de cambio de contraseña.
    solicitud de cambio de contraseña


    En este ejemplo se hará uso de la ingeniería social y la confianza que el usuario tiene en el atacante para que haga clic en el enlace al documento HTML que llevará a cabo el ataque CSRF.

    En caso de no contar con esta ventaja, se podrían emplear otros métodos como por ejemplo combinando un ataque Man in the middle con DNS Spoofing para servirle una web falsa enlazando con nuestro documento HTML en lugar del sitio web original al que pretendía acceder el usuario.

     Man in the middle con DNS Spoofing

    Una vez el usuario haga clic en el enlace se observa que el navegador web le ha redirigido a la

    página de cambio de contraseña y que no se muestra ningún mensaje referente al cambio de la misma.

    Sin embargo, una vez se ha desconectado del sistema y caduca por tanto la cookie con su inicio de sesión, al volver a intentar autenticarse el sistema le muestra un mensaje de error “Login failed”.

    El nivel medio de seguridad de DVWA introduce como condición que la petición de cambio de contraseña provenga del propio servidor donde está alojada la página web. En caso contrario, la petición será desatendida.


    petición será desatendida


    Para explotar esta vulnerabilidad bastaría con un pequeño script programado en PHP que modifica el encabezado de la petición para que al ser ejecutada por la víctima en un servidor externo,

    Prevención


    DVWA sugiere como método más seguro para evitar este tipo de ataque el requerimiento de la contraseña actual junto con la nueva y la rescritura de la misma. Sin embargo esto sólo sería aplicable para este ejemplo concreto de cambio de contraseña, por lo que para otro tipo de acciones se recomienda el uso de tokens de autorización para cada acción.
    Un ejemplo sería utilizar una palabra secreta y el identificador de sesión del usuario para generar los tokens. Las funciones que se muestran a continuación utilizan un valor de configuración prefijado que contiene una palabra secreta a partir de la cual se generan todos los tickets. Esto permite invalidar en cualquier momento todos los tickets modificando simplemente esta palabra.
    palabra secreta a partir de la cual se generan todos los tickets

    La función de generación recibe el nombre del formulario a securizar y obtiene el token asociado haciendo un hash md5 sobre la concatenación de la palabra secreta, el identificador de sesión del usuario y el nombre del formulario. De esta forma se obtiene un token de autorización para cada usuario y cada acción.
    Para comprobar su validez se realiza la misma acción y se compara el token generado con el token recibido.
    Su inclusión en un formulario HTML se realizaría de la siguiente manera:



    compara el token generado con el token recibido



    De este modo, frente al caso en que se hiciera generando tokens personalices por acción con sesión, se utiliza menos espacio en el servidor y se reducirán los problemas de usabilidad. Sin embargo no se tendrá control sobre el tiempo de validez de los tokens, caducando estos en el momento en el que finaliza la sesión de usuario. El siguiente fragmento de código permite comprobar la validez de un token recibido:


    compara el token generado con el token recibido