PRÁCTICA 4 PASO DE MENSAJES

Documentos relacionados
Boletín 7- Sockets. Departamento de Lenguajes y Sistemas Informáticos

Práctica 1 Programación de Aplicaciones Distribuidas: Sockets UDP. Laboratorio de Comunicación de Datos ITT Telemática Septiembre 2011

Diseño de aplicaciones distribuidas ÍNDICE

Migrando aplicaciones a IPv6

Sistemas Operativos: Programación de Sistemas. Curso Oscar Déniz Suárez Alexis Quesada Arencibia Francisco J.

Qué es un socket? Dominios de comunicación. Tipos de sockets en el dominio AF_INET. Sockets Stream. Sockets Datagram. Sockets Raw

Introducción a la programación con sockets en C

Mecanismos IPC: sockets

COMUNICACIÓN Sistemas Distribuidos

Estructuras y funciones de programación de sockets.

-> Todo socket viene definido por dos características fundamentales:

PROGRAMACIÓN CON SOCKETS

Ingeniería Técnica de Telecomunicación, esp. Telemática Universidad de Jaén

Sockets (UDP) Tema 2.- Nivel de aplicación en Internet

Estructuras y funciones de programación de sockets.

Interfaz de Socket. Agustín J. González ELO309 ELO309 1

Redes de Computadores Nivel de Aplicación: Programación con sockets I

Sistemas Operativos Distribuidos

Programación Básica de Sockets en Unix para Novatos

Sockets (TCP) Tema 2.- Nivel de aplicación en Internet

Sockets Básicos. Sockets Básicos

Arquitecturas Cliente/Servidor

DESARROLLO DE APLICACIONES DISTRIBUIDAS. SOCKETS en UNIX

Sistemas Distribuidos. Sockets

Sockets: funcionamiento y programación. Sockets tipo UNIX. MSc. Ivan A. Escobar

Sockets Básicos. APIS para acceso a TCP/IP. APIS para acceso a TCP/IP. APIS para acceso a TCP/IP. APIS para acceso a TCP/IP. Temas a tratar...

Adaptación de aplicaciones a IPv6

Clase de Sockets en lenguaje C. Prof. Ricardo González

ARQUITECTURA DE REDES Laboratorio PRÁCTICA 2: MANUAL DE SOCKETS EN C. Grado en Ingeniería Informática Curso 2014/15

UNIVERSIDAD DE CANTABRIA DEPARTAMENTO DE INGENIERÍA DE COMUNICACIONES GRUPO DE INGENIERÍA TELEMÁTICA

Características de un lenguaje ideal para robótica

Programación C/S Básica

Manejo de sockets IPv6

Introducción de Sockets en C.

sockets Flujo (SOCK_STREAM) Comunicación bidireccional Confiable (entrega garantizada) Información ordenada en el destino Datagrama (SOCK_DGRAM)

Desarrollo de Aplicativos con winsockets

Tema 3: COMUNICACIÓN ENTRE PROCESOS

Tema 4: Sockets: Un interfaz con TCP/IP

Bibliografía [COM00] Internetworking with TCP/IP, vol. 3, Cap. 2 y del 7 al 15.

Ejercicio Sockets Suma Resta. Descripción

Tema 2. Comunicación entre procesos

UNIVERSIDAD NACIONAL AUTÓNOMA DE MÉXICO. Facultad de Ingeniería

Programación en red sobre TCP/IP Interface sockets

Tema 5 El Modelo Cliente-Servidor

Tema 4 Sockets: Un interfaz con TCP/IP

Administración de redes en GNU/Linux

Redes (IS20) Ingeniería Técnica en Informática de Sistemas - (2º Curso)

SOCKETS en Linux. Lic. Leonardo de - Matteis. Departamento de Ciencias e Ingeniería de la Computación Universidad Nacional del Sur 2011

Modem IBM Compatible. IBM Compatible. Ethernet IBM AS/400. Laser printer. Workstation. Mac II. El Interfaz. Socket. versión perliminar

Universidad Simón Bolívar Departamento de Computación y Tecnología de la Información Curso de Redes I CI-4815 Trimestre Septiembre Diciembre 2013

Introducción a Sistemas Operativos: La red

Sistemas de Transportes de Datos (STD) Tema III: UDP y TCP (Entrega 4) Grupo de Aplicaciones Telemáticas. Grupo de Aplicaciones Telemáticas

