Hoy algo de carne, una chuleta sobre las variables superglobales (woh!) no fiables, donde el cliente puede meter mano:
Mostrando entradas con la etiqueta php. Mostrar todas las entradas
Mostrando entradas con la etiqueta php. Mostrar todas las entradas
miércoles, 2 de marzo de 2011
domingo, 27 de febrero de 2011
Un tracker BitTorrent en un .php y una tabla MySQL
Esto lleva un rato sin actualizar, así que traigo una cosilla que puede resultar interesante, un tracker de BitTorrent que solo ocupa un archivo .php de 250 líneas y que necesita únicamente una tabla en una base de datos MySQL, además logicamente del servidor web [ announce.php ]
Etiquetas:
bittorrent,
php,
torrent
domingo, 21 de noviembre de 2010
PoC de login seguro sobre HTTP
A raíz de este hilo en HackXCrack decidí programar un sistema de login que permitiese cierta seguridad ante atacantes pasivos aún funcionando sobre HTTP en plano, todo de forma transparente al usuario.
La idea es simple, cuando el usuario se intenta loguear, se le asigna un token que se utilizará como salt de una función hash que se aplicará a la contraseña (yo he utilizado MD5 porque tenía el código en python a mano), el resultado de la función será el que se envíe. El utilizar un token es importante porque evita ataques de replay, es decir, que el atacante pase a través de la función hash, enviando el resultado directamente, no tendría que conocer la contraseña original si el resultado es siempre el mismo. Además es importante que el token lo establezca el servidor y nunca quién se loguee, ya que lo podría modificar para que fuera el mismo que el del usuario original, con lo que se vuelve al ataque de replay.
Pero tiene bastantes problemas:
Btw... 1 año!!
La idea es simple, cuando el usuario se intenta loguear, se le asigna un token que se utilizará como salt de una función hash que se aplicará a la contraseña (yo he utilizado MD5 porque tenía el código en python a mano), el resultado de la función será el que se envíe. El utilizar un token es importante porque evita ataques de replay, es decir, que el atacante pase a través de la función hash, enviando el resultado directamente, no tendría que conocer la contraseña original si el resultado es siempre el mismo. Además es importante que el token lo establezca el servidor y nunca quién se loguee, ya que lo podría modificar para que fuera el mismo que el del usuario original, con lo que se vuelve al ataque de replay.
Pero tiene bastantes problemas:
- Si el atacante es activo (puede interceptar la conexión y modificar datos al vuelo), puede cambiar el código fuente de la página, invalidando esto.
- Las contraseñas han de guardarse en texto plano, para poder realizar el hash a posteriori.
- Como consecuencia de lo anterior se produce un aumento muy considerable de la carga del servidor, ya que en vez de hacer el hash una sola vez (ya que se supone que las contraseñas se guardan ya hasheadas), en el peor caso, ha de comprobarse el hash de todas las contraseñas cada intento de login.
Btw... 1 año!!
jueves, 22 de abril de 2010
Web's fantasma
Era un concepto que me gusto, la verdad es que ni siquiera era idea mia, sino que la saque de # Freesoftwareando in the night, la idea era dejar ahí el zip... pero como cerraron el post, pues lo dejo aqui.
Lo que entendi grosso modo (seguramente estaria explicado exactamente lo contrario, pero se hace lo que se puede ), era que estaria bien tener paginas web que una vez se visitaran, al volver no hubiera nada, por aquello de que alguien viendo de donde venia la gente por los Refereer acabaria estrellandose con un 404, bien, lo que pude programar es esto [multiplexor.zip], (hay que ajustar algunos parametros en options.php)
Y basicamente lo que hace es que al navegar dentro de la pagina (para empezar hay que navegar al archivo getticket.php) todas las direcciones son "virtuales", si alguien las ve y intenta visistarlas se encontrara con el conocido 404 Not Found, en la practica lo que hace es cifrar con ARC4 el nombre del archivo de la url usando como contraseña el id de session, y que al descifrar si no encuentra nada, envie un 404.
Obviamente no todo son ventajas (acaso tiene alguna utilidad real? ), el script PHP hace una peticion al servidor por cada una que le hace a el (siendo a localhost no deberia haber gran problema, pero es algo a tener en cuenta), ademas el problema de la implementacion es que seguramente funcione mal en paginas con Ajax, y no se tomo en cuenta la posibilidad de usarlo con formularios (es una Prueba de concepto, no habia ganas de implementar un parser html completo y demas )
ps: Perdon desde ya por el ultimo trozo de codigo, me quedo bastante... poco pythonico
ps2: Para quien no quiera bajarse todo el zip, tiene la implementacion de ARC4 en php, en un zip separado
Eso es todo, hasta la proxima!
Lo que entendi grosso modo (seguramente estaria explicado exactamente lo contrario, pero se hace lo que se puede ), era que estaria bien tener paginas web que una vez se visitaran, al volver no hubiera nada, por aquello de que alguien viendo de donde venia la gente por los Refereer acabaria estrellandose con un 404, bien, lo que pude programar es esto [multiplexor.zip], (hay que ajustar algunos parametros en options.php)
Y basicamente lo que hace es que al navegar dentro de la pagina (para empezar hay que navegar al archivo getticket.php) todas las direcciones son "virtuales", si alguien las ve y intenta visistarlas se encontrara con el conocido 404 Not Found, en la practica lo que hace es cifrar con ARC4 el nombre del archivo de la url usando como contraseña el id de session, y que al descifrar si no encuentra nada, envie un 404.
Obviamente no todo son ventajas (acaso tiene alguna utilidad real? ), el script PHP hace una peticion al servidor por cada una que le hace a el (siendo a localhost no deberia haber gran problema, pero es algo a tener en cuenta), ademas el problema de la implementacion es que seguramente funcione mal en paginas con Ajax, y no se tomo en cuenta la posibilidad de usarlo con formularios (es una Prueba de concepto, no habia ganas de implementar un parser html completo y demas )
ps: Perdon desde ya por el ultimo trozo de codigo, me quedo bastante... poco pythonico
ps2: Para quien no quiera bajarse todo el zip, tiene la implementacion de ARC4 en php, en un zip separado
Eso es todo, hasta la proxima!
Etiquetas:
404,
arc4,
ideas ajenas,
php,
web
martes, 20 de abril de 2010
TestWeb, un queso gruyer de vulnerabilidades
Esta idea viene de un post en HackXCrack en el que se buscaba el codigo de una pagina web con vulnerabilidades para hacer pruebas y a falta de una ya escrita, programe una web pequeña.
Tiene un poco de todo: SQL inyection, XSS y todo lo que se me ocurrio =)
Aqui teneis el zip (TestWeb.zip)
Usa una base de datos MySQL, los datos se pueden configurar en el archivo dbdata.php
ps: como ya comente en el post de HackXCrack, si vas a permitir a cualquiera entrar, mejor que pongas la variable $allowUpload en False, ( $allowUpload=False; ) (esta en el archivo _change_avatar.php ) sino se podria causar un DoS..., y de paso asegurate que los archivos estén en un chroot (las distros basadas en Debian lo hacen por defecto)... yo aviso
Hasta otra!
ps2: La tercera parte de Introduccion a la criptografia esta en camino ;)
Tiene un poco de todo: SQL inyection, XSS y todo lo que se me ocurrio =)
Aqui teneis el zip (TestWeb.zip)
Usa una base de datos MySQL, los datos se pueden configurar en el archivo dbdata.php
ps: como ya comente en el post de HackXCrack, si vas a permitir a cualquiera entrar, mejor que pongas la variable $allowUpload en False, ( $allowUpload=False; ) (esta en el archivo _change_avatar.php ) sino se podria causar un DoS..., y de paso asegurate que los archivos estén en un chroot (las distros basadas en Debian lo hacen por defecto)... yo aviso
Hasta otra!
ps2: La tercera parte de Introduccion a la criptografia esta en camino ;)
Etiquetas:
ideas ajenas,
pentesting,
php,
web
domingo, 28 de febrero de 2010
Peligros en el e-Mail
Hoy vamos a ver uno de los "peligros" del correo electronico, y no, no me refiero a el malware, ni al spam ni a nada asi (aunque lleva tanto tiempo ahi como ellos, o aun mas) , sino a algo que incluso se utiliza en correos legitimos (o al menos eso parecen)
Esto es, los correos con HTML
En un principio se podria pensar que esto no tiene nada de malo, se usa HTML en paginas web y no hay ningun problema, ¿verdad?... el problema esta en que se puede utilizar para obtener informacion que no suele ser bueno hacer publica, como la direccion IP utilizada
Veamos como funciona:
Mandamos un correo electronico a una direccion... usuario@example.org , cuando se abra el correo se mostrara el contenido en HTML (a menos que se configure el cliente de correo para que no lo haga) y al mostrar una imagen (por ejemplo), el cliente se conecta al servidor donde esta la imagen, que puede capturar informacion interesante del cliente como la IP, el navegador/cliente utilizado, etc...
Vamos alla, para esto usamos dos archivos, uno PHP (o lo que se utilize en el servidor web que se va a utilizar) y una imagen (o cualquier cosa que haga que el cliente se comunique con nuestro servidor, la imagen es lo mas sencillo y encaja perfectamente en un correo)
El archivo PHP solo tiene que hacer una cosa, guardar los datos del cliente y mandarle la imagen, un ejemplo seria:
Y ya esta, le enviamos el correo a alguien y...

