Subsecciones

2.4 SISTEMAS DISTRIBUIDOS

2.4.1 ¿Qué se entiende por sistema distribuido y sistema operativo distribuido?

Un sistema distribuido es un conjunto de ordenadores o procesadores independientes que cara al usuario funcionan como uno solo. Está formado por varios componentes, relativamente pequeños e independientes, que cooperan estrechamente para dar un servicio único.

Un sistema operativo distribuido es el encargado de cumplir lo anterior. Hay un particionado y cooperación entre todos los componentes, ninguno sobrevive solo, el propio kernel está distribuido por las máquinas. El hardware no da ninguna facilidad, es el software el que determina que un sistema sea distribuido o no. El usuario no sabe dónde se están ejecutando los procesos ni dónde están los recursos. Llevar a la práctica la idea de un kernel global distribuido es muy difícil, pues podría haber inconsistencias de datos en el kernel, además se necesita al menos el kernel mínimo para enviar y recibir información y un mecanismo robusto de comunicación y eficiente para evitar latencias demasiado elevadas.

Lo que se han desarrollado hasta ahora son los llamados sistemas operativos en red. En estos sistemas cada máquina tiene su propio kernel. Los sistemas están conectados por una red y se puede hacer remote login en ellos, en todo momento el usuario sabe donde se encuentran todos los recursos (ficheros, procesos, etc.). No es un sistema distribuido por lo que no tiene las ventajas que se verán en el siguiente apartado.

Actualmente se está caminando desde los sistemas operativos en red a los sistemas distribuidos, aunque aún no se han cumplido los objetivos de un sistema distribuido completamente tenemos ya algunos avances. Por ejemplo ya hay grandes avances en sistemas de ficheros para conseguir que exista un solo directorio raíz al igual que la existencia de una ubicación automática por parte del sistema de los ficheros. Se puede implementar un balanceo de la capacidad y redundancia en los datos para minimizar el impacto de posibles caídas de nodos.

Un cluster openMosix ya implementa una migración de procesos, que a ojos del usuario es transparente. El cluster se usa como un gran computador donde se ejecutan los procesos en todos sus nodos. La ubicación de los procesos la elige el sistema operativo o el usuario, en un intento de balancear la carga.

2.4.2 ¿Por qué necesitamos sistemas distribuidos?

Esta aproximación tiene varias ventajas, por ejemplo en un sistema operativo distribuido se cumplen todas los criterios de transparencia, con todas las ventajas que esto supone, aparte también se tienen las siguientes ventajas:
  1. Economía: la relación precio rendimiento es mayor que en los sistemas centralizados sobretodo cuando lo que se buscan son altas prestaciones, los precios de los sistemas centralizados se disparan.

  2. Velocidad: llega un momento en el que no se puede encontrar un sistema centraliz ado suficientemente potente, con los sistemas distribuidos siempre se podrá encontrar un sistema más potente uniendo esos mismos nodos. Se han hecho comparativas y los sistemas distribuidos especializados en cómputo han ganado a los mayores mainframes.

  3. Distribución de máquinas: podemos tener unas máquinas inherentemente distribuidas por el tipo de trabajo que realizan.

  4. Alta disponibilidad: cuando una máquina falla no tiene que caer todo el sistema sino que este se recupera de las caídas y sigue funcionando con quizás algo menos de velocidad.

  5. Escalabilidad: puedes empezar un cluster con unas pocas máquinas y según se descubre que la carga es elevada para el sistema, se añaden más máquinas, no hace falta tirar las máquinas antiguas ni inversiones iniciales elevadas para tener máquinas suficientemente potentes. Ya se vió un ejemplo en su momento.
    Figura: Sistemas distribuidos. Escalabilidad de servicios en una empresa
    Image escalabilidad_servicios
  6. Comunicación: los ordenadores necesariamente están comunicados, para el correcto y eficaz funcionamiento del cluster se crean unas nuevas funcionalidad es avanzadas de comunicación. Estas nuevas primitivas de comunicación pueden ser usadas por los programas y por los usuarios para mejorar sus comunicaciones con otras máquinas.

  7. Sistema de ficheros con raíz única: este sistema de ficheros hace que la administración sea más sencilla (no hay que administrar varios discos independi entemente) y deja a cargo del sistema varias de las tareas.

  8. Capacidad de comunicación de procesos y de intercambio de datos universal: podemos enviar señales a cualquier procesos del cluster, así mismo podemos hacer trabajo conjunto con cualquier proceso e intercambiar con el datos, por lo tanto podríamos tener a todos los procesos trabajando en un mismo trabajo.