Análisis Experimental de la Transmisión de Datos

PRÁCTICA 2: Cliente-servidor UDP

Programación de aplicaciones distribuidas usando sockets

SCHOOL OF HACKING 2015 RETO BUFFER OVERFLOW

Introducción a Sockets en Linux

COMUNICACIÓN ENTRE PROCESOS SOCKETS

Programación con sockets

Los sockets de Unix. Dr. Roberto Gómez Cárdenas ITESM-CEM. Dr. Roberto Gomez C. Diapo. No.

Introducción a las Redes de Computadoras

Introducción a las Redes de Computadoras. Capa de aplicación. Programación con Sockets. Capitulo 2 Capa de Aplicación

Sistema Cliente Servidor Con Sockets

Versión 1.0, 26 de marzo de 2.000

Computación de Alta Performance Curso 2009 PROGRAMACIÓN PARALELA EN LENGUAJE C

ARQUITECTURA DE REDES Laboratorio

Los sockets de Unix. Funcionamiento y programación Dr. Roberto Gómez Cárdenas DCC del ITESM-CEM

SOCKET S. Alberto Castro Rojas

SISTEMAS DE COMUNICACIONES DE DATOS

Mecanismo(s) de intercambio de información entre 2 ó más computadores conectados entre sí o a través de otros.

Comunicación entre procesos mediante Sockets Preparado por Gabriel Astudillo Muñoz Escuela de Ingeniería Civil Informática Universidad de Valparaíso

TELEPROCESO Y SISTEMAS DISTRIBUIDOS

CENTRO DE ESTUDIOS NOVA - Cartagena Laboratorio de Software de Comunicaciones TEMA 1 FUNDAMENTOS DE SOCKETS TCP Y UDP

Programación de sockets

AMPLIACION DE SISTEMAS OPERATIVOS SOCKETS AIRAN GODOY HERNANDEZ JOSE MARIA RODRIGUEZ RODRIGUEZ 5º INGENIERIA EN INFORMATICA

Redes de Computadores: Relación de problemas 1. Sockets

Problemas de Redes de Computadores. Conjunto de problemas 1

Usando Internet Sockets Brian "Beej" Hall Copyright by Brian "Beej" Hall

Los sockets de Unix. Funcionamiento y programación Dr. Roberto Gómez Cárdenas DCC del ITESM-CEM

1_servicio_eco_stream_secuencial/eco_clie_tcp.c Tue Mar 09 09:57:

Problemas de Redes de Computadores. Ingeniería Técnica en Informática de Gestión Conjunto de problemas 1

ADMINISTRACIÓN GENERAL DE TECNOLOGÍA DE LA INFORMACIÓN ADMINISTRACIÓN CENTRAL DE DESARROLLO Y MANTENIMIENTO DE APLICACIONES

Desarrollo de Aplicaciones Distribuidas. Sockets. Daniel Avellaneda

Programación con Sockets

UDP Tema 3.- Nivel de transporte en Internet

ARQUITECTURA DE REDES Laboratorio

Guía Beej de Programación en Redes

WSAEADDRNOTAVAIL (10049) Dirección solicitada no se puede asignar.

La pila TCP/IP es la familia de protocolos que dirige el internet actual. Mientras otros protocolos también se usa en redes de computador, TCP/IP es

Sistemas Operativos Distribuidos

UNIVERSIDADE DA CORUÑA Departamento de Tecnoloxías da Información e as Comunicacións APÉNDICE: MANUAL DE SOCKETS EN C

TimeOut RTT medido 1 5 seg. 2*5= ,7 3 TimeOut 3 TimeOut 3 0, ,35 5 0,44

Bloque I: Principios de sistemas operativos

IMPLEMENTACIÓN DE APLICACIONES DE SEGURIDAD CON OPENSSL

Sistemas Operativos Distribuidos. Comunicación de Procesos en Sistemas Distribuidos

Nuestro 1er Aniversario

Sistemas operativos: una visión aplicada. Capítulo 10 Introducción a los sistemas distribuidos

07 << Acceso en exclusiva al recurso compartido >>

LABORATORIO DE GESTIÓN DE REDES APÉNDICE: MANUAL DE SOCKETS EN C

Informática PRÀCTICA 9 Curs Práctica Nº 9: Rango y precisión de representación de números en el ordenador.