El primero es abriendolo con el Thunderbird (como se puede ver en Navegador), y la segunda con un webmail (el navegador es Firefox)
Y ya tenemos la IP de a quien se le envio el correo
La siguiente vuelta de tuerca es hacer que en los logs tambien aparezcan las direcciones asociadas a cada IP, solo hay que añadir otra variable
Ahora ademas no se puede simplemente usar la imagen como antes (simplemente indicando su URL) ahora ademas hay que añadir ?mail=usuario@correo.aaa, por ejemplo, para mandarselo a "joe@gmail.com", utilizando la imagen http://aaa.com/imagen.php, habria que indicar http://aaa.com/imagen.php?mail=joe@gmail.com en la direccion de la imagen, el resultado es este:

Y en los dos casos el email parece completamente inofensivo:

Si, vale, no hay texto y la imagen que envie es de otro post, pero para mostrar la idea sirve
Tambien esta la opcion de incluir una imagen que solo tenga un pixel y que ademas es 100% transparente, asi que no se puede ver sin comprobar el codigo del mensaje
La solucion
La forma mas facil de evitar el problema (aparte de no abrir correos que no sean fiables) es deshabilitar el HTML en el cliente de correo (o en el webmail), Thunderbird, por ejemplo, pide confirmacion para leer HTML por defecto
Hasta otra!!
Esto es, los correos con HTML
En un principio se podria pensar que esto no tiene nada de malo, se usa HTML en paginas web y no hay ningun problema, ¿verdad?... el problema esta en que se puede utilizar para obtener informacion que no suele ser bueno hacer publica, como la direccion IP utilizada
Veamos como funciona:
Mandamos un correo electronico a una direccion... usuario@example.org , cuando se abra el correo se mostrara el contenido en HTML (a menos que se configure el cliente de correo para que no lo haga) y al mostrar una imagen (por ejemplo), el cliente se conecta al servidor donde esta la imagen, que puede capturar informacion interesante del cliente como la IP, el navegador/cliente utilizado, etc...
Vamos alla, para esto usamos dos archivos, uno PHP (o lo que se utilize en el servidor web que se va a utilizar) y una imagen (o cualquier cosa que haga que el cliente se comunique con nuestro servidor, la imagen es lo mas sencillo y encaja perfectamente en un correo)
El archivo PHP solo tiene que hacer una cosa, guardar los datos del cliente y mandarle la imagen, un ejemplo seria:
<?php
$fname="log.txt"; // archivo donde se guardan los logs
$f=fopen("$fname","a"); // Abrimos el archivo y lo preparamos
// para seguir escribiendo
fwrite($f,"IP: ".$_SERVER['REMOTE_ADDR']."\n"); // Guardamos la IP del cliente
fwrite($f,"Navegador: ".$_SERVER['HTTP_USER_AGENT']."\n"); // y tambien la
//informacion del cliente
fwrite($f,"---------------------\n"); // Para hacer el archivo mas facil de leer
fclose($f);
// Imagen a mostrar
$img="esfera.png";
// Redireccionamos al cliente a la imagen
header("Location: $img");
?>
Como se puede ver, el codigo es bastante simple, abrir un archivo, escribir un par de variables interesantes (en este caso, la IP y el cliente), y redireccionar el cliente a la imagen, se podria hacer que lea la imagen y la envie al cliente, que seria una solucion mas fiable (si alguien sigue la direccion de la imagen se dara cuenta del truco)Y ya esta, le enviamos el correo a alguien y...

