Sockets de Unix - PowerPoint PPT Presentation

1 / 44
About This Presentation
Title:

Sockets de Unix

Description:

Title: PowerPoint Presentation Last modified by: Patricio Mart nez Barco Created Date: 1/1/1601 12:00:00 AM Document presentation format: Presentaci n en pantalla – PowerPoint PPT presentation

Number of Views:71
Avg rating:3.0/5.0
Slides: 45
Provided by: uaes
Category:

less

Transcript and Presenter's Notes

Title: Sockets de Unix


1
Sockets de Unix
  • Sistemas Informáticos Distribuidos

2
Sockets
  • Parte 1 Manejo de sockets desde C
  • Parte 2 Manejo de sockets desde JAVA

3
Sockets en C
  • Parte 1

4
Modelo OSI de ISO
MÁQUINA A
MÁQUINA B
APLICACIÓN
APLICACIÓN
PRESENTACIÓN
PRESENTACIÓN
SESIÓN
SESIÓN
TRANSPORTE
TRANSPORTE
RED
RED
ENLACE
ENLACE
FÍSICA
FÍSICA
5
Familias
  • Familia AF_UNIX Usa protocolos internos de Unix.
  • Familia AF_INET Usa protocolos de Internet, como
    el TCP (Transmisión Control Protocol).
  • Familia AF_CCITT Norma X.25 de CCITT.
  • Familia AF_NS Protocolos NS de XEROX.
  • Familia AF_SNA Protocolos IBM SNA.
  • Familia AF_DECnet.
  • Familia AF_APPLETALK. 

6
Tipos de conexión
  • Circuito virtual Mediante la búsqueda de enlaces
    libres, se establece un circuito virtual.
    Conexión permanente hasta el final de la
    comunicación. SOCK_STREAM
  • Datagramas no trabajan con circuitos
    permanentes. La transmisión se realiza a nivel de
    paquetes. SOCK_DGRAM

7
Direcciones de red
struct sockaddr u_short sa_family / familia
de sockets AF_xxxx / char sa_data14 / 14
bytes con la dirección./ / Su codificación
depende de la familia /
struct sockaddr_un short sun_family /
AF_UNIX / char sun_path108 / Path name
/
8
Direcciones de red (II)
struct in_addr u_long s_addr / 32 bits con la
identificación de la red y el host (en
binario) /   struct sockaddr_in short
sin_family /en este caso, AF_INET / u_short
sin_port / 16 bits con el número de puerto
/ in_addr sin_addr / id. red y host / char
sin_zero8 / 8 bytes sin usar /
9
Direcciones de red (III)
Número de puerto se usa para asociar el socket
al proceso que se está ejecutando. Si en una
misma máquina hay distintos sockets abiertos cada
uno de ellos deberá llevar un número de puerto
distinto, puesto que todos llevarán la misma
dirección de red.   Número de puerto puede
tomar valores entre 1024 y 65535. El sistema
proporciona automáticamente números de puerto que
estén libres entre 1024 y 5000 mediante ciertas
funciones. Del número 1 al 1024 están reservados
al sistema y no pueden ser usados por
aplicaciones de usuario.   La función int
rresvport (int port) reserva un puerto entre
1024 y 5000.   Si el número de puerto contiene un
0 antes de efectuar la operación BIND, el sistema
también le gestionará un número de forma
automática.
10
Funciones para convertir direcciones
  • unsigned long inet_addr (const char cp)
  • Convierte al formato decimal estándar del
    usuario apuntado por cp al formato binario
    definido en la estructura struct in_addr.
  • struct in_addr direccion
  • .................................
  • direccion.s_addr inet_addr(128.12.10.00)
  •  
  • Las direcciones en internet se dan al usuario en
    formato decimal formado por números del 0 al 255
    separados por puntos, que identifican la red o
    subred y el número de host.
  •  
  • char inet_ntoa ( struct in_addr in ) Hace la
    operación contraria.