Transcripción:

PRÁCTICA 4 PASO DE MENSAJES Introducción Cuando los procesos interactúan unos con otros pueden necesitar intercambiar información. Uno de los métodos posibles para conseguir esto es el paso de mensajes. Además de permitir la comunicación, este método permite la sincronización mediante la exclusión mutua entre procesos y se presta muy bien para ser implementados en sistemas distribuidos así como en sistemas multiprocesador y monoprocesador de memoria compartida. Existen diversas variantes en la implementación del paso de mensajes. En este capítulo se utilizará el sistema de paso de mensajes que emplea el sistema operativo Unix. Conceptos básicos Un método para direccionar los mensajes es mediante lo que se conoce como direccionamiento indirecto. Este método consiste en utilizar unas estructuras de datos compartidas formadas por colas que pueden guardar los mensajes temporalmente. Estas colas se denominan generalmente buzones (sockets). De este modo, para que dos procesos se comuniquen, uno envía mensajes al buzón apropiado y el otro los recoge del buzón. Cada buzón tiene colas para enviar o recibir datos. La relación entre emisores y receptores puede ser uno a uno, de muchos a uno, de uno a muchos o de muchos a muchos. Una relación uno a uno, permite que se establezca un enlace privado de comunicaciones entre dos procesos. Una relación de muchos a uno resulta útil para interacciones cliente/servidor, donde un proceso ofrece un servicio a un conjunto de procesos. Esta última relación ofrece una gran ventaja por su adaptación a las redes de computadoras ya que los procesos clientes o servidor pueden ejecutarse en el mismo host o pueden encontrarse en hosts distintos; pero en cualquier caso, se debe saber en qué host se encuentra el proceso servidor. Un proceso servidor necesita realizar varias operaciones para poder aceptar peticiones por parte de los procesos cliente. Algunas de estas operaciones son: obtener la dirección del host y puerto de comunicaciones local, crear el buzón y enlazar la dirección a éste, escuchar solicitudes, aceptarlas y mantener una comunicación con el cliente. Estudiemos cada una de estas operaciones más detenidamente. Obtener la dirección del host local La dirección internet se obtiene mediante la función gethostbyname que busca en el archivo /etc/hosts a partir del nombre oficial. Su sintaxis es la siguiente: struct hostent *gethostbyname(const char *name); El argumento name especifica el nombre del host del cual se va a obtener la dirección. La función devuelve un puntero a una estructura llamada hostent que contiene la dirección requerida. Su formato es el siguiente: struct hostent char *h_name; /* nombre oficial */ char **h_alias; /* lista de alias */ int h_addrtype; /* tipo de dirección */ int h_length; /*longitud de la dirección */ char **h_addr_list; /*lista de direcciones */ long h_addr; /* dirección IP */ }; Obtener la dirección del puerto local La función getservbyname permite obtener el número del puerto local de un servicio a partir del nombre del servicio. Para ello busca en el archivo /etc/services. Su sintaxis es la siguiente: struct servent *getservbyname(const char *name, const char *protocol);