El primero es abriendolo con el Thunderbird (como se puede ver en Navegador), y la segunda con un webmail (el navegador es Firefox)
Y ya tenemos la IP de a quien se le envio el correo
La siguiente vuelta de tuerca es hacer que en los logs tambien aparezcan las direcciones asociadas a cada IP, solo hay que añadir otra variable
<?php
$fname="log.txt"; // archivo donde se guardan los logs
$f=fopen("$fname","a"); // Abrimos el archivo y lo preparamos
// para seguir escribiendo
fwrite($f,"Direccion: ".$_REQUEST['mail']."\n");
fwrite($f,"IP: ".$_SERVER['REMOTE_ADDR']."\n"); // Guardamos la IP del cliente
fwrite($f,"Navegador: ".$_SERVER['HTTP_USER_AGENT']."\n"); // y tambien la
//informacion del cliente
fwrite($f,"---------------------\n"); // Para hacer el archivo mas facil de leer
fclose($f);
// Imagen a mostrar
$img="esfera.png";
// Redireccionamos al cliente a la imagen
header("Location: $img");
?>
Ahora ademas no se puede simplemente usar la imagen como antes (simplemente indicando su URL) ahora ademas hay que añadir ?mail=usuario@correo.aaa, por ejemplo, para mandarselo a "joe@gmail.com", utilizando la imagen http://aaa.com/imagen.php, habria que indicar http://aaa.com/imagen.php?mail=joe@gmail.com en la direccion de la imagen, el resultado es este:

Y en los dos casos el email parece completamente inofensivo:

Si, vale, no hay texto y la imagen que envie es de otro post, pero para mostrar la idea sirve
Tambien esta la opcion de incluir una imagen que solo tenga un pixel y que ademas es 100% transparente, asi que no se puede ver sin comprobar el codigo del mensaje
La solucion
La forma mas facil de evitar el problema (aparte de no abrir correos que no sean fiables) es deshabilitar el HTML en el cliente de correo (o en el webmail), Thunderbird, por ejemplo, pide confirmacion para leer HTML por defecto
Hasta otra!!
viernes, 27 de noviembre de 2009
Como hacer las imagenes que ponen ip, navegador...
Para esto necesitaremos un servidor HTTP ( como apache ) y PHP, las dos cosas es lo tipico que se encuentra en un hosting gratuito ( aqui hay una lista )
Si lo vamos a alojar nosotros mismos necesitaremos habilitar el paquete php-gd para esto edita el php.ini, descomenta la linea de ";extension=php_gd2.dll" (quitale el ';'... en algunos casos es un '#')
En debian/ubuntu se hace con "sudo apt-get install php5-gd"
Vamos alla...
Buscamos una imagen, la imagen sera la base, conviene que sea lo mas uniforme posible para que quede bien, yo escogi esta, aun que no sea la mas apropiada