2.4.3 Desventajas: el problema de la transparencia

La principal desventaja de estos sistemas es la complejidad que implica su creación. Básicamente se tienen todos los problemas que se puedan tener en un nodo particular pero escalados. Vamos a ver los problemas que ocurren al intentar implantar las ventajas que hemos visto en el apartado anterior. Los puntos 1, 2 y 3 no tienen problemas de implantación porque son inherentes a los sistemas distribuidos. Como se expone en el anterior apartado otras de las ventajas de los sistemas distribuidos es que cumple con todos los criterios de transparencia. Pero conseguir estos criterios implica ciertos mecanismos que debemos implementar:
  1. Transparencia de acceso.

    Implica tener que mantener el viejo sistema para el nuevo cluster, por ejemplo mantener un árbol de directorios usual para manejar todos los dispositivos de almacenamiento del cluster. No tenemos que romper las APIs para introducir las nuevas funcionalidades.

  2. Transparencia de localización.

    A nivel más bajo tenemos que implantar una forma de conocer donde se encuentran los recursos, tradicionalmente se han usado servidores centralizados que lo sabían todo, ahora ya se va consiguie ndo que esta información se distribuya por la red.

  3. Transparencia de concurrencia.

    Esto que no es excesivamente complicado en un sistema local, se ha convertido en un quebradero de cabeza en un sistema distribuido. Se han desarrollado varios métodos para conseguirlo. El mayor problema es la desincronización de los relojes pues es muy complejo que todos los relojes hardware lleven exactamente la misma temporización por tanto algunos ordenadores ven los acontecimientos como futuros o pasados respecto a otros ordenadores. Este tema se tratará con más profundidad en el capítulo de sistemas operativos.

  4. Transparencia de replicación.

    Básicamente el problema es que el sistema sepa que esas réplicas están ahíy mantenerlas coherentes y sincronizadas. También tiene que activar los mecanismos necesarios cuando ocurra un error en un nodo.

  5. Transparencia de fallos.

    Aunque haya fallos el sistema seguirá funcionando. Las aplicaciones y los usuarios no sabrán nada de estos fallos o intentarán ser mínimamente afectados, como mucho, el sistema funcionará más lentamente. Este punto está muy relacionado con la transparencia de replicación.

  6. Transparencia de migración.

    Tenemos que solucionar problemas sobre las decisione s que tomamos para migrar un proceso, hay que tener en cuenta las políticas de migración, ubicación, etc. Además tenemos que ver otros aspectos prácticos como si al nodo que vamos encontraremos los recursos que necesitamos, etc. La aplicación no tiene que saber que fue migrada.

  7. Transparencia para los usuarios.

    Implica una buena capa de software que de una apariencia similar a capas inferiores distintas.

  8. Transparencia para programas.

    La más compleja. Implica que los programas no tienen porque usar llamadas al sistema nuevas para tener ventaja del cluster. Mosix hace esto muy inteligentemente tomando la natural división en procesos de los programas para migrarlos de forma transparentemente.

2.4.4 La tendencia a lo distribuido

Existen varios métodos para intentar distribuir a nivel de aplicación, son métodos que abstraen las capas inferiores y hacen la vida más fácil a los programadores de las aplicaciones, que no se tendrán que preocupar sobre las peculiaridades de las capas inferiores consiguiéndose una mayor efectividad en la programación. Las tecnologías que se verán, en este orden, son:
RPC: Remote Procedure Calls.
RMI: Remote Method Invocation.
CORBA: Estándar de comunicación de objetos.
Bonobo: Abstracción sobre CORBA de GNOME.
KDE: Desktop Enviroment. Veremos: KIO, XMLRPC, DCOP.
SOAP: Simple Object Access Protocol.
DCOM: tecnología de Microsoft.

RPC.-

El concepto de RPC o llamada a procedimiento remoto ha sido explotado desde hace ya varias décadas, de hecho, existen varias implementaciones creadas por distintos grupos e incluso varios protocolos. El concepto de llamada a procedimiento remoto no es otra que la que su propio nombre indica, es decir, se pretende ejecutar funciones o procedimientos en otras máquinas distintas a la nuestra y que el resultado retorne a nuestra máquina, todo ello de manera transparente. Hasta aquí el concepto de llamada a procedimiento remoto parece bastante asequible. El problema surge como siempre a la hora de implementarlo, codificarlo y tener en cuenta consideraciones de sistema.