11
Funciones para convertir formatos numéricos
a) big-endian dirección N byte más
significativo dirección N1 byte menos
significativo (IBM RS6000, SUN, ...,
TCP,UDP)   b) little-endian dirección N byte
menos significativo dirección N1 byte más
significativo DEC Alpha, Intel x86,...)
12
Funciones para convertir formatos numéricos (II)
  •  
  • unsigned long htonl ( unsigned long hostlong )
  • Convierte un long del formato de la máquina al de
    la red.
  • unsigned short htons ( unsigned short hostshort
    )
  • Convierte un short del formato de la máquina al
    de la red.
  • unsigned long ntohl ( unsigned long netlong )
  • Convierte un long del formato de la red al de la
    máquina.
  • unsigned short ntohs ( unsigned short netshort )
  • Convierte un short del formato de la red al de la
    máquina.
  •  
  • struct sockaddr_in servidor_addr
  • ........................................
  • servidor_addr.sin_port htons(7000)

13
Apertura de un punto terminal en un canal.
  • int socket (int af, int type, int protocol)
  • Socket crea un punto terminal para conectarse a
    un canal bidireccional, devuelve un descriptor
    del canal.
  • af - Es la familia AF_UNIX, AF_INET, AF_CCITT,
    AF_NS, ...
  • type - El tipo de conexión SOCK_STREAM,
    SOCK_DGRAM
  • protocol - Protocolo particular que se desea
    usar. Normalmente cada tipo de socket sólo tiene
    un protocolo, pero si hay más de uno se puede
    especificar. Si no, se pone un 0.
  • Si todo funciona bien, socket devuelve un
    descriptor de fichero. En caso contrario devuelve
    -1, quedando codificado el error en la variable
    global errno.

14
Nombre de un socket
  • int bind(int sfd, const void addr,int addrlen)
  • Bind une un socket a una dirección de red
    determinada.
  • Bind hace que el socket con descriptor sfd se una
    a la dirección de socket que especifica la
    estructura apuntada por addr y de longitud
    addrlen.
  • La estructura a la que apunta addr deberá ser
    struct sockaddr_un en el caso de la familia
    AF_UNIX, y será struct sockaddr_in en el caso de
    la familia AF_INET.
  • Si la llamada funciona correctamente, bind
    devuelve 0, en caso contrario -1.

15
Disponibilidad para recibir peticiones de
servicio.
  • int listen (int sfd, int backlog)
  • Listen habilita una cola asociada al socket
    descrito por sfd para alojar las peticiones de
    conexión que le realicen otros programas. La
    longitud de esa cola se especifica en backlog.
  • Listen sólo tiene sentido en sockets del tipo
    SOCK_STREAM.
  • Si listen funciona correctamente devuelve 0, y en
    caso de error -1.

16
Petición de conexión
  • int connect (int sfd,const void addr,int
    addrlen)
  • Llamada del proceso cliente para empezar a
    comunicar.
  • sfd descriptor del socket.
  • addr puntero a estructura de dirección del
    socket remoto con el que se quiere conectar.
    (struct sockaddr_in).
  • addrlen tamaño de la estructura.
  • En SOCK_DGRAM, connect especifica la dirección
    del socket remoto, pero no se conecta con él.
  • En SOCK_STREAM, connect intenta conexión
    devolviendo error si no se consigue (cuando está
    activo el modo de acceso no bloqueante O_NDELAY).
  • El modo de acceso al socket se puede modificar
    usando la función fcntl().
  • fcntl ( sfd, F_SETFL, O_NDELAY )
  • La conexión correcta devuelve un 0. Se devuelve
    -1 en caso de error.

17
Aceptación de conexión
  • int accept(int sfd, void addr, int addrlen)
  • Acepta demanda de servicio en sockets orientados
    a conexión.
  • sfd descriptor del socket.
  • accept extrae la primera llamada de la cola que
    ha creado listen sobre el socket, y después crea
    un nuevo socket con las mismas propiedades que
    sfd, reservándole un nuevo descriptor de fichero.
  • Si no hay peticiones para extraer de la cola,
    accept permanecerá bloqueada a menos que esté
    activo el control de acceso no bloqueante
    (O_NDELAY) en cuyo caso devolverá un error. 
  • addr debe apuntar a una estructura local de
    dirección de socket. La propia llamada accept
    rellenará esa estructura con la dirección del
    socket remoto que ha pedido la conexión. 
  • addrlen debe ser un puntero para permitir que la
    llamada sobrescriba sobre él el tamaño real de la
    dirección leída. 
  • Si no error, devolverá descriptor del nuevo
    socket. En error devuelve -1.