Preparamos el codigo en PHP
El siguiente codigo es el que escribira en la imagen
Como funciona? (Para l@s que no les guste leer los comentarios del codigo)
Se usan dos funciones (navegador y os), que buscan en la cadena del "User-Agent", alguna parte conocida (Firefox, MSIE, etc...), y que devuelven el navegador y el sistema operativo del usuario
El resto es PHP,
$back="esfera.png"; //Imagen de fondo
$img=imagecreatefrompng($back); //Se crea la imagen (desde un png)
Como indican los comentarios, la primera linea es saber donde esta la imagen base, la segunda es para importarla como PNG, tambien se puede hacer para jpg
imagecreatefromjpeg
o con gif
imagecreatefromgif
(aqui hay mas funciones parecidas: http://us3.php.net/manual-lookup.php?pattern=imageCreateFrom&lang=es)
$fcolor=ImageColorAllocate($img,255,120,0); // El color de las letras ($img,r,g,b)
Prepara el color de las letras en la imagen (recuerda que la imagen esta en $img), el color se asigna en rgb, de 0 a 255 (esta combinacion, "255,120,0", seria naranja)
$ip=$_SERVER['REMOTE_ADDR']; //La ip esta en la variable
Guarda la ip (que esta en la variable $_SERVER['REMOTE_ADDR'])
ImageString($img,5,65,75,"IP: $ip",$fcolor);
Escribe en la imagen, con tamaño de letra 5, desde el pixel 65 (horizontal) y el 75 (vertical), la cadena "IP: $ip",en el color $fcolor
El resto es hacer lo mismo con lo que nos interesa (lenguaje, navegador,etc...)
Y despues
Header("Content-Type: image/png"); // Avisamos que es una imagen png
Avisamos al navegador para que reconozca lo que viene ahora como una imagen png (si es jpg, habria que poner "image/png")
Y los dos ultimos pasos
ImagePNG($img); // Convertimos a png
ImageDestroy($img); // Liberamos el espacio
Resultado:

Suerte y hasta otra
Si lo vamos a alojar nosotros mismos necesitaremos habilitar el paquete php-gd para esto edita el php.ini, descomenta la linea de ";extension=php_gd2.dll" (quitale el ';'... en algunos casos es un '#')
En debian/ubuntu se hace con "sudo apt-get install php5-gd"
Vamos alla...
Buscamos una imagen, la imagen sera la base, conviene que sea lo mas uniforme posible para que quede bien, yo escogi esta, aun que no sea la mas apropiada
Preparamos el codigo en PHP
El siguiente codigo es el que escribira en la imagen
<?php // Escrito por Kenkeiras function navegador($ua){ // Devuelve el navegador ...bastante simple ;) $nav=""; if (strstr($ua,"Firefox")) $nav="Firefox"; elseif (strstr($ua,"MSIE 6")) $nav="IExplorer 6"; elseif (strstr($ua,"MSIE 7")) $nav="IExplorer 7"; elseif (strstr($ua,"MSIE 8")) $nav="IExplorer 8"; elseif (strstr($ua,"Opera")) $nav="Opera"; elseif (strstr($ua,"Safari")) $nav="Safari"; return $nav; } function os($ua){ // lo mismo, pero para el SO $os=""; if (strstr($ua,"Linux")) $os="Linux"; elseif (strstr($ua,"Windows")) $os="Windows"; elseif (strstr($ua,"Mac")) $os="Mac"; return $os; } $back="esfera.png"; //Imagen de fondo $img=imagecreatefrompng($back); //Se crea la imagen (desde un png) $fcolor=ImageColorAllocate($img,255,120,0); // El color de las letras ($img,r,g,b) // Ejemplo: ImageString($img,Tamaño de letra,Longitud,Altura,"Texto",$fcolor); $ip=$_SERVER['REMOTE_ADDR']; //La ip esta en la variable $_SERVER['REMOTE_ADDR'] ImageString($img,5,65,75,"IP: $ip",$fcolor); // Escribimos la IP en la imagen $lang=$_SERVER['HTTP_ACCEPT_LANGUAGE']; $i=stripos($lang,";"); if ($i) $lang=substr($lang,0,$i); if ($lang!="") ImageString($img,5,50,100,"Lenguaje: $lang",$fcolor); $ua=$_SERVER['HTTP_USER_AGENT']; $os=os($ua); $nav=navegador($ua); if ($nav!="") ImageString($img,5,40,125,"Navegador: $nav",$fcolor); if ($os!="") ImageString($img,5,35,150,"Sistema Operativo: $os",$fcolor); // ---------------- Header("Content-Type: image/png"); // Avisamos que es una imagen png ImagePNG($img); // Convertimos a png //Si prefieres un JPEG cambia las dos ultimas lineas por //Header("Content-Type: image/jpeg"); //ImageJPEG($img); // ---------------- ImageDestroy($img); // Liberamos el espacio ?>
Como funciona? (Para l@s que no les guste leer los comentarios del codigo)
Se usan dos funciones (navegador y os), que buscan en la cadena del "User-Agent", alguna parte conocida (Firefox, MSIE, etc...), y que devuelven el navegador y el sistema operativo del usuario
El resto es PHP,
$back="esfera.png"; //Imagen de fondo
$img=imagecreatefrompng($back); //Se crea la imagen (desde un png)
Como indican los comentarios, la primera linea es saber donde esta la imagen base, la segunda es para importarla como PNG, tambien se puede hacer para jpg
imagecreatefromjpeg
o con gif
imagecreatefromgif
(aqui hay mas funciones parecidas: http://us3.php.net/manual-lookup.php?pattern=imageCreateFrom&lang=es)
$fcolor=ImageColorAllocate($img,255,120,0); // El color de las letras ($img,r,g,b)
Prepara el color de las letras en la imagen (recuerda que la imagen esta en $img), el color se asigna en rgb, de 0 a 255 (esta combinacion, "255,120,0", seria naranja)
$ip=$_SERVER['REMOTE_ADDR']; //La ip esta en la variable
Guarda la ip (que esta en la variable $_SERVER['REMOTE_ADDR'])
ImageString($img,5,65,75,"IP: $ip",$fcolor);
Escribe en la imagen, con tamaño de letra 5, desde el pixel 65 (horizontal) y el 75 (vertical), la cadena "IP: $ip",en el color $fcolor
El resto es hacer lo mismo con lo que nos interesa (lenguaje, navegador,etc...)
Y despues
Header("Content-Type: image/png"); // Avisamos que es una imagen png
Avisamos al navegador para que reconozca lo que viene ahora como una imagen png (si es jpg, habria que poner "image/png")
Y los dos ultimos pasos
ImagePNG($img); // Convertimos a png
ImageDestroy($img); // Liberamos el espacio
Resultado:
Suerte y hasta otra
Suscribirse a:
Entradas (Atom)