Los argumentos que se le pasan a la función son el nombre del servicio (name) y la familia de protocolos (protocol). La función devuelve un puntero a una estructura (servent) que contiene el número del puerto requerido. Su formato es el siguiente: struct servent char *s_name; /* nombre oficial del servicio */ char **s_aliases; /* lista de alias */ int s_port; /* número del puerto */ char s_proto; /* familia de protocolos */ char **h_addr_list; /* lista de direcciones */ }; Crear el buzón Para poder crear los buzones se utiliza la función socket. Su sintaxis es la siguiente: int socket(int domain, int type, int protocol); El argumento domain especifica la familia de protocolos. Algunos de los valores posibles son AF_INET, AF_UNIX, AF_X25, etc. Utilizaremos en nuestro estudio el dominio AF_INET que corresponde al dominio Internet. type especifica el tipo de comunicación. Algunos de los valores posibles son SOCK_STREAM, SOCK_DGRAM, SOCK_RAW, etc). Para el dominio Internet debemos escoger SOCK_STREAM; y por último, protocol especifica el protocolo específico que se va a usar. La función devuelve un entero que identifica al buzón recién creado. Enlazar dirección al buzón La función bind enlaza una dirección a un buzón. Su sintaxis es: int bind(int s, const struct sockaddr *name, int namelen); Los argumentos que se le pasan son el identificador del buzón (s) que va a ser enlazado, un puntero a una estructura de dirección (name) y el tamaño de dicha estructura (namelen). El formato de una estructura de dirección es el siguiente: struct sockaddr_in short sin_family; /* familia de dirección */ short sin_port; /* número de puerto */ long sin_addr; /* dirección IP */... }; Escuchar solicitudes La función listen solamente indica que la aplicación desea aceptar solicitudes de conexión. Su sintaxis es la siguiente: int listen (int s, int max); Los argumentos que se le pasan son el identificador del buzón (s) y el número máximo de solicitudes pendientes en la cola mediante el parámetro max. Aceptar solicitudes La función accept obtiene la primera conexión de la cola de conexiones pendientes, crea un nuevo buzón con las mismas propiedades que tiene el buzón que se utiliza para aceptar solicitudes y asigna un nuevo descriptor para el buzón recién creado. Su sintaxis es: int accept (int s, struct sockaddr_in *addr, int *len); Los argumentos que se le pasan a la función son el identificador de buzón (s), un puntero a una estructura de dirección (addr) y un puntero a un entero que contiene el tamaño de dicha estructura (len). La función devuelve el nuevo descriptor de buzón. Enviar/recibir información La función send se utiliza para enviar datos a un buzón conectado. Su sintaxis es: int send(int s, const char *msg, int len, int flags);

Los argumentos que se le pasan son el identificador del buzón (s), un puntero al buffer desde donde se van a enviar los datos (msg), la longitud del buffer de recepción (len) y por último se le pasa el parámetro flags para especificar unas opciones que permiten, entre otras cosas, ser usados por programas de diagnóstico por ejemplo. La función recv se utiliza para leer datos desde un socket conectado. Su sintaxis es: int recv(int s, char *buf, int len, int flags); Los argumentos que se le pasan son el identificador del buzón devuelto por la función accept (s), un puntero al buffer donde se van a recibir los datos (buf) y la longitud del buffer de recepción (len). El parámetro flags tiene el mismo significado que en send. Un proceso cliente necesita realizar algunas de las operaciones anteriormente indicadas y otras que desarrollamos a continuación para poder solicitar servicios por parte de un proceso servidor: Obtener la dirección remota Se utiliza la función gethostbyname, de forma similar a como se emplea en el proceso servidor. Obtener la dirección del puerto remoto Se utiliza la función getservbyname, de forma similar a como se emplea en el proceso servidor. Crear un buzón Se utiliza la función socket para crear buzones, de forma similar a como se emplea en el proceso servidor. Conectar con el servidor La función connect permite a un cliente iniciar una conexión con el buzón de un servidor. Su sintaxis es: int connect(int s, struct sockaddr *name, int namelen); Los argumentos que se le pasan a la función son el identificador del buzón (s), un puntero a una estructura de dirección (name) y un puntero a un entero que contiene el tamaño de dicha estructura (namelen). Enviar/recibir información Se utilizarán las funciones send o recv según sea el flujo de información que interese. Se emplea de forma similar a como se ha visto para el proceso servidor. En los programas 1 y 2 podemos ver un ejemplo que nos permite comprobar cómo se utilizan las llamadas al sistema que permiten crear un modelo cliente/servidor mediante buzones. Programa 1: Proceso cliente para la implementación del paso de mensajes #include <stdio.h> #include <signal.h> #include <errno.h> #include <sys/types.h> #include <sys/socket.h> #include <netdb.h> #include <netinet/in.h> #include <arpa/inet.h> main () /*declaración de variables y estructuras de datos */ int retcode, sock; struct sockaddr_in name; struct servent *servrec; struct hostent *hostrec; char buf[40], host[30]; int flag=0; /* Obtener host remoto del proceso servidor */ if ((hostrec=gethostbyname("almanzora"))==null)