18
Lectura o recepción de mensajes de un socket
  • int read (int sfd, char buf, unsigned nbyte)
  • Read lee nbyte bytes del socket sfd y los
    almacena en el buffer apuntado por buf. Si no hay
    error, devuelve el número de bytes leídos.
  • ssize_t readv (int sfd, const struct iovec iov,
    size_t iovcnt)
  • struct iovec
  • caddr_t iov_base / Dirección inicial del
    buffer /
  • int iov_len / Tamaño en bytes del buffer /
  • Readv lee los datos del socket sfd y los
    distribuye entre los distintos buffers
    especificados por el array iov. El total de
    elementos de iov viene especificado por iovcnt
    iov0, .., ioviovcnt-1

19
Lectura o recepción de mensajes de un socket (II)
  • int recv (int sfd, void buf, int len, int flags)
  • int recvfrom (int sfd,void buf,int len,int
    flags,void from, int fromlen)
  • int recvmsg (int sfd, struct msghdr msg, int
    flags)
  • sfd descriptor del socket del que se lee.
  • buf puntero al buffer donde se escriben los
    datos leídos.
  • len número máximo de bytes que cabe en el
    buffer.
  • flags es una combinación de 2 bits
  • MSG_PEEK1 el dato leído del socket no se vacía,
    se volverá a leer.
  • MSG_OOB1 lee sólo los datos "urgentes" (mensajes
    fuera de banda).
  • Por lo tanto, flags puede valer 0 (00), 1 (01), 2
    (10) o 3 (11).
  • En AF_UNIX no puede tener activos ninguno de los
    dos anteriores.
  • Las 3 funciones devuelven el total de bytes
    leídos del socket.

20
Lectura o recepción de mensajes de un socket (III)
  • int recv (int sfd, void buf, int len, int flags)
  • int recvfrom (int sfd,void buf,int len,int
    flags,void from, int fromlen)
  • int recvmsg (int sfd, struct msghdr msg, int
    flags)
  • En SOCK_STREAM, las llamadas sólo pueden usarse
    después de haber establecido una conexión con
    CONNECT.
  • En los SOCK_DGRAM no es necesario, si se hace,
    entonces se recibe siempre del mismo, si no, se
    recibe de cualquiera.
  • Recvfrom puede devolver la dirección del socket
    desde el que se enviaron los datos. Si
    fromltgtNULL, al volver, la dirección del socket
    origen se recibirá en la estructura apuntada, y
    fromlen debe contener el tamaño de la dirección
    apuntada por from (al llamar a la función, la que
    tenga from, y al salir la que ha leído realmente)
  • En SOCK_STREAM, recvfrom recv.

21
Lectura o recepción de mensajes de un socket (IV)
  • int recv (int sfd, void buf, int len, int flags)
  • int recvfrom (int sfd,void buf,int len,int
    flags,void from, int fromlen)
  • int recvmsg (int sfd, struct msghdr msg, int
    flags)
  • recvmsg permite que los datos leídos puedan
    distribuirse entre varios buffers. Así msg es un
    array de cabeceras de mensaje con la siguiente
    estructura
  • struct msghdr
  • caddr_t msg_name / dirección de socket
    (opcional) /
  • int msg_namelen / tamaño de la dirección de
    socket /
  • struct iovec msg_iov / array de buffers
    sobre los que distribuir los datos leídos /
  • int msg_iovlen / num. de elementos del array
    msg_iov /
  • caddr_t msg_accrights / derechos de acceso /
  • int msg_accrightslen / tamaño de msg_accrights
    /

22
Escritura o envío de mensajes a un socket
  • int write (int sfd, char buf, unsigned nbyte)
  • Write escribe nbyte bytes del buffer apuntado por
    buf en el socket sfd. Si no hay error, devuelve
    el número de bytes escritos realmente.
  • ssize_t writev (int sfd, const struct iovec iov,
    size_t iovcnt)
  • Writev escribe los datos en el socket sfd
    tomándolos de los distintos buffers especificados
    por el array iov. El total de elementos de iov
    viene especificado por iovcnt.
  • Writev devuelve el número total de bytes
    escritos.

