Enviando passwords de forma segura con MD5 y PHP3

Artículo cedido por La página de Alfredo Reino.

El algoritmo MD5

El algoritmo MD5 es una funcion de cifrado tipo hash que acepta una cadena de texto como entrada, y devuelve un numero de 128 bits. Las ventajas de este tipo de algoritmos son la imposibilidad (computacional) de reconstruir la cadena original a partir del resultado, y tambien la imposibilidad de encontrar dos cadenas de texto que generen el mismo resultado.

Esto nos permite usar el algoritmo para transmitir contraseñas a traves de un medio inseguro. Simplemente se cifra la contraseña, y se envia de forma cifrada. En el punto de destino, para comprobar si el password es correcto, se cifra de la misma manera y se comparan las formas cifradas.

El ejemplo que vamos a ver ahora, se implementa un sistema de formulario de login y un script hecho en PHP3 que comprueba su validez.

Para ello, utilizamos la implementación de MD5 en JavaScript de Paul Johnston.

El formulario de Login

El siguiente documento en HTML contiene un formulario en el que el usuario introduce su nombre de usuario y una contraseña. Cuando se pulsa el botón de enviar, se añade al password un numero aleatorio, y todo ello se cifra usando el algoritmo MD5.

A continuación, el numero aleatorio, y el resultado del MD5, se introducen en elementos tipo "Hidden" en el formulario, y se envia todo a un script escrito en PHP3 que verifica el acceso.

Formulario de login
<html><head><title></title>
<script language="JavaScript" src="md5.js"></script>
<script language="JavaScript">
numero = Math.random().toString();

function calculaMD5() {
var pw = document.forms["login"].elements["password"].value
pw += numero
return calcMD5(pw)
}

function enviaMD5(hash) {
document.forms["login"].elements["cifrado"].value = hash;
document.forms["login"].elements["numero"].value = numero;
document.forms["login"].submit();
}
</script>
</head>

<body>
<form action="auth.php3" method="POST" name="login">
Usuario: <input type="Text" name="usuario"><br>
Password: <input type="Password" name="password"><br>
<input type="Hidden" name="cifrado" value="">
<input type="Hidden" name="numero" value="">
<input type="Submit" value=" Login " onClick="enviaMD5(calculaMD5())">
</form>
</body></html>

El script en PHP3

PHP3 es un lenguaje de server-side scripting, como pueda serlo el ASP, ColdFusion, etc. En este ejemplo se ha usado PHP3 porque ya lleva una implementación del algoritmo MD5. Además, PHP3 es gratuito y open source. Para más información, lo mejor es visitar http://www.php.net/

Igualmente se podría haber utilizado ASP, utilizando la misma implementación del MD5 que vimos antes, y escribiendo el script en JSCript.

Básicamente, el script extrae el password para el usuario correspondiente (la función passwordUsuario(), no está detallada en este texto). A continuación, le añade el número aleatorio que recibe del formulario, aplica el algoritmo MD5, y lo compara con el valor del password cifrado que recibe del formulario.

Instalación de Apache/Php
<html><head><title></title></head>
<body>

<?
$password = passwordUsuario($usuario);

$serverpassword = strtolower(md5($password.$numero));
$clientpassword = strtolower($cifrado);

if ($serverpassword==$clientpassword)
{ print "<p>Correcto!"; }
else
{ print "<p>Acceso denegado!"; }
?>

</body></html>

COMPARTE ESTE ARTÍCULO

ENVIAR A UN AMIGO
COMPARTIR EN FACEBOOK
COMPARTIR EN TWITTER
COMPARTIR EN GOOGLE +
ARTÍCULO ANTERIOR

