<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"> <HTML> <HEAD> <META http-equiv="Content-Type" content="text/html; charset=iso-8859-1"> <META NAME="GENERATOR" CONTENT="lfparser_2.34"> <META NAME="LFCATEGORY" CONTENT="SystemAdministration"> <link rel="icon" href="../../common/images/lf-16.png" type="image/png"> <TITLE>lf273, SystemAdministration: Asegurando tus conexiones con SSH</TITLE> <style type="text/css"> <!-- td.top {font-family: Arial,Geneva,Verdana,Helvetica,sans-serif; font-size:12 } pre { font-family:monospace,Courier } p.cl { color:#EE9500 } a.nodec { text-decoration:none } p.trans { font-size:8pt; text-align:right } p.clbox { width:50%; alignment:center; background-color:#FFD700; border-style:none; border-width:medium; border-color:#FFD700; padding:0.5cm; text-align:center } p.code { width:80%; alignment:center; background-color:#aedbe8; border-style:none; border-width:medium; border-color:#aedbe8; padding:0.1cm; text-align:left } p.foot { background-color:#AAAAAA; color:#FFFFFF; border-style:none; border-width:medium; border-color:#AAAAAA; padding:0.5cm ; margin-top:0.1cm; margin-right:1cm; margin-left:1cm; text-align:center } .mark { background-color:#e6e6ff } --> </style> </HEAD> <BODY bgcolor="#ffffff" text="#000000"> <!-- this is generated html code. NEVER use this file for your translation work. Instead get the file with the same article number and .meta.shtml in its name. Translate this meta file and then use lfparser program to generate the final article --> <!-- lfparser can be obtained from http://www.linuxfocus.org/~guido/dev/lfparser.html --> <!-- this is used by a number of tools: =LF=AUTHOR: Bernard Perrot =LF=CAT___: SystemAdministration =LF=TITLE_: Asegurando tus conexiones con SSH =LF=NUMBER: 273 =LF=ANAME_: article273.html --> <!-- 2pdaIgnoreStart --> <!-- start navegation bar --> <!-- top navegation bar --> <TABLE summary="topbar_1" cellspacing="0" cellpadding="0" border="0" align="center" width="90%"> <TR bgcolor="#2e2292"> <TD class="top"><TABLE summary="topbar_1_logo" cellspacing="0" cellpadding="0" border="0" width= "100%"> <TR><TD width="319"><IMG src="../../common/images/logolftop_319x45.gif" alt="[LinuxFocus-icon]" width="319" height="45" align="left" border="0"></TD> <TD class="top"> <TABLE summary="topbar_1_links" width="100%"> <TR align="right"> <TD class="top"><A class="nodec" href="../index.shtml"><FONT color= "#DDDDDD" size="2">Hogar</FONT></A> | <A class= "nodec" href="../map.html"><FONT color= "#DDDDDD" size="2">Mapa</FONT></A> | <A class= "nodec" href="../indice.html"><FONT color= "#DDDDDD" size="2">Indice</FONT></A> | <A class="nodec" href="../Search/index.html"><FONT color= "#DDDDDD" size="2">Busqueda</FONT></A> </TD> </TR> <TR align="right"> <TD class="top"> <HR width="100%" noshade size="1"> </TD> </TR> </TABLE> </TD> </TR> </TABLE> </TD> </TR> </TABLE> <!-- end top navegation bar --> <!-- blue bar --> <TABLE summary="topbar_2" cellspacing="0" cellpadding="0" border="0" align="center" width="90%"> <TR bgcolor="#00ffff"> <TD><IMG src="../../common/images/transpix.gif" width="1" height= "2" alt=""></TD> </TR> </TABLE> <!-- end blue bar --> <!-- bottom navegation bar --> <TABLE summary="topbar_3" cellspacing="0" cellpadding="0" border="0" align="center" width="94%"> <TR bgcolor="#000000"> <TD> <TABLE summary="topbar_3_links" cellspacing="0" cellpadding="1" border="0" width= "100%"> <TR align="center"> <TD WIDTH="20%"><A class="nodec" href="../News/index.shtml"><FONT color= "#FFFFFF">Noticias</FONT></A> </TD> <TD WIDTH="5%"><FONT color="#FFFFFF">|</FONT> </TD> <TD WIDTH="20%"><A class="nodec" href="../Archives/index.html"><FONT color= "#FFFFFF">Arca</FONT></A> </TD> <TD WIDTH="5%"><FONT color="#FFFFFF">|</FONT> </TD> <TD WIDTH="20%"><A class="nodec" href="../Links/index.html"><FONT color= "#FFFFFF">Enlaces</FONT></A> </TD> <TD WIDTH="5%"><FONT color="#FFFFFF">|</FONT> </TD> <TD WIDTH="20%"><A class="nodec" href="../aboutus.html"><FONT color= "#FFFFFF">Sobre LF</FONT></A> </TD> </TR> </TABLE> </TD> </TR> </TABLE> <!-- end bottom navegation bar --> <!-- stop navegation bar --> <!-- SSI_INFO --> <!-- tr_staticssi include virtual --> <!-- tr_staticssi exec cmd --> <!-- addedByLfdynahead ver 1.4 --><TABLE ALIGN="right" border=0><TR><TD ALIGN="right"><FONT SIZE="-1" FACE="Arial,Helvetica">Este documento está disponible en los siguientes idiomas: <A href="../../English/March2003/article273.shtml">English</a> <A href="../../Castellano/March2003/article273.shtml">Castellano</a> <A href="../../Deutsch/March2003/article273.shtml">Deutsch</a> <A href="../../Francais/March2003/article273.shtml">Francais</a> <A href="../../Nederlands/March2003/article273.shtml">Nederlands</a> <A href="../../Turkce/March2003/article273.shtml">Turkce</a> </FONT></TD></TR></TABLE><br> <!-- SSI_INFO STOP --> <!-- 2pdaIgnoreStop --> <!-- SHORT BIO ABOUT THE AUTHOR --> <TABLE ALIGN=LEFT BORDER=0 WIDTH="190" summary="about the author"> <TR> <TD> <!-- 2pdaIgnoreStart --> <!-- PALM DOC --> <TABLE BORDER=0 hspace=4 vspace=4 summary="pda download"> <TR> <TD> <font size=1> <img src="../../common/images/2doc.gif" width=34 align=left border=0 height=22 alt="convert to palm"><a href="http://cgi.linuxfocus.org/cgi-bin/2ztxt">Convert to GutenPalm</a><br>or <a href="http://cgi.linuxfocus.org/cgi-bin/2pda">to PalmDoc</a></font> </TD> </TR> </TABLE> <!-- END PALM DOC --> <!-- 2pdaIgnoreStop --> <br> <img src="../../common/images/bernard.perrot.jpg" width="100" height="138" alt="Bernard Perrot"> <BR>por Bernard Perrot <br> <small><bernard.perrot(at)univ-rennes1.fr></small> <BR><BR> <I>Sobre el autor:</I><BR> <!-- aboutauthor_start --> Bernard ha sido el Ingeniero de red y sistemas del CNRS (Centro Nacional de Investigaciones Científicas de Francia) desde 1982. Ha estado a cargo de los proyectos relativos a la seguridad del sistema informático en el "Instituto nacional de física nuclear y física de las partículas" (In2p3). Ahora, trabaja para el Instituto de investigación matemática (IRMAR) en el Departamento de ciencias físicas y matemáticas (SPM).<br><br> <!-- aboutauthor_stop --> <!-- TRANSLATED TO es --> <BR><BR><I>Taducido al español por:</I><BR> Javier Gómez Sierras <small><jgomsi(at)obelix.umh.es></small> <br> <!-- =LF=TRANSTO=es: Javier Gómez Sierras --> <!-- TRANSLATED TO STOP --> <BR><i>Contenidos</i>: <UL> <LI><A HREF="#273lfindex0">¿Para qué se usa SSH?</A></LI> <LI><A HREF="#273lfindex1">¿Qué se necesita?</A></LI> <LI><A HREF="#273lfindex2">Manejando un montón de claves</A></LI> <LI><A HREF="#273lfindex3">Los algoritmos de cifrado</A></LI> <LI><A HREF="#273lfindex4">Redirección de puertos, túneles</A></LI> <LI><A HREF="#273lfindex5">Principales distribuciones: disponibles gratuitamente</A></LI> <LI><A HREF="#273lfindex6">OpenSSH </A></LI> <LI><A HREF="#273lfindex7">Malas noticias...</A></LI> <LI><A HREF="#273lfindex8">Explotando el canal cubierto (inducido por el relleno aleatorio en SSHv1)</A></LI> <LI><A HREF="http://cgi.linuxfocus.org/cgi-bin/lftalkback?anum=273">Formulario de "talkback" para este artículo</A></LI> </UL> </TD></TR></TABLE> <!-- HEAD OF THE ARTICLE --> <br> <table border="0"><tr><td> <H2>Asegurando tus conexiones con SSH</H2> <img src="../../common/images/illustration273.gif" alt="ssh" hspace="10" width="320" height="95"> <!-- ABSTRACT OF THE ARTICLE --> <P><i>Resumen</i>: <P> <!-- articleabstract_start --> <p>Este artículo se publicó por primera vez en un número especial de Linux Magazine France enfocado a la seguridad. El editor, los autores y los traductores permitieron amablemente a LinuxFocus publicar todos los artículos de este número especial. En consecuencia, LinuxFocus los publicará tan pronto como estén traducidos al inglés. Gracias a todas las personas implicadas en este trabajo. Este resumen se mostrará en todos los artículos que procedan de la misma fuente.<p><p>El propósito de este artículo es realizar un buen repaso de SSH, y por qué se usa. Esto no es un manual o guía de instalación, sino una introducción al vocabulario y las características de SSH. Los enlaces y la documentación que aparecen durante todo el artículo, te darán todos los detalles de la implementación. </p> <!-- articleabstract_stop --> <br><!-- HR divider --><center><font color="#8282e0"><b>_________________ _________________ _________________</b></font></center><br> </td></tr></table> <!-- BODY OF THE ARTICLE --> <A NAME="273lfindex0"> </A> <H2>¿Para qué se usa SSH?</H2> <p>Primero de todo (e históricamente), SSH (el comando <i>ssh</i>) es una versión segura de los comandos <i>rsh</i> (y <i>rlogin</i>). SSH significa "<i>Secure SHell -- shell segura</i>" y <i>rsh</i> significa "<i>Remote SHell -- shell remota</i>". Por lo tanto, mientras que <i>rsh</i> te da un acceso a una shell remota fácilmente, pero sin un mecanismo de autentificación de usuario, <i>ssh</i> proporciona el mismo servicio pero con una seguridad multinivel muy alta.</p> <p>Si quisiéramos dar una explicación muy breve a un usuario que no quiere saber nada más (o hacer nada más), uno se podría para aquí y decir el administrador ha hecho su trabajo y ha instalado el software (esto es bastante fácil hoy en día), todo lo que tienes que hacer es reemplazar los comandos <i>telnet, rsh</i> o <i>rlogin</i> por el comando <i>ssh</i>, y todo funcionará igual pero con más seguridad. </p> <p>Por lo tanto, donde hacías:</p> <p> <tt>% rlogin servidor.org</tt> (o <tt>telnet servidor.org</tt>)</p> <p>ahora tienes que hacer:</p> <p> <tt>% ssh servidor.org</tt></p> <p>¡y es mucho mejor!</p> <p>Para terminar este breve resumen, sugeriré que hoy en día, todos los incidentes de seguridad que podrían haber sido evitados simplemente usando SSH en vez de <i>rsh</i> (<i>rlogin</i>,<i>telnet</i>) son principalmente consecuencia de la negligencia de las víctimas.</p> <A NAME="273lfindex1"> </A> <H2>¿Qué se necesita?</H2> <p>Para ver los detalles, aquí tienes algunos de los aspectos más importantes y frágiles de las conexiones interactivas que uno quiere ver resueltos:</p> <ul> <li>El primero de todos, evitar que las contraseñas se transmitan a través de la red</li> <li>uso de autentificación fuerte en los sistemas a conectar, pero no sólo basado en el nombre o dirección IP que están sujetos a spoofing;</li> <li>ejecución de comandos remotos con total seguridad.</li> <li>protección de las transferencias de ficheros;</li> <li>securización de las sesiones X11 que son muy vulnerables</li> </ul> <p>Para responder a estas necesidades, existen algunas soluciones que no son del todo satisfactorias:</p> <ul> <li>Los "<i>R-commands</i>": estos comandos no transmiten las contraseñas en texto plano pero el mecanismo "rhosts" usando está sujeto a numerosos problemas de seguridad,</li> <li>Los "<i>Contraseñas de un solo uso -- One Time Password</i>, (OTP)": protegen sólo la autentificación y no el flujo de datos que le sigue. Aunque este sistema es muy atractivo desde el punto de vista de la seguridad, tiene unas limitaciones que lo hacen un sistema difícil de aceptar por parte de los usuarios. Consecuentemente se aplica mayoritariamente en entornos que no están sujetos a consideraciones de ergonomía;</li> <li>telnet con cifrado: esta solución sólo es aplicable ... a telnet. A parte, no incluye al protocolo X11, un complemento a menudo necesario.</li> </ul> <p>Y tenemos SSH, una buena solución para:</p> <ul> <li>reemplazo de los <i>R-commands</i>: <i>ssh</i> en vez de <i>rsh</i> y <i>rlogin</i>, <i>scp</i> con <i>rcp</i>, <i>sftp</i> con <i>ftp</i>;</li> <li>uso de autentificación fuerte, basada en algoritmos de cifrado usando claves públicas (tanto para sistemas como usuarios);</li> <li>capacidad de redirigir el flujo de datos TCP en un "tunel" por sesión y en particular en sesiones X11 donde se puede hacer automáticamente;</li> <li>Cifrado del tunel, y cuando sea necesario y especificado, comprimirlo.</li> </ul> <h4>SSH versión 1 y SSH versión 2</h4> <p>Como nada en este mundo es perfecto, existen dos versiones incompatibles del protocolo SSH: la versión 1.x (1.3 y 1.5) y la versión 2.0. Pasar de una versión a la otra no es doloroso para el usuario, teniendo a mano el cliente correcto y el servidor correcto compatible con la versión.</p> <p>La versión 1 del protocolo SSH está integrada, mientras que la versión 2 ha definido el protocolo anterior en tres "capas":</p> <ol> <li>Capa de transporte del protocolo SSH (SSH-TRANS)</li> <li>Autentificación del protocolo SSH (SSH-AUTH)</li> <li>Conexión del protocolo SSH (SSH-CONN)</li> </ol> <p>Cada capa del protocolo está definida específicamente en un documento (borrador) normalizado por la IETF, seguido de un cuarto borrador que describe la arquitectura (Arquitectura del protocolo SSH, SSH-ARCH). Se pueden encontrar todos los detalles en: <a href= "http://www.ietf.org/html.charters/secsh-charter.html">http://www.ietf.org/html.charters/secsh-charter.html</a></p> <p>Sin meternos en muchos detalles, aquí tienes lo que encontrarás en SSHv2:</p> <ul> <li>la capa de transporte proporciona integridad, cifrado, y compresión, la autentificación de sistemas</li> <li>la capa de autentificación proporciona ... autentificación (contraseña, basada en máquina, clave pública)</li> <li>la capa de conexión que gestiona el túnel (shell, agente SSH, redirección de puertos, control del flujo).</li> </ul> <p>Las principales diferencias técnicas entre la versión 1 de SSH y la versión 2 son:</p> <table border="1" width="582" cellpadding="1" bgcolor="#aedbe8"> <tr valign="TOP"> <th> <p>SSH versión 1</p> </th> <th> <p>SSH versión 2</p> </th> </tr> <tr> <td> <p>diseño monolítico (integrado)</p> </td> <td> <p>separación de las funciones de autentificación, conexión y transporte en capas</p> </td> </tr> <tr> <td> <p>integridad via CRC32 (no seguro)</p> </td> <td> <p>integridad via HMAC (cifrado hash)</p> </td> </tr> <tr> <td> <p>un único canal por sesión</p> </td> <td> <p>un número ilimitado de canales por sesión</p> </td> </tr> <tr> <td> <p>negociación usando únicamente cifrado simétrico en el canal, identificación de sesión con una única clave en ambos lados</p> </td> <td> <p>negociación más detallada (cifrado simétrico, llave pública, compresión, ...), y una clave de sesión independiente, compresión e integridad en ambos lados</p> </td> </tr> <tr> <td> <p>sólo RSA para el algoritmo de clave pública</p> </td> <td> <p>RSA y DSA para el algoritmo de clave pública</p> </td> </tr> <tr> <td> <p>clave de sesión transmitida por el cliente</p> </td> <td> <p>clave de sesión negociada por el protocolo Diffie-Hellman</p> </td> </tr> <tr> <td> <p>clave de sesión válida para toda la sesión</p> </td> <td> <p>clave de sesión renovable</p> </td> </tr> </table> <A NAME="273lfindex2"> </A> <H2>Manejando un montón de claves</H2> <p>Tipos de claves SSH, las definiré rápidamente:</p> <ul> <li>Clave de usuario: un par de claves compuestas de una clave pública y otra privada (ambas asimétricas), definidas por el usuario y permanentes (se guardan en el disco). Estas claves permiten la autentificación de usuario si se utiliza el método de autentificación de clave pública (descrito más adelante).</li> <li>Clave de máquina: también un par de claves compuestas de una llave pública y otra privada (ambas asimétricas), pero definidas al instalar/configurar SSH por el administrador del servidor y permanentes (guardadas en el disco). Esta clave permite la autentificación entre sistemas.</li> <li>Clave de servidor: de nuevo un par de claves compuestas de una clave pública y otra privada (ambas asimétricas), pero generadas por un demonio al iniciarse y renovadas regularmente. Esta clave permanece en memoria para asegurar el intercambio de la clave de sesión en SSHv1 (con SSHv2, no hay clave de servidor ya que el intercambio se asegura con el protocolo Diffie-Hellman).</li> <li>Clave de sesión: esta es una clave secreta usada por el algoritmo de cifrado simétrico para cifrar el canal de comunicación. Como es en todos los productos modernos de criptografía, la clave es aleatoria y perecedera. SSHv1 tiene una clave por sesión, en ambos lados. SSHv2 tiene dos claves de sesión regeneradas, una en cada lado.</li> </ul> <p>El usuario añade una frase de paso (pass phrase) que protege la parte privada de las anteriores claves. Esta protección se asegura cifrando el fichero que contiene la clave privada con un algoritmo simétrico. La clave secreta usada para cifrar el fichero se deriva de esta frase de paso.</p> <h4>Métodos de autentificación</h4> <p>Hay varios métodos de autentificación de usuario, la elección depende de la necesidades definidas en las políticas de seguridad. Los métodos autorizados se activan o no en el fichero de configuración del servidor. Aquí están las principales categorías:</p> <ul> <li> <b>"similar a telnet":</b> <p>Este es el "tradicional" método de la contraseña: al conectar, después de haber introducido nuestro identificador, se le pide al usuario que introduzca una contraseña que se envía al servidor que la compara con la que tiene asociada a dicho usuario. El problema residual (el que causa una cifra astronómica actos delictivos en Internet) es que la contraseña se envía a la red <i>en claro</i>, y por lo tanto puede ser interceptada por cualquiera que que tenga un simple "<i>sniffer</i>" (capturador de paquetes). En este caso SSH tiene la misma apariencia (es un modo fácil usuarios inexpertos que migran de telnet a SSH, ya que no hay nada nuevo que aprender ...), no obstante el protocolo SSH cifra el canal y la contraseña en claro se encapsula. </p> <p>Una variante incluso más segura, configurable si uno tiene lo necesario en el servidor es el uso de una "<i>Contraseña de un solo uso -- One time password</i>" (S/Key por ejemplo): seguramente es mejor, obviamente más seguro, pero las limitaciones de ergonomía lo hacen aplicable únicamente a situaciones particulares. Este sistema opera como sigue: después de introducir nuestro identificador, en vez de preguntar al usuario una contraseña (estática), el servidor envia un "<i>desafío</i>" al que el usuario debe responder. Dado que el desafío debe ser diferente, la respuesta debe también cambiar. En consecuencia, la interceptación de la respuesta no es importante ya que no puede ser reusada. La limitación, como se mencionó, viene esencialmente de la codificación de la respuesta que debe ser calculada (por un token, software en el lado cliente, etc.), y la entrada es bastante "cabalística" (seis monosílabos ingleses, en el mejor de los casos).<br> </p> </li> <li> <b>"similar a rhosts"</b> (<i>basados en la máquina</i>): <p>En este caso la identificación es similar a la de los R-commands con ficheros como /etc/rhosts o ~/.rhosts, que "certifican" los sitios clientes. SSH sólo contribuye a una mejor identificación del sitio, y al uso de de ficheros "<i>shosts</i>" privados. Esto no es suficientemente recomendable desde el punto de vista de la seguridad y no recomiendo usar este método si se utiliza sin más.</p> </li> <li> <b>Por claves públicas</b> <p>En este caso, el sistema de autentificación se basa en el cifrado asimétrico (para más detalles ver el <a href="../May2002/article243.shtml">artículo sobre criptografía</a>; básicamente, SSHv1 usa RSA, y SSHv2 ha introducido DSA). La clave pública del usuario se registra de antemano en el servidor y la clave privada se guarda en el cliente. Con este sistema de autentificación, ningún secreto viaja a través de la red ni es enviado al servidor.</p> <p>Este sistema es excelente, y sin embargo, su seguridad está limitada (desde mi punto de vista) por ser casi exclusivamente dependiente de la "seriedad" del usuario (este problema no es particular de SSH, sino que creo es el EL principal problema de los sistemas de clave pública, como los actualmente populares sistemas PKI): por lo tanto, para evitar un compromiso de la clave pública del ordenador cliente, la clave se protege con una contraseña (a menudo llamada <i>palabra de paso -- pass phrase</i> para enfatizar la necesidad de usar más de una <i>palabra</i>). Si el usuario no protege cuidadosamente (o simplemente NO protege) su clave privada, alguien puede usarla fácilmente para conseguir acceder a todos sus recursos. Es por esto por lo que digo que la seguridad recae en la seriedad del usuario y su nivel de confianza, ya que en este sistema el administrador del servidor <i>no</i> tiene ninguna manera de saber si la clave privada está protegida o no. Hoy en día, SSH no administra listas de revocación (no lo hacen muchos, ni siquiera PKI...). Por ejemplo, si una clave privada se guarda sin una frase de paso en el ordenador de casa (no hay ningún chico malo en casa, así que para qué preocuparse por una frase de paso...) y un día se lleva al servicio de reparación de un distribuidor importante ( no os riáis, esto es lo que va a pasar cuando las firmas electrónicas sean comunes...), el encargado de la reparación ( su hijo, sus amigos ) podrán conseguir las claves privadas de cualquier ordenador que pase por sus mesas.</p> <p>Configurar el mecanismo de autentificación para el usuario es ligeramente diferente si uno usa SSHv1, SSHv2, o OpenSSH, también en el caso de un cliente MacOS<sup>tm</sup> o Windows<sup>tm</sup>. Los principios básicos y los pasos a recordar son:</p> <ul> <li>Generar un "par de claves asimétricas" (esto es un par de claves pública/privada RSA o DSA), la mayoría de veces en el sistema cliente, (si varios sistemas clientes se conectan entonces generamos el par de claves en uno de los clientes y después replicamos las claves en los otros clientes). Algunos de los clientes de Windows<sup>tm</sup> y MacOS<sup>tm</sup> no tienen ninguna utilidad para generar el par de claves, se tiene que hacer la generación en una máquina Unix antes de duplicar las claves. El par de claves se registra en el directorio de usuario <tt>~/.ssh</tt>.</li> <li>Copiar una clave pública a los servidores que se usarán para la autentificación. Esto se hace añadiendo una línea, que corresponde al par de claves generado del directorio de usuario ~/.ssh, a un fichero en el mismo directorio del servidor. (El nombre depende de la versión SSH, tanto <tt>authorized_keys</tt> o <tt>authorization</tt>).</li> <li>Y eso es todo... si la configuración requiere una autentificación mayor a nivel de servidor, entonces el cliente preguntará una "<i>frase de paso</i>" al conectar.<br> </li> </ul> </li> </ul> <p>También, es útil saber al menos dos elementos más referentes a la autentificación:</p> <ul> <li> <b>ssh-agent</b> <p>Una de las razones por las que uno no protege su clave privada es lo molesto que resulta tener que introducir la clave en cada conexión interactiva y la imposibilidad de usar conexiones ssh en scripts que corran en segundo plano. Existe un remedio, el <i>Agente SSH -- SSH agent</i>. Es un programa (<i>ssh-agent</i>), que una vez activado por el usuario, te ayuda a almacenar el identificador de tres parámetros (nombre de usuario, nombre del servidor, frase de paso), y envia por ti el identificador cuando se realiza una conexión. En el lado cliente, la contraseña se pregunta una sola vez, así que lo podríamos llamar SSO (<i>Single Sign On -- Registro único</i>).</p> <p>Ahora que estas informado, nada te obliga a proteger tus claves privadas, pero si no lo haces, será una negligencia por tu parte, y tú serás el responsable de las consecuencias.</p> </li> <!-- guido --> <li> <b>modo <i>"prolijo"</i> -- "<i>verbose</i>" mode</b> <p>Puede pasar que la conexión falle por motivos que el usuario desconoce: simplemente añade la opción "<tt>-v</tt>" (viene de "<i>verbose</i>", "prolijo, verboso") al comando <i>ssh</i>. Con esta opción, aparecerán numerosos mensajes detallados en la pantalla durante la conexión, lo que a menudo te dará suficiente información para determinar la causa del fallo.</p> </li> </ul> <A NAME="273lfindex3"> </A> <H2>Los algoritmos de cifrado</H2> <p>Se debe distinguir entre los que cifran los canales de comunicación (cifrando con claves secretas) y los que se usan para la autentificación (cifrando con claves públicas).</p> <p>Para la autenticación, podemos elegir entre RSA y DSA con la versión 2 del protocolo, y únicamente RSA con la versión 1 (no hay elección posible...). Históricamente se eligió DSA porque RSA estaba <i>patentado</i> en algunos países. Desde finales del verano del año 2000, RSA está libre de derechos, y por lo tanto esta restricción ha desaparecido. No tengo preferencia sobre si la elección buena y la mala (y más cuando DSA es un producto "puro" de la NSA, aunque halla sido esta quien lo ha puesto directa o indirectamente a disposición de la criptografía pública y comercial...¿?) </p> <p>Para el cifrado simétrico existen casi demasiados donde elegir... El protocolo impone un algoritmo común que tiene que estar presente en todas las implementaciones : el <i>triple-DES con tres claves</i>. En consecuencia, siempre se usará si la negociación entre el cliente y el servidor falla con los otros algoritmos. Si puedes, prueba a negociar con otro algoritmo, que será mejor, ya que que 3DES es hoy en día uno de los algoritmos de menor rendimiento. No obstante dejaremos de lado, a menos que sea necesario, los exóticos o antiguos (arc4, DES, RC4, ...) y nos limitaremos a:</p> <ul> <li>IDEA: tiene un mejor rendimiento que 3DES, pero no es completamente libre de licencias bajo ciertas condiciones (era a menudo el algoritmo por defecto en las versiones Unix);</li> <li>Blowfish: muy rápido, posiblemente seguro, pero el algoritmo tiene que ser probado más tiempo;</li> <li>AES: el nuevo estándar (reemplaza a DES), si está disponible en ambos lados, entonces úsalo, está hecho para esto.</li> </ul> <p>Personalmente, me pregunto a mi mismo sobre el interés que tiene proponer tanto algoritmos: incluso aunque el protocolo permite la posibilidad de negociar "uno privado" ( para un grupo particular de usuarios, por ejemplo), algo que me parece esencial, pero para el uso normal, creo que con el tiempo, AES está llamado a convertirse en el estándar. Si AES fuera comprometido, entonces los problemas de seguridad serían mucho mayores que los que pudiese inducir SSH...</p> <A NAME="273lfindex4"> </A> <H2>Redirección de puertos, túneles</H2> <p>SSH permite la redirección (<i>forwarding</i>) de cualquier flujo de datos TCP a través de un "túnel" en una sesión SSH. Esto significa que el flujo de datos de la aplicación, en vez de ser gestionada directamente por los puertos del servidor y el cliente, es "encapsulada" en un "túnel" creado al conectar (inicio de sesión) (<i>ver el siguiente diagrama</i>).</p> <p>Esto mismo se hace con el protocolo X11 sin ningún esfuerzo especial (por parte del usuario), con un manejo transparente de los <i>displays</i> y la capacidad de propagarse continuamente cuando se realizan varias conexiones.</p> <p>Para otros flujos, existe una opción de línea de comandos, para cada lado:<br> </p> <ul> <li> Conexión directa entre el cliente y servidor<br> <p><img src="../../common/images/article273/SSH.gif" alt= "SSH.gif" width="356" height="121"></p> <p>(ejemplo: <tt>usuario@alice% telnet bob.org)<br> </tt></p> </li> <li> Redirección de un puerto local (cliente) a un puerto remoto (servidor) <p><img src="../../common/images/article273/SSH4.gif" alt= "SSH4.gif" width="356" height="211"></p> <p>ejemplo: <tt>usuario@alice% ssh -L 1234:bob.org:143 bob.org</tt></p> <p>este sistema permite el acceso desde "<i>alice.org</i>" a el servidor imap de "<i>bob.org</i>",<br> las conexiones externas a la red local serán rechazadas. Únicamente estarán disponibles a través del la dirección <i>localhost</i>, puerto 1234, desde el cliente imap ejecutado en "<i>alice.org</i>".</p> <ul> <li>(1) el usuario en "<i>alice.org</i>" abre (realiza una conexión) el túnel SSH</li> <li>(2) el usuario de <i>"alice.org"</i> configura el cliente local de imap para acceder al<br> servidor imap que se encuentra en <i>localhost</i> puerto 1234<br> </li> </ul> <br> <br> </li> <li> Redirección de un puerto remoto (cliente) a un puerto local (servidor)<br> <p><img src="../../common/images/article273/SSH5.gif" alt= "SSH5.gif" width="356" height="215"></p> <p>ejemplo: <tt>root@alice% ssh -R 1234:bob.org:143 bob.org</tt></p> <p>Esto es lo mismo que antes pero el puerto en la máquina remota se redirecciona. Únicamente root tiene los privilegios necesarios para ejecutar este comando SSH pero cualquier usuario puede usar este puerto redirigido/túnel. </li> </ul> </li> </ul> <p>Esta potente característica ha llevado algunas veces a calificar a SSH como "un túnel para pobres". Se debe comprender que la pobreza aquí significa: aquellos que no tienen privilegios de administrador en el lado cliente. Sólo en casos particulares se puede redirigir un puerto local con menos privilegios ( puertos > 1024) y sin privilegios de superusuario ("<i>root</i>"). Por otro lado, cuando se necesita redirigir un puerto local con privilegios, se tiene que hacer con la cuenta de <i>root</i>, o el cliente debe tener privilegios de superusuarios ("<i>suid</i>") (De hecho, un puerto local privilegiado permite la redefinición de un servicio estándar).</p> <p>Como con IP, es bastante fácil meter cualquier cosa en cualquier cosa (y lo contrario), no solo es posible redirigir un flujo TCP, sino también las conexiones PPP, lo que nos permite hacer un túnel IP "real" en IP (que está cifrado, por lo tanto seguro). El método excede el objetivo de este artículo, pero puedes leer el "<a href="http://www.linuxdoc.org/HOWTO/VPN-HOWTO.html">Linux VPN-HOWTO</a>" para conocer los detalles y obtener scripts de instalación (también podrás encontrar soluciones nativas VPN para Linux, como "<i>stunnel</i>" que deberías considerar antes de realizar la elección final).</p> <p>Ten presente que la primera posibilidad es redirigir los flujos de <i>telnet</i>: Esto podría parecer totalmente inútil, ya que SSH implementa una conexión interactiva por defecto. Sin embargo, al redirigir las conexiones <i>telnet</i>, podrías usar tu cliente favorito en vez del modo SSH interactivo. Esto es realmente valioso en entornos Windows<sup>tm</sup> o MacOS<sup>tm</sup> donde los clientes SSH puede que no se adecuen a la ergonomía preferida por el usuario. Por ejemplo, la "emulación de terminal" parte del cliente "<i>Mindterm</i>" (cliente SSH en Java, presente en todos los sistemas modernos) sufre la escasez de rendimiento del lenguaje Java: puede ser ventajoso usar este cliente únicamente para abrir un túnel SSH. <p>De la misma manera, también puedes iniciar un cliente remoto como "<i>xterm</i>" (por ejemplo, usando redirección X11 automática -- <i>automatic X11 forwarding</i> -- en SSH), lo que nos permite usar SSH en terminales X. </p> <p>Ten en cuenta que el túnel permanece abierto mientras halla un flujo de datos, incluso aunque no venga del que lo inició. Por lo tanto, el comando "<i>sleep</i>" es muy útil para abrir un túnel SSH para redirigir una nueva conexión TCP.</p> <p><tt> % ssh -n -f -L 2323:serveur.org:23 serveur.org sleep 60</tt></p> <p><tt> % telnet localhost 2323</tt></p> <p><tt> ... bienvenido a serveur.org ...</tt></p> <p>La primera línea abre el túnel, lanza el comando "<i>sleep 60</i>" en el servidor, y redirige el puerto local número 2323 al puerto remoto (<i>telnet</i>) número 23. El segundo inicia un cliente <i>telnet</i> en el puerto local número 2323, y entonces usará el túnel (cifrado) para conectarse al demonio <i>telnetd</i> del servidor. El comando "<i>sleep</i>" terminará después de un minuto (tienes sólo un minuto para iniciar telnet) , pero SSH sólo cerrará el túnel cuando el último cliente halla terminado.</p> <A NAME="273lfindex5"> </A> <H2>Principales distribuciones: disponibles gratuitamente</H2> <p>Tenemos que distinguir entre los clientes y/o servidores en las diferentes plataformas y deberías saber que la SSH versión 1 y SSH versión 2 son incompatibles. Las referencias al final del artículo te ayudarán a encontrar otras implementaciones, que no se incluyen en la siguiente tabla que se limita a los productos gratuitos con características suficientemente estables.</p> <table border="1" width="553" cellpadding="1" bgcolor="#aedbe8"> <tr> <th> <p>producto</p> </th> <th> <p>plataforma</p> </th> <th> <p>protocolo</p> </th> <th> <p>enlace</p> </th> <th> <p>notas</p> </th> </tr> <tr> <td> <p>OpenSSH</p> </td> <td> <p>Unix</p> </td> <td> <p>versiones 1 y 2</p> </td> <td> <p><a href= "http://www.openssh.com/">www.openssh.com</a></p> </td> <td> <p>detalles debajo</p> </td> </tr> <tr> <td> <p>TTSSH</p> </td> <td> <p>Windows<sup>tm</sup></p> </td> <td> <p>versión 1</p> </td> <td> <p><a href= "http://www.zip.com.au/~roca/ttssh.html">www.zip.com.au/~roca/ttssh.html</a></p> </td> <td> </td> </tr> <tr> <td> <p>Putty</p> </td> <td> <p>Windows<sup>tm</sup></p> </td> <td> <p>versiones 1 y 2</p> </td> <td> <p><a href= "http://www.chiark.greenend.org.uk/~sgtatham/putty/">www.chiark.greenend.org.uk/~sgtatham/putty</a></p> </td> <td> <p>sólo beta</p> </td> </tr> <tr> <td> <p>Tealnet</p> </td> <td> <p>Windows<sup>tm</sup></p> </td> <td> <p>versiones 1 y 2</p> </td> <td> <p><a href= "http://telneat.lipetsk.ru/">telneat.lipetsk.ru</a></p> </td> <td> </td> </tr> <tr> <td> <p>SSH secure shell</p> </td> <td> <p>Windows<sup>tm</sup></p> </td> <td> <p>versiones 1 y 2</p> </td> <td> <p><a href="http://www.ssh.com/">www.ssh.com</a></p> </td> <td> <p>gratuito para uso no comercial</p> </td> </tr> <tr> <td> <p>NiftytelnetSSH</p> </td> <td> <p>MacOS<sup>tm</sup></p> </td> <td> <p>versión 1</p> </td> <td> <p><a href= "http://www.lysator.liu.se/~jonasw/freeware/niftyssh/">www.lysator.liu.se/~jonasw/freeware/niftyssh/</a></p> </td> <td> </td> </tr> <tr> <td> <p>MacSSH</p> </td> <td> <p>MacOS<sup>tm</sup></p> </td> <td> <p>versión 2</p> </td> <td> <p><a href= "http://www.macssh.com/">www.macssh.com</a></p> </td> <td> </td> </tr> <tr> <td> <p>MindTerm</p> </td> <td> <p>Java</p> </td> <td> <p>versión 1</p> </td> <td> <p><a href= "http://www.mindbright.se/">www.mindbright.se</a></p> </td> <td> <p>v2 ahora comercial</p> </td> </tr> </table> <p>Ten en cuenta que MindTerm es tanto una implementación independiente en Java (sólo necesitas el <i>runtime</i> de Java ) como un <i>servlet</i> que se puede ejecutar dentro de un un navegador web compatible y bien diseñado. Desafortunadamente, las últimas versiones de esta excelente distribución han pasado a ser productos comerciales.</p> <A NAME="273lfindex6"> </A> <H2>OpenSSH </H2> <p>Hoy en día esta distribución es probablemente la que se debe usar en entornos Unix/Linux (soporte continuo, buen tiempo de respuesta, código abierto y gratuito).</p> <p>El desarrollo de OpenSSH comenzó con la versión original (SHH 1.2.12) de Tatu Ylonen (la última realmente libre) en el proyecto OpenBSD 2.6 (via OSSH). Ahora, OpenSSH es desarrollado por dos grupos, uno desarrollando únicamente para el proyecto OpenBSD, y otro adaptando continuamente el código para hacer una versión portable.</p> <p>Todo esto tiene algunas consecuencias, particularmente, el código es cada vez más y más una monstruosa adaptación constante (noto el síndrome "<i>sendmail</i>" apareciendo en el horizonte) y esto no es saludable para una aplicación dedicada al cifrado que debería ser extremadamente rigurosa y clara.</p> <p>Además de una programación limpia y legible, otros dos puntos me molestan:</p> <ul> <li>OpenSSH usa la librería OpenSSL para sus servicios de cifrado, y generalmente esta librería se enlaza dinámicamente. En nuestro caso, la implementación de una utilidad de cifrado que tiene características tales como un buen nivel de seguridad y unas opciones totalmente confiables, hace que la anterior aproximación me parezca totalmente errónea. Por supuesto, una ataque a la librería significa un ataque al producto. Más que un ataque perverso, las características de cifrado (calidad) en OpenSSH son/serán las de la librería, que tiene un desarrollo independiente de OpenSSH.</li> <li>OpenSSH usa el sistema OpenBSD para algunos de sus servicios más sensibles (por ejemplo, un generador de números aleatorios). Sólo en este contexto, quiero resaltar la dependencia de un servicio externo como con OpenSSL. Más molesto todavía, la versión portable de OpenSSH, que debería funcionar en otras plataformas, delega los servicios requeridos por OpenBSD a diversos mecanismos en otras plataformas. Por ejemplo, dependiendo de si hay disponible o no un generador de números aleatoreos, se usará este o uno interno. En consecuencia, la entropía efectiva de OpenSSH depende de la plataforma de ejecución, lo que digamos es moderadamente determinístico.</li> </ul> <p>En mi opinión (y no soy el único), un producto de cifrado multiplataforma debería tener un comportamiento demostrado, determinado y constante independientemente de la plataforma, así como tomar en cuenta (eliminando) las características particulares de la plataforma y su evolución. </p> <p>Dicho esto, tenemos que admitir que, las implementaciones de la competencia no son ni numerosas ni atractivas. Creo que es más pragmático considerar que hoy en día OpenSSH es la peor implementación ¡si excluimos al resto...! Un proyecto muy útil para la comunidad sería el rediseño y reescritura del código.</p> <A NAME="273lfindex7"> </A> <H2>Malas noticias...</H2> <p>¡SSH no es milagroso! Cumple bien la tarea para la que fue diseñado, pero no le puedes pedir más. Particularmente no evitará conexiones "autorizadas": si una cuenta es comprometida, el intruso podrá conectarse via SSH a tu máquina, aunque este sea el único método, ya que controla la autentificación. Sólo se puede confiar totalmente en SSH si va acompañado de una política de seguridad práctica y coherente: si alguien usa la misma contraseña para todo, y no usa SHH en todos lados, el riesgo potencial sólo disminuye ligeramente. Podemos admitir que en esta situación SSH se puede "volver contra tí" ya que el intruso puede usar una conexión segura cifrada con un túnel, y podrá hacer casi todo lo que quiera sin que puedas rastrearlo de forma eficiente.</p> <p>De la misma manera, uno debe tener en cuenta también los "rootkits" bien hechos que normalmente contienen un demonio SSH para hacer volver discretamente a tu sistema, pero con unas pocas modificaciones: por supuesto no escucha en el puerto 22, tiene la delicadeza de no loguear, se llama como un demonio ordinario ( por ejemplo <i>httpd</i>), e invisible para el comando "ps" (que también ha sido modificado de alguna manera por el rootkit). </p> <p>Al contrario, uno no debe estar demasiado preocupado por el peligro que puede representar un demonio SSH que puede permitir a los intrusos estar más cubiertos todavía: deberías saber (espero) que es posible meter casi cualquier cosa en casi cualquier cosa en IP, incluyendo la "apropiación indebida" de protocolos esenciales a través de un cortafuegos: tunelización de HTML, tunelización de ICMP, tunelización de DNS, .... Así que no enciendas el ordenador si quieres un sistema 100% seguro ;-). </p> <p>SSH no está exento de "agujeros" de seguridad derivados de la implementación (muchos han sido corregidos en el pasado, no hay programa perfecto), pero también a nivel de protocolo. Estos "agujeros", aunque se anuncien como muy alarmantes, normalmente afectan a debilidades que son difíciles de utilizar lo que hace que su manipulación sea técnicamente compleja: uno debe tener en mente que los incidentes de seguridad que podrían haber sido evitados por el uso de SSH son diarios, mientras que aquellos que estarían causados por puntos débiles de SSH son de alguna manera teóricos. Sería interesante leer el estudio relativo a ataques "<i>man in the middle</i>": <a href= "http://www.hsc.fr/ressources/presentations/mitm/index.html"> http://www.hsc.fr/ressources/presentations/mitm/index.html</a>. No obstante será necesario tener en cuenta este tipo de vulnerabilidades potenciales para las aplicaciones de "alta seguridad" (banca, militares, ....), donde los medios usados por el cracker, altamente motivado por el premio y el beneficio, pueden ser considerables.</p> <ul> <li> Ataque "Man in the middle":<br> <p><img src="../../common/images/article273/SSH3.gif" alt= "SSH3.gif" width="503" height="257"></p> <p>El agresor intercepta los paquetes de ambos lados, y genera sus paquetes para engañar a ambas partes<br> (diferentes escenarios son posibles, hasta el extremo de terminar la conexión en un lado,<br> y continuar con el otro lado haciéndole creer que es la otra parte habitual)</p> </li> </ul> <p>Me gusta señalar a menudo una debilidad incomprensible del protocolo respecto al "relleno -- padding" (conocido como canal cubierto): tanto en la versión 1 y 2 los paquetes, tienen una longitud que el múltiplo de 64 bits, si son rellenados con un número aleatorio. Esto es bastante inusual y por lo tanto da lugar a un fallo clásico que es bien conocido en las implementaciones de los productos de cifrado: un canal "oculto" (o "subliminal"). Normalmente, "rellenamos" con una secuencia verificada como por ejemplo, dar el valor <i>n</i> para el rango de bytes <i>n</i> (<i>relleno autodescriptivo</i>). En SSH, la secuencia siendo (por definición) aleatoria, no se puede verificar. Consecuentemente es posible que una de las partes en comunicación comprometiese la comunicación, por ejemplo como en el caso de una tercera parte que está a la escucha. Una también puede imaginar una implementación corrupta desconocida por las dos partes (fácil de realizar en un producto donde se proporcionen únicamente los binarios como en general es el caso de los productos comerciales). Esto se puede hacer fácilmente y en este caso uno sólo necesita "infectar" el cliente o el servidor. Dejar dicho increíble fallo en el protocolo, siendo universalmente conocido que la instalación de un canal cubierto en un producto de cifrado es EL método clásico y básico para corromper la comunicación, me parece increible. Puede ser interesante leer los comentarios de Bruce Schneier sobre la implementación de dichos elementos en productos influenciados por agencias gubernamentales. (<a href= "http://www.counterpane.com/crypto-gram-9902.html#backdoors">http://www.counterpane.com/crypto-gram-9902.html#backdoors</a>).</p> <p>Para terminar quiero resaltar el error que encontré en el código de las versiones Unix anteriores a la 1.2.25, al realizar SSF, la adaptación francesa de SSH, y cuya consecuencia era que el generador de números aleatoreos producía... resultado... predecibles (esta situación es lamentable en un producto criptográfico, no entraré en detalles pero se podía comprometer una comunicación con simplemente capturar los datos). Por aquel entonces el equipo de desarrollo de SSH ya había corregido el problema (sólo había que modificar una línea), pero curiosamente sin enviar ninguna alerta, ni siquiera una mención en el "changelog" del producto... si no hubiesen querido que no se supiera, no habrían actuado de esa manera. Por supuesto esto no tiene ninguna relación con el enlace al artículo anterior.</p> <h4>Conclusión</h4> <p>Voy a repetir lo que escribí en la introducción: SSH, ni hace milagros, ni resuelve él solo todos los problemas de seguridad, pero hace posible el manejo eficiente de los aspectos más frágiles de los programas históricamente utilizados para las conexiones interactivas (telnet, rsh...). </p> <h4>Bibliografía, enlaces esenciales</h4> <p>Los dos siguientes libros cubren la versión 1 y 2 de SSH: </p> <ul> <li><i>SSH: the Secure Shell</i><br> Daniel J. Barret & Richard E. Silverman<br> O'Reilly - ISBN 0-596-00011-1<br> </li> <li><i>Unix Secure Shell</i><br> Anne Carasik<br> McGraw-Hill - ISBN 0-07-134933-2</li> <li><a href= "http://www.openssh.com/">openssh: http://www.openssh.com</a></li> </ul> <p>Y si te quieres gastar un poco de dinero, aquí tienes un sitio donde comenzar...:</p> <ul> <li><a href="http://www.ssh.com/">http://www.ssh.com</a></li> </ul> <A NAME="273lfindex8"> </A> <H2>Explotando el canal cubierto (inducido por el relleno aleatorio en SSHv1)</H2> <p> Aquí tienes un método para explotar el canal cubierto (subliminal) consecuencia del uso el relleno aleatorio en SSHv1 (y v2). Rechazo cualquier responsabilidad sobre los ataques de corazón que les puedan dar a los más paranoicos.</p> <p>Los paquetes de SSHv1 tienen la siguiente estructura:</p> <table border="1" width="565" cellpadding="1" bgcolor="#aedbe8"> <tr> <td> <p><b>offset</b></p> <p><b>(bytes)</b></p> </td> <td> <p><b>nombre</b></p> </td> <td> <p><b>longitud</b></p> <p><b>(bytes)</b></p> </td> <td> <p><b>descripción</b></p> </td> </tr> <tr> <td> <p>0</p> </td> <td> <p>tamaño</p> </td> <td> <p>4</p> </td> <td> <p>tamaño del paquete, tamaño del campo sin relleno, entonces:</p> <p>tamaño = longitud(tipo)+longitud(data)+longitud(CRC)</p> </td> </tr> <tr> <td> <p>4</p> </td> <td> <p>relleno</p> </td> <td> <p>p =1 a 8</p> </td> <td> <p>relleno <b>aleatorio</b> : tamaño ajustado para que la parte cifrada sea múltiplo de ocho</p> </td> </tr> <tr> <td> <p>4+p</p> </td> <td> <p>tipo</p> </td> <td> <p>1</p> </td> <td> <p>tipo de paquete</p> </td> </tr> <tr> <td> <p>5+p</p> </td> <td> <p>datos</p> </td> <td> <p>n (variable >= 0)</p> </td> <td> </td> </tr> <tr> <td> <p>5+p+n</p> </td> <td> <p>suma de control (checksum)</p> </td> <td> <p>4</p> </td> <td> <p>CRC32</p> </td> </tr> </table> <p>Únicamente un campo no está cifrado: el "tamaño". La longitud de la parte cifrada es siempre un múltiplo de ocho, ajustada por el "relleno". El relleno siempre se realiza, si la longitud de los últimos tres campos es ya múltiplo de 8 entonces el relleno tendrá una longitud de ocho bytes (<i>5+p+n</i> resto 0 modulo 8). Sea la función de cifrado <i>C</i>, simétrica, usada en modo CBC, y la función de descifrado <i>C<sup>-1</sup></i>. Para simplificar la demostración, cogeremos solo los paquetes con un relleno de ocho bytes. Cuando llega un paquete, en vez de rellenarlo con un número aleatorio, pondremos un valor <i>C<sup>-1</sup>(M)</i>, de ocho bytes en este caso. Esto significa descifrar el mensaje <i>M</i> con la función <i>C</i> usada para cifrar el canal (el hecho de que <i>M</i> sea "descifrada" sin haber sido cifrada de antemano no tiene ninguna importancia desde un punto de vista estrictamente matemático, no voy a entrar en detalles aquí sobre la implementación). Lo siguiente es llevar a cabo el procesado normal del paquete, esto es, el cifrado en bloques de ocho bytes.</p> <p>El resultado será el siguiente :</p> <table border="1" width="478" cellpadding="1" bgcolor="#aedbe8"> <tr> <td> <p><b>offset</b></p> </td> <td> <p><b>contenidos</b></p> </td> <td> <p><b>notas</b></p> </td> </tr> <tr> <td> <p>0</p> </td> <td> <p>tamaño</p> </td> <td> <p>4 bytes no cifrado</p> </td> </tr> <tr> <td> <p>4</p> </td> <td> <p>relleno de 8 bytes (cifrado)</p> </td> <td> <p>entonces <i>C(C<sup>-1</sup>(M))</i></p> </td> </tr> <tr> <td> <p>12... fin</p> </td> <td> <p>tipo, datos, CRC</p> </td> <td> </td> </tr> </table> <p>¿Qué es lo asombroso? El primer bloque cifrado contiene <i>C(C<sup>-1</sup>(M))</i>. Como <i>C</i> es una función de cifrado simétrica, entonces <i>C(C<sup>-1</sup>(M))</i> = <i>M</i>. ¡Este primer bloque se envia sin cifrar en un flujo de datos cifrado! Eso simplemente significa que cualquier persona espiando la comunicación que conozca la estratagema sabrá como explotar la información. Por supuesto, uno puede asumir que el propio mensaje <i>M</i> está cifrado (mediante una clave pública, por ejemplo, lo que evita poner la clave dentro del código pervertido), lo que permite que alguien que no esté informado no la pueda descifrar.</p> <p>Por ejemplo, son suficientes tres paquetes de este tipo para pasar la clave de sesión triple-DES (168 bit), tras los cuales el sniffer escuchando este flujo podrá descifrar toda la comunicación. A partir del momento en que la clave es transmitida, ya no es necesario "pre-descifrar" el relleno pervertido antes de inyectarlo al paquete, es posible usar rellenos de cualquier tamaño si uno quiere añadir incluso más información. </p> <p>El uso de este canal cubierto es <i>¡absolutamente indetectable!</i> (se debe tener cuidado al cifrar cada elemento del mensaje como se explicó previamente, para que la entropía del bloque no revele la estratagema). Indetectable porque el relleno es aleatorio, lo que elimina cualquier posibilidad de pruebas de validación. El Relleno Aleatorio <i>nunca</i> debería utilizarse en los productos de criptografía, nunca.</p> <p>Lo que hace a este canal incluso más peligroso que otros en el protocolo es lo inducido por mensajes como SSH_MSG_IGNORE que es utilizable <i>sin</i> tener conocimiento de la clave cifrada.</p> <p>Para evitar los perversos efectos del relleno aleatorio, uno simplemente debe definir en el protocolo el uso del relleno determinístico: normalmente llamado "<i>self describing padding -- relleno autodescriptivo</i>", lo que significa que el bit de offset <i>n</i> contiene <i>n</i>. El relleno aleatorio existe en SSH v2, es una elección, así que tenlo presente... </p> <p>Para terminar, simplemente diré que si critico el canal cubierto, es porque me gustaría que un producto como SSH, que dice ser altamente seguro, realmente ofreciera un máximo de seguridad. Ahora eres capaz de imaginar que existen múltiples oportunidades potenciales de manipulación en los productos comerciales: solo los productos de código abierto pueden ofrecer una solución a un requisito indispensable, la posibilidad de revisar el código (incluso aunque dichas revisiones sean necesarias).</p> <!-- 2pdaIgnoreStart --> <A NAME="talkback"> </a> <h2>Formulario de "talkback" para este artículo</h2> Cada artículo tiene su propia página de "talkback". A través de esa página puedes enviar un comentario o consultar los comentarios de otros lectores <center> <table border="0" CELLSPACING="2" CELLPADDING="1" summary="tb-button-outerpart"> <tr BGCOLOR="#C2C2C2"><td align=center> <table border="3" CELLSPACING="2" CELLPADDING="1" summary="tb-button"> <tr BGCOLOR="#C2C2C2"><td align=center> <A href="http://cgi.linuxfocus.org/cgi-bin/lftalkback?anum=273"><b> Ir a la página de "talkback" </b></a> </td></tr></table> </td></tr></table> </center> <HR size="2" noshade> <!-- ARTICLE FOOT --> <CENTER><TABLE WIDTH="98%" summary="footer"> <TR><TD ALIGN=CENTER BGCOLOR="#9999AA" WIDTH="50%"> <A HREF="../../common/lfteam.html">Contactar con el equipo de LinuFocus</A> <BR><FONT COLOR="#FFFFFF">© Bernard Perrot, <a href="../../common/copy.html">FDL</a> <BR><a href="http://www.linuxfocus.org">LinuxFocus.org</a></FONT> </TD> <TD BGCOLOR="#9999AA"> <!-- TRANSLATION INFO --> <font size=2>Información sobre la traducción:</font> <TABLE summary="translators"> <tr><td><font size="2">fr --> -- : Bernard Perrot <small><bernard.perrot(at)univ-rennes1.fr></small></font></td></tr> <tr><td><font size="2">fr --> en: Guy Passemard <g.passemard(at)free.fr></font></td></tr> <tr><td><font size="2">en --> es: Javier Gómez Sierras <jgomsi(at)obelix.umh.es></font></td></tr> </TABLE> </TD> </TR></TABLE></CENTER> <p><font size=1>2003-04-07, generated by lfparser version 2.34</font></p> <!-- 2pdaIgnoreStop --> </BODY> </HTML>