23
Escritura o envío de mensajes a un socket (II)
  • int send (int sfd, void buf, int len, int flags)
  • int sendto (int sfd, void buf, int len, int
    flags, void to, int tolen)
  • int sendmsg (int sfd, struct msghdr msg, int
    flags)
  • sfd descriptor del socket donde se escribe.
  • buf puntero al buffer de donde se leen los
    datos a escribir.
  • len número de bytes en el buffer.
  • flags puede valer 0 o MSG_OOB. (MSG_PEEK no
    tiene sentido aquí)
  • Las 3 funciones devuelven el total de bytes
    escritos en el socket.
  • En SOCK_STREAM, las llamadas sólo pueden usarse
    después de haber establecido una conexión con
    CONNECT.
  • En los SOCK_DGRAM no es necesario.

24
Obtención de nombres de socket
  • int getsockname(int sfd, void addr, int addrlen)
  • int getpeername(int sfd, void addr, int addrlen)
  • En la familia SOCK_STREAM.
  • Getsockname devuelve sobre la estructura apuntada
    por addr, la dirección del socket de descriptor
    sfd. 
  • Getpeername devuelve sobre la estructura apuntada
    por addr, la dirección del socket que se
    encuentra conectado al socket de descriptor sfd. 
  • addrlen indica el tamaño en bytes de la
    estructura apuntada por addr.

25
Nombre del nodo actual
  • int gethostname (char hostname, size_t size)
  • Se usa para determinar el nombre oficial que
    tiene un nodo en la red.
  • gethostname devuelve en el array apuntado por
    hostname el nombre oficial de host del ordenador
    que hace la llamada. Size contiene la longitud de
    ese array.

26
Pipes con sockets
  • int socketpair(int family, int type, int
    protocol, int sockvec2)
  • Crea un par de sockets que permiten la
    comunicación bidireccional.
  • family, type y protocol tiene el mismo
    significado que en la definición de socket
    aunque, por ahora, sólo admite la familia
    AF_UNIX.
  • sockvec es un vector que contendrá los 2
    descriptores de los sockets generados.

27
Cierre del socket
  • int close (int sfd)
  • cierra el socket en los dos sentidos de recepción
    y envío.
  • int shutdown(int sfd, int how)
  • Si how0 cierra recepción de datos, 1 cierra
    envío de datos y 2 cierra ambos.

28
Lectura del fichero etc/hosts
  • struct hostent gethostent()
  • struct hostent gethostbyname(char name)
  • struct hostent gethostbyaddr(const char addr,
    int len, int type)
  • int sethostent(int stayopen)
  • int endhostname()
  • etc/hosts contiene la información sobre todas las
    direcciones internet y los nombres de host de
    todos los nodos conectados a la red.
  • Si nuestra red tiene un servidor de nombres
    (DNS), es éste el que resuelve la correspondencia
    entre direcciones IP y nombres de máquinas.

29
Lectura del fichero etc/hosts (II)
  • struct hostent
  • char h_name
  • char h_aliases
  • int h_addrtype
  • int h_lenght
  • char h_addr_list
  • define h_addr h_addrlist0 / Para
    compatibilizar /
  • h_name nombre oficial del host.
  • h_aliases array con nombres alternativos del
    host
  • h_addrtype Siempre AF_INET.
  • h_lenght longitud en bytes de la estructura.
  • h_addr_list array de direcciones de red a las
    que responde el host. La lista se devuelve en
    formato de trabajo interno de la máquina
    (unsigned long), no como cadena de caracteres.

30
Lectura del fichero etc/hosts (III)
  • struct hostent gethostent()
  • struct hostent gethostbyname(char name)
  • struct hostent gethostbyaddr(const char addr,
    int len, int type)
  • int sethostent(int stayopen)
  • int endhostname()
  • Gethostent lee la siguiente línea del fichero
    devolviendo la estructura anterior. Si es la
    primera, además abre el fichero para lectura. Si
    es la última, devuelve NULL.
  • Sethostent abre el fichero para lectura y lo deja
    preparado para leer en la primera línea. Si
    además stayopen es distinto de 0, después de cada
    llamada de gethostent no se cierra el fichero.
  • Endhostent cierra el fichero.
  • Gethostbyname lee secuencialmente el fichero
    hasta encontrar el nombre de host, o su alias,
    que coincide con name.
  • Gethostbyaddr hace lo propio con la dirección
    addr con longitud len.