Para empezar se deben tener en cuenta cosas como que tipo de protocolo se va a utilizar en capas inferiores. Puede ser conectivo, perfecto para olvidarse de las retransmisiones y fallos o no conectivos y aprovechar al máximo la capacidad de la red. También hay que prestar atención al formato de representación entre distintas máquinas de un mismo sistema, como podrían ser ASCII, EBCDIC o Little Endian y Big Endian, y en otros muchos problemas que implican las llamadas a procedimientos remotos2.17.

Por último (como colofón de las pegas de los sistemas implementados de los RPC) está el que generalmente no son tan transparentes como debieran. En el caso ideal, se supone que, el programador no debe saber si los procedimientos de una biblioteca son locales o remotos, ni necesitar de ningún tipo de interface para poder llamar a dichos procedimientos. Esto no se cumple, no sólo en el caso de RPC, sino en prácticamente cualquier sistema distribuido.

El RPC por excelencia es el RPC diseñado e implementado por Sun Microsystems cuya versión 2 esta especificada y tipificada en el RFC 1831. En esta RFC se puede leer no sólo el modelo de llamada a procedimiento remoto, sino también ejemplos de programación de RPC, semánticas de transporte, sistema de autenticación y modelo de programación en general de esta implementación. Dicha implementación utiliza como modelo de comunicación IP/UDP ya que la mayoría de las aplicaciones suelen estar en una LAN y por tanto se obtiene más efectividad que con TCP. Se utiliza también XDR para hacer compatible entre varios formatos de representación. Los programas requieren de librerías y funciones especiales y al mismo tiempo se requiere rpcportmapper instalado como demonio para efectuar las transacciones. Existen varias referencias acerca de como podría implementarse un sistema distribuido de este tipo en el libro Sistemas Operativos Distribuidos de Andrew S. Tanembaum.

¿Por qué no utilizar RPC en sistemas distribuidos o clusters? Existen diversas causas, unas con más peso que otras. Por norma general el modelo RPC suele ser bastante lento a pesar de utilizar UDP, por ejemplo en lo que se refiere al checksum, cambio de referencias en memoria, traducción XDR, rellenado de cabeceras y otras tantas operaciones que hacen que dicho sistema sea compatible en un entorno de trabajo hetereogéneo.

Es decir, en entornos de trabajo en los cuales no se requiere de confiabilidad, autenticación (y seguridad en general), eficiencia, y consistencia; la solución RPC es aceptable. En el caso de los clusters, suele implementarse con unos requerimientos de sistema bastante exigentes en lo que se requiere a eficiencia, y es mejor considerada una macro en el programa que utilizar todo un sistema como puede ser XDR. Generalmente los sistemas distribuidos suelen basar su desarrollo en nuevas implementaciones o modelos, que no tienen por que ser el de RPC, y no utilizan RPC debido a la poca eficiencia que este reporta y a la mala fama en seguridad que este posee.




RMI.-

También desarrollado por Sun para Java, mucha gente considera a RMI el sucesor de RPC.

RMI es un concepto confuso, tiene dos aceptaciones:

RMI es un mecanismo que permite invocar un método de un objeto que no existe en el espacio de direccionamiento de la propia aplicación, este otro espacio de direcciones puede encontrarse en la propia máquina o en otra diferente. Básicamente podemos aplicar lo explicado en RPC pero teniendo en cuenta que este mecanismo es orientado a objetos. Comparando con el siguiente punto CORBA, aunque básicamente ambos métodos son un RPC para lenguajes orientados a objetos, CORBA es un estandard e independiente del lenguaje, RMI sólo es para Java. CORBA incluye muchos otros mecanismos en su estándar (lo que le hace ser una implementación más lenta y pesada) que no son parte de RMI. Tampoco existe el concepto de ORB (Object Request Broker) en RMI. Java RMI ha estado evolucionando y convirtiéndose en más compatible con CORBA, en particular hay ahora una nueva forma de RMI llamada RMI/IIOP (RMI sobre IIOP) que usa IIOP (Internet Inter-ORB Protocol de CORBA como protocolo de bajo nivel para las comunicaciones RMI. Por supuesto podemos imaginar las consecuencias para el rendimiento.

Hay 3 procesos que participan en que la invocación de métodos remotos se haga efectiva:

Hay dos tipos de clases que pueden ser usadas en Java RMI.




CORBA.-

Es un estándar desarrollado por una fundación creada por distintas empresas llamada OMG (Object Management Group) para poder hacer fácilmente programación distribuida, reutilización de objetos y de código ya hecho. CORBA cumple correctamente estos objetivos, para ello la estructura de CORBA cuenta de un lenguaje estandar llamado IDL (Interfaz Definition Language) que sirve para determinar los interfaces entre objetos, la implementación de los objetos se hace con cualquier lenguaje que tenga un compilador capaz de enlazar IDL.

CORBA es un middleware entre el sistema operativo y las aplicaciones usuario, entre ese middleware se encuentra el ORB encargado de hacer las llamadas entre objetos. En resumidas cuentas, CORBA es un nivel más de abstracción.

-- Ventajas:

--Desventajas:

Aunque haya más ventajas que inconvenientes estos últimos son más relevantes puesto que no podemos suponer que los procesos con los que trabajemos vayan a estar desarrollados en CORBA, además CORBA no nos soluciona el problema de migrar procesos y si lo hiciera sería extremadamente lento.

Aún se podría pensar en usar CORBA para envío de mensajes, pero la sobrecarga que genera no merece la pena. CORBA es muy potente para aplicaciones distribuidas o no de nueva creación y seguramente se le pudieran añadir funciones de balanceo de carga, pero para que nuestra solución sea más general es preferible no usar CORBA y tratar todo a nivel de proceso, sin abstracciones mayores. Aunque el estándar CORBA no añade estas capacidades de balanceo, implementación es específicas si que tienen reconfiguración dinámica, por ejemplo, Dinamic TAO.



--Programación:



CORBA tiene la capacidad para heredar las interfaces (i.e. manejo de excepciones) aparte de las interfaces que proveen el ORB y los servicios CORBA. El ORB es la librería usada por la aplicación que se encarga de todos los detalles de bajo nivel, como uso del protocolo IIOP de los objetos por la red y mantener el conjunto de interfaces expuestas al exterior. Los servicios CORBA cubren áreas funcionales como el manejo de objetos, sincronización de los tiempos, transacciones, eventos y seguridad.

Con toda esta funcionalidad lo que se hace es obtener el manejador de un objeto (IOR) y entonces un objeto conocerá los interfaces de ese otro objeto, si este objeto se encuentra en la misma aplicación, en otra aplicación o en una aplicación que funciona en la otra parte del mundo. Necesita activar el objeto con OAF.

Los tipos de datos de CORBA permiten la representación de casi cualquier estructura de datos a través de una amplia selección de tipos de datos, y gran cantidad de modos de combinar estos tipos de datos básicos en estructura s de datos más complejas.

El enlace estándar para CORBA es C. Se compila el IDL y se generan varios ficheros de código fuente C. Divididos en dos partes importantes: stubs y skels.

Cada vez que se llama a CORBA ocurre lo siguiente:
  1. se llama a tu función stub la cual dialoga o simplemente envía la petición al ORB

  2. el ORB llama a la función skel del objeto destino, la cual llama a la implementa ción de esta función.

  3. la función skel envía de vuelta el valor de retorno a la función stub que lo decodifica y lo devuelve.
Por supuesto hay optimizaciones y cuando el objeto está en la misma aplicación se le llama directamente. En otro caso la sobrecarga seria excesiva.




Bonobo.-

Abstracción por encima de CORBA desarrollada por el proyecto GNOME.

Bonobo es un conjunto de interfaces CORBA, algunos implementados por objetos contenedores y otros por los objetos que serán contenidos (por ejemplo cuando pulsamos sobre un pdf y este se abre en nuestro propio navegador, el navegador es el contenedor y el programa lector de pdf el contenido). Bonobo es también una implementación por defecto de estos interfaces CORBA que es exportado en forma de API C para evitar a la mayoría de los programadores de preocuparse por tener que codificar directamente los interfaces CORBA.

Aunque no lo hemos mostrado en el punto anterior la programación en CORBA es ciertamente compleja, por tanto dentro del esfuerzo del proyecto GNOME para incorporar CORBA se ha desarrollado una librería de un nivel más alto llamada Bonobo (el nombre es de ciertos monos en vías de extinción que sirven para ilustrar la teoría de conexión de componentes). Otro de estos desarrollos fue ORBit que es un ORB pero con la particularidad de estar altamente mejorado en velocidad, siendo el más rápido existente (casi el doble que su más cercano competidor Omniorb) y de los que menos memoria necesita.

A parte de ORBit tenemos Gnorba que facilita en algo algunas tareas de ORBit y es más específico de GNOME, por ejemplo permite la integración del bucle principal de ORBit con el bucle principal de Gtk+, añade seguridad a las comunicaciones y un método estándar para acceder al servicio de nombres de GNOME. Para permitir acceso a un objeto en concreto se dispone la información en GOAD (GNOME Object Activation Directory) donde tenemos el id del objeto, las interfaces que exporta y como crear un ejemplar, gracias a esto se pueden usar métodos a través de la red.

Bonobo se creó para intentar mantener las aplicaciones con poca complejidad para que a los nuevos programadores les cueste poco saber cómo funciona el código y sea más fácil el mantenimiento y desarrollo. Usando todas las facilidades de CORBA que es usado para la capa de comunicación y para unir todos los componentes Bonobo entre sí. Cada componente tiene su interfaz (definido en términos de las interfaces CORBA) que exporta, ahíes donde cualquier otro componente puede conseguir información o unirse al componente.

El interface CORBA se introduce en un objeto GTK+, esto quiere decir que los objetos GTK+ son la implementación del interface IDL. Las implementaciones contienen ciertas acciones por defecto para no molestar al programador con detalles de CORBA, pero se dan unos métodos para cambiar este comportamiento.




KDE.-

En este apartado vamos a ver tres tecnologías que utiliza KDE a partir de sus versiones 2.0 y posteriores:

  1. KIO: entrada y salida , transparencia de red.
  2. XML-RPC: manejo de programas remotamente.
  3. DCOP: comunicación entre componentes Kparts.

Estas tres tecnologías permiten acercarnos a un proceso distribuido y a una transparencia de red enormes. KDE es muy buen ejemplo de cómo se intenta cumplir algunos de los objetivos de los sistemas distribuidos, y cómo usuarios que somos de este entorno podemos decir que esta tecnología hace el día a día más sencillo.

SOAP.-

Hoy en día lo que se le pide a un sistema que use RPC o RMI es que sea confiable, robusto, que tenga APIs desarrolladas para varios lenguajes, interoperabilidad entre lenguajes, plataformas y modelos de componentes.

Desafortunadamente no hay un único sistema que tenga todas esas características. El formato de los datos y el protocolo usado para intercambiarlos es un factor determinante en el grado de interoperabilidad que pueden alcanzar las aplicaciones.

XML(eXtensible Markup Language) se está convirtiendo en un estandar para representar datos en un formato independiente de la plataforma. XML es un lenguaje fácil de general y de leer. HTTP (HyperText Transfer Protocol) también se está convirtiendo en un protocolo muy usado gracias a las aplicaciones web, que está soportado por todos los sistemas.

Las peticiones/respuesta de HTTP se pasan a través de firewall y son manejadas de forma segura, todo lo contrario que una ejecución de una llamada RPC o RMI.

Por lo tanto XML sobre HTTP parece una forma bastante inteligente para las aplicaciones distribuidas de comunicarse entre ellas. SOAP hace exactamente eso.

Representando RPCs de forma independiente a la plataforma, abre la posibilidad de implementar otros protocolos específicos de arquitectura en SOAP. Por ejemplo Microsoft parece querer usar SOAP como protocolo intermedio de intercambio al que otros protocolos pueden ser fácilmente traducidos, para potenciar el uso de sus componentes COM.

RPC en SOAP son interacciones cliente servidor sobre HTTP donde la petición/resp uesta se hacen de acuerdo con las reglas SOAP. Para elegir el objeto se usa el URI (Universal Resource Identifier) que es propio de HTTP o la cabecera SOAPAction que indica el nombre del interface. Se especifica una convención de la llamada remota , que determina la representa ción y el formato de las llamadas y respuestas. Una llamada es un dato compuesto con varios campos, uno por cada parámetro. Un mensaje de retorno es un valor de retorno y unos parámetros.




DCOM.-

Microsoft tiene una serie de tecnologías de componentes (COM, COM+, DCOM) la que trataremos aquí es DCOM (Distributed Component Object Model), no trataremos activeX por estar más enfocado a las aplicaciones internet. DCOM es un protocolo que permite a los componentes software comunicar directame nte sobre una red de una manera confiable, segura y eficiente. Esta tecnología anteriormente se llamaba Network OLE pero fué cambiada de nombre por cuestiones de márketing. Está diseñada para ser usada sobre distintos protocolos de más bajo nivel como HTTP. Se basa en DCE-RPC, por tanto la capa más baja es RPC con lo que eso conlleva. Cuando una aplicación accede a un objeto, recibe un puntero indirecto a las funciones del interfaz del objeto. El puntero tiene información sobre dónde se encuentra el objeto. Tras recibir este puntero, la aplicación que llama no necesita saber dónde está el objeto o cómo hace su trabajo. Por tanto el usuario puede acceder y compartir la información sin tener que saber donde se encuentran los objetos. Si los objetos se encuentran en la misma computadora DCOM sirve para implementa r un sistema IPC. Lleva incorporado un mecanismo de seguridad con permisos y autentificación de dominio.


miKeL a.k.a.mc2 2003-09-28