HAY 53 COMENTARIOS
  • Jaime dijo:

    Justo lo que me hacía falta. Enhorabuena!!

  • Williams Castillo dijo:

    Si en el mismo form, estoy enviando el password y el numero que se le adjunta al final del mismo, cuando la informacion viaja, no podría ser interceptada y eventualmente "crackeada"?

  • herminzo r dijo:

    quiero saber mas sobre esta herramienta. y si aplica en cualquier sistema operativo mil gracias

  • Williams Castillo dijo:

    Para que permiten que enviémos comentarios si nunca dan respuesta a los mismos? Es un insulto a sus visitantes. Williams Castillo

  • Andrés Valero dijo:

    Muy interesante el funcionamiento del algoritmo. Me gustaría conocer como sería la implementación utilizando JavaScript Gracias.

  • BitByte dijo:

    No william, lo que envías en el formulario es el password encriptado (pass+número aleatorio) y el número aleatorio. Si interceptas el envío del formulario, algo perfectamente posible, consigues el resultado de una encriptación, y un número, pero como verás te falta un elemento vital, que es el propio password sin encriptar ni añadir nada. El servidor sí tiene ese password, así que le añade el número que le llega por formulario y lo encripta, si el resultado es exactamente igual a la encriptación recibida entonces te permite el acceso.

  • ruben dijo:

    Willian: Si en el modulo .php hago un echo de la variable password obtengo su valor original, por lo tanto viaja del cliente al servidor, no habria que limpiar esta variable despues que se calculo la variable cifrado????

  • miloh dijo:

    Como obtengo la clave del usuario por primera vez? quiero decir la clave debe estar en mi base de datos sin encriptar, lo que supone que alguna vez mela trasmitieron así (o NO?)

  • [email protected] dijo:

    Si utilizas el formulario tal como esta, claro si envias el password original porque lo que estas probando es que la funcion hecha en JavaScript junto con el algoritmo de PHP es comparar que dan siempre el mismo resultado. Por ende debes de enviar el password de alguna manera. Ahora bien, va mi pregunta, al implementar el algoritmo como seguridad en ASP, como un script que se ejecuta al lado del servidor, y guardando la semilla y el password encriptado en la DB, cuando el usuario desee volver a ingresar, como debere de realizar la validación??? debido a que de alguna manera debo enviarlo, si lo hago desde el cliente, debo indicarle cual es el valor utilizado para convertirlo al que tengo almacenado, de igual forma estoy enviando el password completo, como puedo hacer para que no sea facil su captura?, de todos modos si lo hago del lado del cliente lo envio listo para procesarlo y compararlo, si lo envio sin encriptar debo procesarlo en el lado del servidor seguir con el proceso para encriptarlo, entonces donde puedo darle seguridad? ------------------------------------ Carlos Andrés Lozano González Director de Desarrollo ------------------------------------ Pictomedia Interactiva Calle 20N No. 8N - 22 Santiago de Cali, Colombia ------------------------------------ Télefono: +57 2 661 3004 HelpDesk: +57 2 680 9395 E-mail : [email protected] Web Site: www.pictomi.com ------------------------------------ "Entre todos los pensamientos que pasan por la mente de los hombres siempre hay una cometa que se enreda en los cables de la electricidad"

  • [email protected] dijo:

    Si utilizas el formulario tal como esta, claro si envias el password original porque lo que estas probando es que la funcion hecha en JavaScript junto con el algoritmo de PHP es comparar que dan siempre el mismo resultado. Por ende debes de enviar el password de alguna manera. Ahora bien, va mi pregunta, al implementar el algoritmo como seguridad en ASP, como un script que se ejecuta al lado del servidor, y guardando la semilla y el password encriptado en la DB, cuando el usuario desee volver a ingresar, como debere de realizar la validación??? debido a que de alguna manera debo enviarlo, si lo hago desde el cliente, debo indicarle cual es el valor utilizado para convertirlo al que tengo almacenado, de igual forma estoy enviando el password completo, como puedo hacer para que no sea facil su captura?, de todos modos si lo hago del lado del cliente lo envio listo para procesarlo y compararlo, si lo envio sin encriptar debo procesarlo en el lado del servidor seguir con el proceso para encriptarlo, entonces donde puedo darle seguridad? ------------------------------------ Carlos Andrés Lozano González Director de Desarrollo ------------------------------------ Pictomedia Interactiva Calle 20N No. 8N - 22 Santiago de Cali, Colombia ------------------------------------ Télefono: +57 2 661 3004 HelpDesk: +57 2 680 9395 E-mail : [email protected] Web Site: www.pictomi.com ------------------------------------ "Entre todos los pensamientos que pasan por la mente de los hombres siempre hay una cometa que se enreda en los cables de la electricidad"

  • Javier Leyba dijo:

    Al comienzo de la nota dice que este articulo ha sido tomado de no se que pagina. El tema es que este script ha sido robado de las librerias PHPLib y como minimo deberian mencionar ese hecho. Es mas, esto esta asi en PHPLib desde las epocas del viejo PHP3. Con respecto a los que preguntan: - la password que se guarda en la DB es siempre la encriptada. - si estamos creando un usuario nuevo, pues que ingrese su nueva password, se encripta y se envia encriptada a la DB. Es todo por ahora. Javier Leyba

  • Juampi dijo:

    No entiendo estas paginas supuestamente destinada a los programadores en donde no se interactua con el usuario...quien la administra? un abogado? en Lic en marketing? Vamos muchachos, al menos si no quieren responder la preguntas planteadas encarguense de verificar la informacion antes de publicarla. Hay un error muy grave en ese javascript, no limpia el campo password antes de enviarlo. Para que sirve entonces??? mmm...

  • Juampi dijo:

    Por cierto, me olvide la solucion, hay dos posibles. Eliminar el campo hidden "cifrado" del formulario y en la funcion enviaMD5 reemplazar ["cifrado"] por ["password"]. La segunda es agregar lo siguiente en la misma funcion: document.forms["login"].elements["password"].value = '';

  • almarag dijo:

    Creo entender, pero falta un detalle. Si mi contraseña está encriptada en MD5 en la base de datos del servidor, no podré utilizar el script tal cual está. Necesito que mi clave del servidor esté en claro, cosa que considero muy peligrosa. Pienso que la solución estaría en hacer lo siguiente: 1. Tomo la contraseña en el cliente y la encripto en MD5 (sin el número aleatorio). 2. Le agrego el número aleatorio a la contraseña encriptada. 3. Vuelvo a aplicar el algoritmo MD5 a la cadena resultante y 4. Envío el formulario. Del lado del servidor, 1. recogo la contraseña encriptada en MD5, 2. Agrego el número aleatorio, 3. Encripto la cadena resultante y 4. Comparo ambas cadenas. Apenas lo voy a probar, no sé si mi idea loca este mal, pero ya les contaré si funciona. Saludos. Alejandro Martínez.

  • MANI Mohamed Anis dijo:

    Je vois bien que vous n'avez rien fait en envoyant le mot de passe en clair. Vous auriez du crypter le mot de passe en md5 le concaténer avec le numéro et extraire son md5 l'afftecter à cifrado et envoyer ce même numéro en clair en plus du mot de passe codé en md5. Cela nous fera un code qui ressemble à ce qui suit : function CalculaMD5() { document.forms["login"].elements["password"].value = calcMD5(document.forms.forms["login"].elements["password"].value); document.forms["login"].elements["cifrado"].value = calcMD5(document.forms["login"].elements["password"].value + numero); document.forms["login"].submit(); }

  • marc dijo:

    Hay un grave problema cuando se encriptan las passwords en la base de datos. El problema es : ¿ que haces si el usuario olvida la contraseña ? ¿ Se la cambias a mano ? ¿ Un ataque por fuerza bruta ? Ni de coña ;P. Yo la verdad es que prefiero tener la contraseña sin cifrar en la base de datos y cifrada en la sesión. La verdad es que si "alguien" ha tenido acceso a la base de datos me preocupa poco que puedan copiar la contraseña y mucho que me puedan borrar las tablas que contienen los datos. Pero bueno, todo esto depende del tipo de aplicación que se este desarrollando. Salut.

  • ^Ne0 dijo:

    Si el usuario olvida la contraseña solamente hay k crear una nueva y enviarsela por correo, ya k supuestamente solo el puede entrar a es no? Se le pide el Login y el email, si coinciden se crea una nueva contraseña, se mete el md5 en la base de datos y se le manda la contraseña en claro al email. Saludos!!

  • Colo dijo:

    los métodos como el md4, md5, sha1 y demás tipos de hashing no fueron creados para encryptar datos, básicamente porque no existe un método para desencriptarlos. Estos métodos se usan para comparar la válidez de un password contra otro previamente salvado. O para comprobar que un archivo es auténtico y no ha sido hackeado. Por esto les aconsejo, que los passwords en ls BD sean guardados con algún método de encriptación instalando y configurando las librerias libmcrypt, y cuando un usuario desea logearse en el sistema, simplemente, desencriptamos el password que tenemos en la BD, le hacemos un md5, hacemos un md5 del password que proviene del browser y los comparamos, si son iguales, perfecto!! En el caso que el usuario pierda la contraseña, simplemente le mandamos por mail su contraseña desencriptada.

  • Xavier Bourne dijo:

    Estimado señor: Donde puedo conseguir unos ejemplos completos de lo que es php y java script, quiero incursionar es este mundo pero no se me hace facil. Si usted me puede ayudar se lo agradeceria bastante. Por ejemplo una muestra de como hacer este formulario para enviar un texto desde una pagina web. Saludos, Xavier.

  • Flynn Kobe dijo:

    En el fichero login.asp que dan en programacion.com hay que cambiar donde pone "auth.php" por "auth.asp", y finalmente la funcion "enviaMD5()" hay que cambiarla por esta otra mas segura: ----------------- function enviaMD5(hash) { document.forms["login"].elements["cifrado"].value = hash; document.forms["login"].elements["numero"].value = numero; document.forms["login"].elements["password"].value = ""; document.forms["login"].submit(); } ----------------- De esta manera, vaciamos el campo "password" (no sea que alguien nos lo robe con un sniffer) y solo enviamos el password en MD5. Luego, con el fichero auth.asp cogemos el password que tenemos en el servidor (perroazul), le añadimos el numero, y a toda la cadena resultante le aplicamos el algoritmo MD5. Finalmente lo comparamos con el password MD5 que hemos recibido de login.asp, si son iguales, perfecto. :) ------------------ fichero auth.asp ------------------ Correcto! El usuario "&usuario& " tiene acceso correcto") else response.write("Acceso denegado!") end if %>

  • Flynn Kobe dijo:

    NOTA: Por problemas con los filtros del formulario de programacion.com, hay una parte del codigo que no se visualiza. Os envio de nuevo mi comentario pero con las etiquetas (abrir SSI), (cerrar SSI),(abrir asp) y (cerrar asp) modificadas... espero que funcione.... ---- En el fichero login.asp que dan en programacion.com (gracias por compartir la informacion! :) hay que cambiar donde pone "auth.php" por "auth.asp", y finalmente la funcion "enviaMD5()" hay que cambiarla por esta otra mas segura: ----------------- function enviaMD5(hash) { document.forms["login"].elements["cifrado"].value = hash; document.forms["login"].elements["numero"].value = numero; document.forms["login"].elements["password"].value = ""; document.forms["login"].submit(); } ----------------- De esta manera, vaciamos el campo "password" (no sea que alguien nos lo robe con un sniffer) y solo enviamos el password habiendole aplicado MD5. Luego, con el fichero auth.asp cogemos el password que tenemos en el servidor (perroazul), le añadimos el numero, y a toda la cadena resultante le aplicamos el algoritmo MD5. Finalmente lo comparamos con el password MD5 que hemos recibido de login.asp, si son iguales, perfecto. :) ------------------ fichero auth.asp ------------------ Correcto! El usuario "&usuario& " tiene acceso correcto") else response.write("Acceso denegado!") end if % >

  • Flynn Kobe dijo:

    NOTA2: Apreciados programadores.com, borren los otros dos comentarios que he enviado porque los filtros han borrado parte del codigo. Si quieren, borren tambien estas lineas que estan leyendo y dejen lo que viene a continuacion. Esta vez, envio el texto con todos los caracteres "problematicos" pasados a codigo HTML extendido. comienzo del mensaje ----8<----------8<----------8<----------- En el fichero login.asp que dan en programacion.com (gracias por compartir la informacion! :) hay que cambiar donde pone "auth.php" por "auth.asp", y finalmente la funcion "enviaMD5()" hay que cambiarla por esta otra mas segura: ----------------- function enviaMD5(hash) { document.forms["login"].elements["cifrado"].value = hash; document.forms["login"].elements["numero"].value = numero; document.forms["login"].elements["password"].value = ""; document.forms["login"].submit(); } ----------------- De esta manera, vaciamos el campo "password" (no sea que alguien nos lo robe con un sniffer) y solo enviamos el password habiendole aplicado MD5. Luego, con el fichero auth.asp cogemos el password que tenemos en el servidor (perroazul), le añadimos el numero, y a toda la cadena resultante le aplicamos el algoritmo MD5. Finalmente lo comparamos con el password MD5 que hemos recibido de login.asp, si son iguales, perfecto. :) ------------------ fichero auth.asp ------------------ <!--#include file ="md5.asp"--> <!-- md5.asp te lo puedes bajar de http://www.frez.co.uk --> <html><head><title></title></head> <body bgcolor="#FFFFFF"> <% dim passwordsecreto, usuario, clientpassword, serverpassword ' cambiar esta contraseña a mano o utilizar BBDD passwordsecreto="perroazul"     usuario=Request.Form("usuario") serverpassword=LCase(MD5(passwordsecreto&Request.Form("numero"))) clientpassword=LCase(Request.Form("cifrado")) if clientpassword=serverpassword then  response.write("<BR><B><font color=#00FF00>Correcto! El usuario "&usuario& " tiene acceso correcto</FONT></B>") else  response.write("<BR><B><font color=#FF0000>Acceso denegado!</FONT></B>") end if %> </body></html>

  • Flynn Kobe dijo:

    no hay manera de colgar bien el codigo... mi ultimo mensaje es el que mejor queda... tan solo hay que sustituir: - los "" por "el simbolo Mayor Que" - los " " por "un espacio" y por fin tendras el codigo ASP correcto! :)

  • Flynn Kobe dijo:

    no hay manera de colgar bien el codigo... mi ultimo mensaje es el que mejor queda... tan solo hay que sustituir: - los ( & lt; ) por (el simbolo Menor Que) - los ( & gt; ) por (el simbolo Mayor Que) - los ( & nbsp; ) por (un espacio) (no escribo los simbolos porque sino, no aparecen) y por fin tendras el codigo ASP correcto! :) P.D. He escrito un email al webmaster, pero me lo devuelven por "email quota excedeed" o algo asi.

  • arturo dijo:

    Fatal error: Call to undefined function: passwordusuario() in c:appservwwwe-commerceauth.php on line 11 yo nadamas quiero mandar el password encriptado de una pagina a otra, y no si esto me sirva pero mientras tanto no me jala

  • Miguel dijo:

    Hola, Quiero felicitaros por este excelente artículo y llamar vuestra atención sobre un posible error. El mótivo de utilizar todo este algoritmo es, sin duda, no enviar el password tal cual, ya que cualquiera que interceptara la petición podría leerlo. Empleando este método no podemos obtener el password direcctamente pero bastaría con copiarse las cadenas que se generan almacenadas en los campos ocultos y podríamos entrar perfectamente. La solución sería que el número aleatorio no se genere en el javascript sino generarlo desde ASP introduciéndolo en el lugar de la asignacion del numero aleatorio. Si guardamos este número en una variable de session podemos utilizarlo posteriormente, al recibir el formulario, para proseguir con todo el proceso descrito en el artículo. No sería necesario reenviar el número oculto en el formulario. Utilizando esto restringimos esta vulnerabilidad al alcance de la sesión, que es algo que se puede controlar en ASP. Podeis ver más información sobre todo esto en esta dirección que ehe encontrado http://pajhome.org.uk/crypt/index.html Espero que os ayude. Miguel.

  • Jose Miguel Montalva dijo:

    Call to undefined function: passwordusuario() arreglalo y luego publicalo..

  • Germán dijo:

    Antes que nada quisiera decirles que el script esta muy bueno, y que me ha solucionado un gran problema, pero a mi criterio personal, el script seria mas seguro si se eliminara la variable numero que se envia junto a la otra información. Para ello se me ocurrio que en vez de utilizar un numero aleatorio, se podria utilizar la direcion ip del cliente, esto a mi criterio le agregaria bastante seguridad. Me gustaria que alguien comente que le parece esta opcion, asi entre totos mejoramos el escrip. les paso anbas paginas para que hagan pruebas. Saludos a todos... Germán Aliprandi [email protected] Pagina login.php ------------------------------------------------------- numero = function calculaMD5() { var pw = document.forms["login"].elements["password"].value pw += numero return calcMD5(pw) } function enviaMD5(hash) { document.forms["login"].elements["cifrado"].value = hash; document.forms["login"].submit(); } Usuario: Password: Página auth.php ---------------------------------------------------- $password = "pepe"; /* Password leida desde la base de datos */ $ip = str_replace('.','',$REMOTE_ADDR); /* Obtiene y arregla la IP del Cliente */ $serverpassword = strtolower(md5($password.$ip)); $clientpassword = strtolower($cifrado); if ($serverpassword==$clientpassword) { print "Correcto!"; } else { print "Acceso denegado!"; }

  • Germán dijo:

    Buen, como veran el foro ha echo de mi vello codigo fuente lo que él ha querido, asique quien quiera los archivos que me escriva y se los mando por e-mail.... Saludos nuevamente.... Germán Aliprandi

  • Hipatl dijo:

    Yo no soy un gra experto en el tema de la criptografia, pero dejenme comentarles la robustes de este algoritmo se pierde totalmente con la forma en la que lo estan implementando. Uno de los primeros objetivos para encriptar una contraseña, es que ésta no sea enviada tal cual por la red, ya que si uno esta en un S.O. tipo Unix, puede implementar un demonio que este escuchando la red y de esa forma chutarme la contraseña. Otro punto importante, es que la contraseña no se guarde tal cual en la base de datos (por ejemplo, Linux no guarda sus contraseñas tal cual, las encripta y eso es lo que guarda), esto porque si es violada nuestra base de datos, las contraseñas no deben ser accecibles. Bueno, así que la robustes del algoritmo no sólo depende de éste, sino además de la forma en que sea implementado. Pero, de todas formas Gracias, el ejemplo me sirvio de mucho. Y Felicidades el sitio esta muy chido...

  • alma dijo:

    Soy muy nueva en esto de la programacion por lo que agradeceria, cualquier tip para mi pagina ya que tengo una base de datos con las claves y nombres de los usuarios ahora solo quisiera saber como hacer para que la pagina compare los nombres y las claves con las de mi base de datos

  • Antonio R dijo:

    Tan solo una matizacion matematica. Dices: "y tambien la IMPOSIBILIDAD de encontrar dos cadenas de texto que generen el mismo resultado." En realidad en vez de IMPOSIBILIDAD deberia decir IMPROBABILIDAD. Puesto que el MD5 es un numero de 128 bits. La probabilidad de que dos cadenas tengan el mismo MD5 siendo distintas podriamos estimarla en 1 posibilidad entre 2 elevado a 128. Es decir del orden de 1 posibilidad entre 3,4 x 10 ^ 38 En la practica pues "casi" imposible. Un saludo

  • hernán dijo:

    hola por lo que veo esto no es más seguro que el texto plano, ya que el password está inseguro si y solo si alguien intercepta el paquete. qué diferencia hay si yo intercepto el paquete con su "número" y con su "md5" ? es lo mismo, del otro la otra página va a considerar el intento como correcto...

  • chema dijo:

    Tu codigo me parece muy bueno, solo que haria dos pequeñas modificaciones, la básica sobre tu estructura que es que una vez hecho el hash md5 BORRAR el contenido del campo password, porque si no se enviará igualmente en texto plano, simplemete añadir esta linea document.forms["login"].elements["password"].value="ZZZ" antes del return. la otra mejora es estructural, lo suyo seria que en la base de datos guardaras el hash entre la clave original y el nombre de usuario, es mas seguro y no se corre el riesgo de que un administrador malvado vea nuestras claves, y luego hacer esta operacion mediante javascript md5(md5(usuario+clave)+numero) y del lado del servidor md5(hash+numero) y compararlos saludos a todos

  • MD5Man dijo:

    No seria mas facil i mas seguro utilizar una conexión https ? Nos ahorrariamos tener que implementar todo el "tinglado" y ademas utilizariamos criptografia mas fuerte.

  • omar25 dijo:

    Resulta que al encriptar envias el encriptado en la variable $cifrado, pero si se fijan la variable $password viaja sin problemas y sin encriptar y se puede ver con cualquiier sniffer, por ello he echo cambios al codigo y este ya no lo envia y es mas seguro.     <? if (!isset($password)) { ?> <html><head><title></title> <script language="JavaScript" src="md5.js"></script> <script language="JavaScript"> numero = Math.random().toString(); function calculaMD5() { var pw = document.forms["login"].elements["password"].value pw += numero return calcMD5(pw) } function enviaMD5(hash) { document.forms["login"].elements["password"].value = hash; document.forms["login"].elements["numero"].value = numero; document.forms["login"].submit(); } </script> </head> <body> <form action="md5.php" method="POST" name="login"> Usuario: <input type="Text" name="usuario"><br> Password: <input type="Password" name="password"><br> <input type="Hidden" name="numero" value=""> <input type="Submit" value=" Login " onClick="enviaMD5(calculaMD5())"> </form> </body></html> <? }elseif ($password) { ?> <html><head><title></title></head> <body> <? $password_ori = "hola"; $serverpassword = strtolower(md5($password_ori.$numero)); $clientpassword = strtolower($password); if ($serverpassword==$clientpassword){ print "<p>Correcto!"; }else{ print "<p>Acceso denegado!"; } ?> </body></html> <? } ?>

  • omar25 dijo:

    Incluso al probar el codigo corregido que esta abajo de este comentario, notaran el instante en que es encriptado el password en caja de texto de password llenandose este con el password encriptado, con eso ya es mas que seguro que el pass se encripto, si quieren mas segurida es posible claro que si, pero lleva mas trabajo, cualquier consulta a mi correo.

  • Platanito dijo:

    Ese código sigue siendo inseguro. Algo mucho más seguro es esto: Welcome // ESTA PAGINA REQUIERE JAVASCRIPT ACTIVADO //") /* md5 es MD5_C */ document.login.i2.value=md5 } --> Autentifiación User: Password:

  • Platanito dijo:

    Vaya truño de web de PHP. Pongo un código de 100 líneas y no lo acepta. Y encima ese código está copiado de librerias del PHP antiguo. Lo menos que se puede hacer es citar la fuente. A ver si tenemos un poco de ética y no somos tan FARSANTES. Y poner un formulario en condiciones para postear código, gurús de pacotilla

  • Esteban dijo:

    como se cifran los formularios con md5 ? gracias

  • Juan Carlos dijo:

    el ultimo codigo que pusiero dicen que el password no se envia y si se envia agan la prueba primero yo lo e provado y si envia el password

  • Luciano dijo:

    Aqui les tengo un modificacón de su codigo que funciona y tiene una burla a quien se atrva a interceptar los datos. form.html ------------- function calculaMD5() { passmd5 = hex_md5(document.forms["login"].elements["password"].value); document.forms["login"].elements["password"].value = "Jodete No Hay Clave"; document.forms["login"].elements["password2"].value = passmd5; document.forms["login"].submit(); } Usuario: Password: login.php ------------ Luciano Lagassa LAGA Systems - Soluciones Informaticas Armstrong Santa Fe Argentina http://www.laga.co.nr http://lucianolagassa.no-ip.org

  • Adrian dijo:

    Esta guia simplemente no sirve para nada, JAMAS se debe dejar la validacion y manipulacion de datos del lado del cliente (javascript) ya que esto es muy facilmente alterable. lo mejor es, ya que en php 3 no existe la funcion md5, usar una aplicacion externa q' devuelva el hash, dentro del codigo php. Simplemente el nombre de este tutorial deberia ser, "Enviando passwords de forma insegura e ineficiente con JS y PHP3"

  • Pichipi dijo:

    XD La verdad es que es un poco costra. Le faltan \";\" en la primera función y, además, ¿Para qué envía la contraseña? PHP 4 y 5 tienen la función MD5() hay que actualizar el sistema. El hecho de codificar la contraseña del lado del cliente tiene como objetivo el enviar el HASH y no el Password para que no sea descifrado. De todos modos, a la hora de validar en el servidor, no solo necesitaremos el hash. Este código solo me sirve para codificar en md5 del lado del cliente. Ahora me las apañaré para que quién tenga solo el login y el hash se coma los mocos.

  • Eduardo dijo:

    POr lo visto este articulo es muuuuuy pero muyyyyyyy viejo, ya que php 4 y 5 incorpora la funcion md5... pero sirve de algo el javascript aqui. algo mas de seguridad ya que se envia desde el cliente la contraseña encriptada.

  • Eduardo dijo:

    POr lo visto este articulo es muuuuuy pero muyyyyyyy viejo, ya que php 4 y 5 incorpora la funcion md5... pero sirve de algo el javascript aqui. algo mas de seguridad ya que se envia desde el cliente la contraseña encriptada.

  • Loksly dijo:

    No tiene ningún sentido utilizar este sistema, pues no protege contra reenvío. Sería mejor que el número aleatorio se enviase desde el servidor, se almacenase en una variable $_COOKIE. Entonces en el lado del cliente se concatenaría el número aleatorio con el password y se enviaría. En el lado del servidor se recuperaría la variable "número aleatorio" almacenada en el array $_COOKIE y se simularía el proceso realizado en el cliente. Esta comprobación sería mucho más segura que la mostrada por el artículo.

  • Luis dijo:

    En respuesta a Loksly , tu solución es igual de inútil. Da lo mismo que el nº aleatorio se genere en el cliente o en el servidor. La cuestión es que es enviado y puede ser interceptado por un tercero que esté escuchando la red. Luego sólo tiene que repetir lo que tenía previsto hacer el cliente y hacerse pasar por él. Mirad (y esto va para todos), las técnicas basadas en cifrar simétricamente a base de secretos, en donde dichos secretos viajan por la red, no tienen sentido. Toda esta tontería de usar funciones hash en el lado del cliente no protege contra nada. El propio protocolo HTTP incorpora la posibilidad de usar MD5 para cifrar los passwords en el navegador (la famosa "autenticación digest"). Y en la especificación se deja claro que ese método es una medida de seguridad no confiable. Si realmente queréis seguridad dejad de reinventar la rueda (y lo que es peor, sin saber) y centraos en los certificados digitales con su correspondiente respaldo de terceros (Verisign y cia). El resto son ganas de perder el tiempo y, lo que es peor, de crear una falsa imagen de seguridad.

  • Juan Carlos dijo:

    Hola, me parece bárbaro el artículo y muy bueno el ejemplo, pero me gustaría que me expliques un poco la parte en que escribes: -“ y también la imposibilidad de encontrar dos cadenas de texto que generen el mismo resultado.” Te contradices con: -“ para comprobar si el password es correcto, se cifra de la misma manera y se comparan las formas cifradas.” ¿Si es imposible que de dos cadenas de texto se generen el mismo resultado, como hago para comparar la clave enviada y la que ya esta almacenada en el host? ¿ah?  Saludos.

  • Luis dijo:

    Tu respuesta titulada "pequeña gran contradición" no es tal, y sólo es fruto de no saber cómo funcionan las funciones hash de una sola vía. Lo que el autor ha querido decir con eso es que, conociendo un resumen criptográfico (hash) de una cadena, generar otra que tenga el mismo resumen (colisión) es difícil. Y dicha dificultad reside en la cantidad de hashes diferentes que puede generar la función, que en el caso de MD5 es de dos elevado a 128. Si una persona conoce un resumen criptográfico y quisiera conocer cuál es la cadena que ha dado lugar a ese hash, necesitaría en el peor de los casos 2 elevado a 128 intentos para conseguirlo peeeero, eso no le garantiza obtener la misma cadena (lo cual es casi imposible porque es de una posibilidad frente a infinito) sino que obtendrá otra cadena que produce el mismo hash. No obstante, a efectos de la autenticación sería válido ya que el servidor se basa en el hash obtenido, no en la cadena que lo ha generado. En resumidas cuentas: El autor ha escrito mal el texto al hablar sobre la "imposibilidad de encontrar dos cadenas de texto que generen el mismo resultado". Sí que se puede, y el caso peor está calculado. Lo que sucede es que es muy difícil (cada día menos debido a los ordenadores más rapidos). Por otro lado, cometes un error al tragarte este pastiche sobre autenticación y seguridad.

  • Alber dijo:

    Creo que es una vergüenza que alguien que parece de seguridad y que seguro que aprecia la informática diga: "dejad de reinventar la rueda". Si por algo la informática es tan rica hoy en dia es justo por "reinventar la rueda". Si tienes conocimiento de la evolución de la informática, sabrá que han surgido lenguajes como php, java habiendo cgi + C, o C respectivamente. "Reinventaron la rueda", pero haciendola válida para todos los coches y que se pudiera trabajar con ella más fácilmente. Bien, dicho esto, solo apuntar que este script no sirve de nada porque un sniffer tendria los datos del hash y del numero, con lo que no te sirve. Aqui el proposito es lograr una conexion segura sin htpps (claro que es lo ideal, pero paga tu eso). Desde luego enviar la contraseña encriptada en md5 en un gran paso para que un sniffer no sepa la contraseña original, sino solo el hash. Ahora, lo del numero es una tonteria porque un sniffer tambien te va a coger el numero. Y coge y envia el has con el numero ese y listo. La cuestion seria obligar al que envia la información a usar un numero en la codificación. Asi, si un sniffer lo intenta, el servidor no le hará caso ya que el numero que le manda el usuario no es el numero que el servidor queria. El problema de esto seria que habria que almacenar los numeros en alguna base de datos (mysql), y luego borrarlos. Habria que asociarlo con una id o con su ip, da lo mismo. La cuestion es que el servidor imponga un numero al azar. Luis, este metodo que progongo supongo que si que es seguro. El sniffer solo tiene un hash o varios hash con un numero que el no sabe cual es. Si esto lo hacemos con numero del 1 al 10000 o mas, tendria que almacenar cientos de hashes y hacerlo en el tiempo que se está autentificando el usuario. Es decir, que estamos ante un sistema seguro!

  • Raul Ramos dijo:

    ¡Es un buen metodo! y felicito al que publico y/o lo creo por que demuestra interes en el tema, mucho mas que aquellos que solo se dedican a criticar y no aportan nada. En cuanto al metodo y en mi opinion personal es bueno para proteger las contraseñas de tus usuarios y que no sean descubiertas por atancantes a la base de datos o por otras personas qu tengan acceso a la misma, como compañeros de trabajo o algo asi, pero no ofrece seguridad a nivel de Red, ya que para un snifer es indiferente si la contraseña viaja sifrada o no, solo necesita escuchar la red y replicar la misma informacion, si al contraseña va cifrada y es interferida tengo su resultado, para que necesito la clave original, el servidor no entiende que se le envie la clave original, el servidor entiende que ecibe una clave cifrada y eso es lo que le envio, de igual manera sucede si le envio la clave sin cifrar y es cifrada en el servidor. Repito, Felicito a la persona que publico este articulo, y hago enfasis en su utilidad para impedir que la contraseña de un usuario sea leida por personas que tengan acceso a la base de datos, no funciona a nivel de red, para la seguridad a nivel de Red se requie un canal seguro como con https, que proporciona como una especie de canal invisible a los snifer entre el cliente y el servidor

  • pepe terminnator dijo:

    Amigos, si no limpian el campo password no sirve el método propuesto ya que el password se transmite por la red en texto plano!

Conéctate o Regístrate para dejar tu comentario.