error (1); /* Obtener puerto remoto del servicio */ if ((servrec=getservbyname( servicio1, tcp ))==NULL) error (2); /* Crear un socket */ if ((sock=socket(af_inet, SOCK_STREAM, 0))==-l) error (3); /* Actualizar nombre de socket */ name.sin_port = servrec->s_port; name.sin_family = hostrec->h_addrtype; name.sin_addr.s_addr = INADDR_ANY; /* Contactar con el servidor */ if ((retcode=connect(sock,&name,sizeof(name)))==-1) error (4); /* Enviar información al servidor */ strcpy (buf, Esto es un mensaje ); if ((retcode=send(sock,buf,sizeof(buf),flag))==-1) error (5); /* Cerrar conexión */ if (close (sock)==-1) error (6); } /* fin de main */ error (n) int n; switch (n) case 1: printf ( Error en gethostbyname \n ); break; case 2: printf ( Error en getservbyname \n ); break; case 3: printf ( Error en socket \n ); break; case 4: printf ( Error en connect \n ); break; case 5: printf ( Error en send \n ); break; case 6: printf ( Error en close \n ); break; } /* fin de switch */ exit (1); } /* fin de error */ Programa 2: Proceso servidor para la implementación del paso de mensajes #include <stdio.h> #include <signal.h> #include <errno.h> #include <sys/types.h> #include <sys/socket.h> #include <netinet/in.h> #include <netdb.h> #include <arpa/inet.h> main () /* declaración de variables y estructuras de datos */ char host[30]; struct hostent *hostrec; struct servent *servrec; struct sockaddr_in name, addr; int retcode, sock, newsock; int len=0; char buf[40]; /* Obtener nombre del host local */

if ((hostrec=gethostbyname("almanzora"))==null) error (1); /* Obtener puerto local */ if ((servrec=getservbyname( servicio1, tcp ))==NULL) error (2); /* Crear un socket */ if ((sock=socket(af_inet, SOCK_STREAM, 0))==-1) error (3); /* Actualizar nombre de socket */ name.sin_port = servrec -> s_port; name.sin_family = hostrec -> h_addrtype; name.sin_addr.s_addr = INADDR_ANY; /* Enlazar nombre al socket */ if ((retcode=bind(sock,&name,sizeof(name)))==-1) close (sock); error (4); } /* Escuchar solicitudes */ if ((retcode=listen(sock, 1)) == -1) error (5); /* Aceptar solicitudes */ memset (&addr, 0, sizeof (addr)); len = sizeof (addr); if ((newsock=accept(sock, &addr, &len)) == -1) error (6); /* Recibir un mensaje */ if (retcode=recv(newsock,buf,sizeof(buf),0)==-1) error (7); /* Visualizar informacion transferida */ printf ( %s \n, buf); /* Cerrar socket */ if (close (newsock) == -1) error (8); } /* fin de main */ error (n) int n; switch (n) case 1: printf ( Error en gethostbyname\n"); break; case 2: printf ( Error en getservbyname\n ); break; case 3: printf ( Error en socket\n ); break; case 4: printf ( Error en bind\n ); break; case 5: printf ( Error en listen\n ); break; case 6: printf ( Error en accept\n ); break; case 7: printf ( Error en recv\n ); break; case 8: printf ( Error en close\n ); break; } /* fin de switch */ exit (1); } /* fin de error */ Ejercicio Crear un programa que simule el juego de adivinar una frase (juego del ahorcado). Para ello, se creará un proceso cliente y otro proceso servidor. El proceso servidor solicitará a un usuario una frase y, posteriormente, recibirá del proceso cliente letras para comprobar si se encuentran en la frase. En caso afirmativo, el servidor informa al cliente de las posiciones donde se encuentra la letra; en caso negativo, lo que le envía es el número de errores que lleva cometidos. El

programa termina cuando se cometen 5 errores o cuando se adivina la frase completa. Limitar la frase para que no tenga más de 40 caracteres (incluyendo los espacios en blanco). Información complementaria En el capítulo 11 de [BACH86] y el 3 de [ANDL90] podemos encontrar información sobre la estructura de buzones implementada en Unix. [RIWE92] es una obra dedicada exclusivamente a la programación de aplicaciones de red. En este libro podemos encontrar toda la información necesaria para programar en los distintos dominios mediante buzones y con otras estructuras más avanzadas. En el capítulo 7 de [ROCH85] podemos encontrar información de otro método de implementación de mensajes mediante FIFOs. El capítulo 12 de [ROBB96] también desarrolla la comunicación cliente/servidor mediante diversos mecanismos de comunicación, entre los que se encuentran los buzones. Otra fuente de información aparece en la ayuda en línea (man) de las llamadas al sistema estudiadas.