31
Esquema general C/S
Proceso Servidor
Proceso Cliente
Abrir canal
Abrir canal
Publicar dirección
Contactar servidor
Esperar petición servicio
proceso hijo
Pedir servicio
fork
Atender cliente
Esperar respuesta
proceso padre
Fin hijo
Fin cliente
32
Esquema Cliente-Servidor con sockets orientados
a conexión
Proceso Servidor
Proceso Cliente
socket( )
socket( )
bind( )
listen( )
accept( )
connect( )
read( )
write( )
write( )
read( )
close( )
33
Esquema Cliente-Servidorcon sockets orientados a
datagrama
Proceso Servidor
Proceso Cliente
socket( )
socket( )
bind( )
bind( )
recvfrom()
sendto( )
sendto( )
recvfrom()
close( )
34
Bibliografía
  • Márquez García, Francisco Manuel. UNIX,
    programación avanzada. RA-MA, 1993 
  • Rifflet, J.M. Comunicaciones en UNIX
    McGraw-Hill, 1992

35
Sockets en JAVA
  • Parte 2

36
Sockets en JAVA
  • Modelo general
  • SERVIDOR CLIENTE
  • ServerSocket(port,timeout) Socket(host,port)
  • accept()
  • ............ ............
  • OutputStream OutputStream
  • InputStream InputStream
  • ............ ............
  • close() close()

37
Conexión cliente
  • Socket miCliente
  • miCliente new Socket(maquina, numeroPuerto)
  • --------------------------------------------------
    -------------------
  • Socket miCliente
  • try
  • miCliente new Socket(maquina,numeroPuerto)
  • catch ( IOException e )
  • System.out.println ( e )

38
Conexión servidor
  • Socket miServicio
  • try
  • miServicio new ServerSocket(numeroPuerto)
  • catch ( IOException e )
  • System.out.println ( e )
  • .......
  • Socket socketServicio null
  • try
  • socketServicio miServicio.accept()
  • catch ( IOException e )
  • System.out.println ( e )

39
Creación Streams entrada
  • DataInputStream entrada (--- CLIENTE ---)
  • try
  • entrada new DataInputStream(
    miCliente.getInputStream() )
  • catch ( IOException e )
  • System.out.println ( e )
  • DataInputStream entrada (--- SERVIDOR ---)
  • try
  • entrada new DataInputStream(
    socketServicio.getInputStream() )
  • catch ( IOException e )
  • System.out.println ( e )

40
DataInputStream
  • Lectura del socket
  • read()
  • readChar()
  • readInt()
  • readDouble()
  • readLine()

41
Creación Streams salida
  • PrintStream salida (--- CLIENTE y SERVIDOR ---)
  • try
  • salida new PrintStream( miCliente.getOutputStre
    am() )
  • catch ( IOException e )
  • System.out.println ( e )
  • DataOutputStream salida (--- CLIENTE y SERVIDOR
    ---)
  • try
  • entrada new DataOutputStream(miCliente.getOutpu
    tStream() )
  • catch ( IOException e )
  • System.out.println ( e )

42
PrintStream//DataOutputStream
  • PrintStream
  • write()
  • println()
  • DataOutputStream
  • writeBytes()

43
Cierre Sockets
  • CLIENTE
  • PrintStream salida
  • try
  • salida.close()
  • entrada.close()
  • miCliente.close()
  • catch ( IOException e )
  • System.out.println ( e )

SERVIDOR PrintStream salida try
salida.close() entrada.close() socketServic
io.close() miServicio.close() catch (
IOException e ) System.out.println ( e
)
44
Clases útiles
  • Socket objeto básico
  • ServerSocket socket de servidor
  • DatagramSocket socket datagrama
  • DatagramPacket paquete datagrama
  • MulticastSocket comunicación en grupo
  • SocketImpl interfaz para crear un modelo de
    comunicación
Write a Comment
User Comments (0)
About PowerShow.com