Está en la página 1de 122

RPC: Remote Procedure Call

peticin
respuesta

El Llamado de procedimientos
remotos

Dr. Luis Enrique Colmenares

Diapo. No. 1

RPC: Remote Procedure Call

Cliente/Servidor: envo/recepcin mensajes

cliente

cliente

cliente

cliente

Dr. Luis Enrique Colmenares

(leer FA45 de arch1)

(ack)

(34759037F3247A)

(ack)

servidor

servidor

servidor

servidor

Diapo. No. 2

RPC: Remote Procedure Call

Desventajas paradigma envio/recepcin mensajes


Paradigma envio/recepcin es del tipo Entrada/Salida
procedimientos send(), receive() estn dedicados a realizar
E/S

E/S no es un concepto clave para los sistemas


centralizados; pero si para la computacin o clculo
distribuido
Objetivo: hacer el clculo distribuido como si fuera
clculo centralizado
Clculo centralizado: llamadas de procedimientos y/o
funciones
Dr. Luis Enrique Colmenares

Diapo. No. 3

RPC: Remote Procedure Call

Ejecucin de una llamada de procedimiento local


main()
{
:
count = read(fd, bytes, buf)
:
}

Variables locales
al main

a) Stack antes llamada read

Dr. Luis Enrique Colmenares

main()
{

main()
{

:
count = read(fd, bytes, buf)
:
}

:
count = read(fd, bytes, buf)
:
}

SP

Variables locales
al main
bytes
buf
fd
direccin regreso

b) Stack durante ejecucin read

Variables locales
al main

SP

SP

c) Stack despus llamada read

Diapo. No. 4

RPC: Remote Procedure Call

Tipos de paso de parmetros


Por valor
en el stack se copia el valor del parmetro
valor de salida es igual al valor de entrada

Por referencia
en el stack se almacena la direccin de la variable
es posible modificar el valor del parmetro

call-by-copy/restore
se copia el valor de la variable en el stack, (como en paso por valor)
al final de la ejecucin local se copia el valor que tiene la variable dentro
del procedimiento, en el stack
el procedimiento que mand llamar al procedimiento copia el valor final
en condiciones normales tiene el mismo efecto que el paso por referencia
Dr. Luis Enrique Colmenares

Diapo. No. 5

RPC: Remote Procedure Call

El RPC
Creado por Birrel & Nelson en 1984
Permiten a los programas llamar procedimientos localizados en
otras mquinas
Un proceso x en una mquina A, puede llamar un procedimiento
localizado en una mquina B
Informacin puede llevarse del proceso invocador al invocado
dentro de los parmetros
Ningn mensaje u operacin de E/S es visible para el programador
Problemas a resolver:
procedimientos invocador e invocado se ejecutan en diferentes mquinas, i.e.
diferentes direcciones y posiblemente diferentes arquitecturas
ambas mquinas pueden fallar
Dr. Luis Enrique Colmenares

Diapo. No. 6

RPC: Remote Procedure Call

Principio funcionamiento del RPC


Mquina Cliente

Mquina Servidor
stub del
cliente

call
cliente
return

Pack
parmetros

stub del
servidor
Unpack
parmetros

Unpack
resultado

kernel

call
servidor

Pack
resultado

return

kernel

Mensaje transportado en la red


Dr. Luis Enrique Colmenares

Diapo. No. 7

RPC: Remote Procedure Call

Proveniencia de los stubs


Varios sistemas: generados automticamente
rpcgen de Sun
generacion archivos esqueleto, para cliente y servidor, a
partir de un compilador y de la especificacin del
servicio

Rutinas de especificacin de stubs


rutinas de alto y bajo nivel
posibilidad de definir ms aspectos
timeouts
protocolos
Dr. Luis Enrique Colmenares

Diapo. No. 8

RPC: Remote Procedure Call

El
El paso
pasode
deparmetros
parmetros
stubs
Mquina Cliente

Mquina Servidor

mensaje
:
sum
:
4
n=sum(4,7);
:
7
:

mensaje sum(i,j)

kernel

kernel

Dr. Luis Enrique Colmenares

sum

4
7

int i,j;
{
return(i+j);
}

Diapo. No. 9

RPC: Remote Procedure Call

Aspectos a considerar en el paso de parmetros


Tipos de paso de parmetros
por valor
por referencia
call-by-copy/restore

Problemas a resolver
diferencias entre representacin de datos
diferencias en formatos
paso de apuntadores, (estructuras complejas)

Optimizacin
especificacin parmetros de entrada y salida
registros para paso de apuntadores

Dr. Luis Enrique Colmenares

Diapo. No. 10

RPC: Remote Procedure Call

Binding dinmico: especificacin formal servidor

#include <header.h>
specification of file_server, version 3.1
long read(in char name[MAX_PATH], out char buf[BUF_SIZE],
in long bytes, in long position);
long write(in char name[MAX_PATH], in char buf[BUF_SIZE],
in long bytes, in long position);
int create(in char[MAX_PATH], in int mode);
int delete(in char[MAX_PATH]);
end.

Dr. Luis Enrique Colmenares

Diapo. No. 11

RPC: Remote Procedure Call

Parmetros entrada/salida de la interfaz binder

Accin

Parmetros Entrada

Registrar

Nombre, versin, manejador, id nico

Suprimir

Nombre, versin, id nico

Buscar

Nombre, versin

Dr. Luis Enrique Colmenares

Salida

Manejador, id nico

Diapo. No. 12

RPC: Remote Procedure Call

Registro
Registrodel
delservidor
servidor

SERVIDOR

Nombre
Num. versin
Id.nico
Manejador,
(handler)
Otros
(autentificacin)

Dr. Luis Enrique Colmenares

Binder

Sistema Distribuido

Diapo. No. 13

RPC: Remote Procedure Call

Peticin
Peticincliente
cliente
error

3
servicio NO
disponible

Binder
proceso 1
solicitante

2
stub
cliente

servicio
disponible

Nombre, Num. versin,


Id.nico, Manejador

Dr. Luis Enrique Colmenares

Diapo. No. 14

RPC: Remote Procedure Call

Registro y localizacin de un servidor RPC


Paso 1: Este es
PRIMEPROG Version 1,
Estoy usando el puerto 1061

Servidor

Puerto
1061

Maquina Servidor
Puerto
111

Portmapper

Paso 2: Donde
esta PRIMEPROG
Version 1?

Paso 4: Llama
procedimiento 1.
Aqu estn los
datos

Prog Vers Puerto

Paso 3: Esta en
el puerto 1061

Cliente

Dr. Luis Enrique Colmenares

Diapo. No. 15

RPC: Remote Procedure Call

Binding y nombramiento servicios


Convencin para nmeros de programa de Sun
00000000 - 1FFFFFFF
20000000 - 3FFFFFFF
40000000 - 5FFFFFFF
nmeros)
60000000 - FFFFFFFF

definido por y administrado por Sun


definido por el usuario
de trnsito, (aplicaciones con generacin de
reservado para un futuro uso

El comando rpcinfo
Realiza una llamada RPC a un servidor RPC y reporta lo que encuentra.
Dependiendo de los parmetros es posible:
- listar todos los servicios de un RPC en un host
- listar todos los servicios RPC registrados con rpcbind versin 2
- realizar una llamada RPC al procedimiento 0 de un determinado programa
y de una determinada versin en un host dado.
Dr. Luis Enrique Colmenares

Diapo. No. 16

RPC: Remote Procedure Call

Sintaxis y opciones rpcinfo


Sintaxis
rpcinfo [ -m -s ] [ host ]
rpcinfo -p [ host ]
rpcinfo -T transport host prognum [ versnum ]
rpcinfo -l [ -T transport ] host prognum [ versnum ]
rpcinfo -b [-T transport ] prognum versnum
rpcinfo -d [-T transport ] prognum versnum
Algunas opciones
-T especifica el transporte sobre el cual el servicio es requerido
-a utiliza el parmetro como la direccin universal en el transporte
-b realiza un broadcast al procedimiento 0 de los prognum y versnum
especificados y reporta todos los hosts que respondieron
-d borra el regsitro correpondiente al prognum y versnum especificados
-l despliega una lista de entradas que contienen un prognum y un versnum
en el host especificado
-s despliega una lista consisa de todos los programas RPC registrados en
host. Si no se especifica ningn host tomo el host local
Dr. Luis Enrique Colmenares

Diapo. No. 17

RPC: Remote Procedure Call

Ejemplo rpcinfo

rmagnac:45>rpcinfo -s toto
ogram version(s)
netid(s)
service owner
00000
2,3,4
udp, tcp, tictls, ticosord, ticots
rpcbin
superuser
00029
2,1
ticots, ticotsord, ticlts
keyserv superuser
00078
4
ticots, ticotsord, ticlts
kerbd
superuser
00087
10
udp
admind superuser
00011 1
ticlts, udp
rquotad superuser
00002
3,2
ticlts, udp
rusersd superuser
00099
1
ticots, ticotsord, ticlts
superuser
00012
1
ticlts, udp
sprayd
superuser
00008
1
ticlts, udp
walld
superuser
00001
4,3,2
ticlts, udp
rstad
superuser
00024
1
ticots, ticotsord, ticlts, tcp, udp
status
superuser
00021
2,3,1
ticots, ticotsord, ticlts, tcp, udp
nlockmgr superuser
34177279 1,2
tcp
5001
rmagnac:46>

Dr. Luis Enrique Colmenares

Diapo. No. 18

RPC: Remote Procedure Call

Pasos de una Llamada a un Procedimiento Remoto


Mquina Servidora

Programa Servidor
procedimientos servicio

Portmapper

funcin dispatch

callrpc ()
host, programa, versin,
procedimiento, argumentos

errores o resultados
Programa Cliente

Mquina Cliente

Dr. Luis Enrique Colmenares

Diapo. No. 19

RPC: Remote Procedure Call

Niveles del Protocolo TCP/IP


5-7. SESIN

Aplicacin
Usuario

4. TRANSPORTE

TCP

UDP

3. RED

IP
1-2.ENLACE / FSICO

NIVELES
OSI

Interface
Hardware

RED
Dr. Luis Enrique Colmenares

Diapo. No. 20

RPC: Remote Procedure Call

Pasos en la ejecucin de un RPC

1. El procedimiento del cliente llama al client-stub normalmente.


2. El client-stub construye un mensaje y lo pasa al kernel.
3. El kernel enva el mensaje al kernel remoto.
4. El kernel remoto pasa el mensaje al server-stub.
5. El server-stub desempaca los parmetros y llama al servidor.
6. El servidor realiza el trabajo y regresa el resultado al stub.
7. El server-stub lo empaqueta en un mensaje y lo pasa al kernel.
8. El kernel remoto enva un mensaje al cliente.
9. El kernel del cliente le da el mensaje al client-stub.
10. El stub desempaca el resultado y lo regresa al cliente.

Dr. Luis Enrique Colmenares

Diapo. No. 21

RPC: Remote Procedure Call

Ruta crtica de cliente a servidor


Mquina Cliente
Cliente

Llamar procedimientos stub


Preparar mensaje buffer
Marshall los parmetros en el buffer
Poner los encabezados a los mensajes
Pasar al kernel

Stub
Cliente

Kernel
Mquina

Contexto switch al kernel


Copiar mensaje en el kernel
Determinar direcciones destino
Poner direccin en encabezado mensaje
Establecer la interfaz de la red
echar a andar el timer

Dr. Luis Enrique Colmenares

Mquina Servidor
Realizar sevicio Servidor

Llamar al servidor
Poner los parametros en el stack
Unmarshall parametros

Switch contexto a server stub


Copiar mensaje en server stub
Ver si stub esta esperando
Decidir a que stub darselo
Checar el paquete para validacin
Interrupcin de proceso

Servidor
Server
Stub

Kernel
Mquina

Diapo. No. 22

RPC: Remote Procedure Call

EL RPC DE SUN

El rpcgen y el lenguaje de especificacin RPCL


Ejemplos:
- Llamada procedimientos con un solo parmetro
- Llamada remota con mltiples parmetros

Dr. Luis Enrique Colmenares

Diapo. No. 23

RPC: Remote Procedure Call

user developed

Desarrollo de una Aplicacin


de Red con un
Compilador de Protocolo RPC
Especificacin RPC

RPC and data


representation
libraries

Compilador RPC

stub del cliente

filtros comunes
y archivo
encabezado

stub del servidor

compilar
y
ligar

compilar
y
ligar
funciones
cliente

cdigo cliente
Dr. Luis Enrique Colmenares

Bibliotecas de RPC y
de representacin
de datos

funciones
servidor

cdigo servidor
Diapo. No. 24

RPC: Remote Procedure Call

El lenguaje RPC (RPCL)


RPCL

Equivalente en C

-Comentarios
Igual que en lenguaje C
-Constantes simblicas
const MAX_SIZE = 8192

#define MAX_SIZE 8192

- Enumeraciones
enum colores{ROJO = 0, VERDE=1, enum colores { ROJO=0, VERDE=1,
AZUL=2};
AZUL=2};
typedef enum colores colores;
-Booleanos
bool termino;
bool_t termino;
-Arreglos tamao fijo
int alumnos[10];

Dr. Luis Enrique Colmenares

int alumnos[10];

Diapo. No. 25

RPC: Remote Procedure Call

RPCL

Equivalente en C

-Arreglos tamao variable


int a <12> /* a los mas 12 elementos*/
struct {
u_int a_len;
int *a_val;
} a;
int b<> /* cualquier numero de elementos */
struct {
u_int b_len;
int
*b_val;
} b;
Tamao mximo = parmetro maxsize en xdr_array()
No especificacin mximo => mximo valor puede tomar u_int;
Solo es posible trabajar con arreglos unidimensionales
-Estructuras
struct punto {
int x;
int y;
};
Dr. Luis Enrique Colmenares

struct punto {
int x;
int y;
};
typedef struct punto punto;
Diapo. No. 26

RPC: Remote Procedure Call

-Strings
No existen en C, RPCL convencin de terminacin en NULL
Tamao especifica mximo nmero caracteres permitidos en string
No especificado => tamao mximo = mximo valor u_int;
string nombre <32>
string nombresote<>

char *nombre;
char *nombresote;

-Uniones
Ms cercanas al registro variante de Pascal
union resultado switch (int errno){
struct resultado {
case 0:
int errno;
opaque data[1024];
union {
case 1:
char data[1024]
int
valor;
int valor;
default:
} resultado_u;
void
};
};
typedef struct resultado resultado;

Dr. Luis Enrique Colmenares

Diapo. No. 27

RPC: Remote Procedure Call

RPCL

-Datos opacos
Usados para describir datos que no tienen tipo
Dato puede ser de tamao fijo o variable

Equivalente en C

opaque diskblock[512];
char diskblock[512];
opaque filedata<1024>
struct {
u_int filedata_len;
char *filedata_val;
} filedata
-Typedef RPCL
Misma sintaxis que en C
Ejemplo define un fname_type usado para declarar strings de nombres de
archivos que tienen una longitud mxima de 255 caracteres
typedef string fname_type <255>

typedef char *fname_type;

- Identificadores
Compuestos de letras, nmeros y el underscore
Distincin entre mayusculas y minusculas

Dr. Luis Enrique Colmenares

Diapo. No. 28

RPC: Remote Procedure Call

Pasos
Pasospara
paraconvertir
convertirllamadas
llamadaslocales
localesen
enremotas
remotas

- Disear programa usando llamadas locales.


- Restructurar cada funcin de tal forma que slo tenga un parmetro
pasado por valor y asegurarse que trabaja
bien localmente.
- Crear un archivo de especificacin con extensin .x.
- Ejecutar rpcgen con opciones -a y -C para generar archivos necesarios.
- Usar el makefile generado para compilar los archivos. Es posible detectar
errores en las definiciones de tipos en el
archivo de especificacin.
- Insertar programa que va a llamar a la funcin en el archivo _client.c
generado por rpcgen.
- Insertar cdigo funcin local en el archivo _server.c generado por rpcgen.
- Intentar compilar los programas usando el makefile generado.
- Jugar, (fiddle), con el _server.c y el _client.c hasta que trabajen. Este
Dr. Luis Enrique Colmenares

Diapo. No. 29

RPC: Remote Procedure Call

Ejemplo aplicacin: permetro y rea de un cuadro

perimetro (a)
area(a)

:
per = perimetro(20)
:
sup = area(20
:

Dr. Luis Enrique Colmenares

int
double

:
4*a
:
a*a
:

Diapo. No. 30

RPC: Remote Procedure Call

Paso I
Diseo del
servicio local

Dr. Luis Enrique Colmenares

Diapo. No. 31

RPC: Remote Procedure Call

Calculo
Calculopermetro
permetroyyrea
reade
deun
uncuadrado
cuadrado
#include <stdio.h>

int perimetro(int a)
{
return 4*a;
}
double area (int a)
{
return a*a;
}

main(int argc, char *argv[])


{
int a;
int per;
double sup;
if (argc !=2 ) {
fprintf(stderr,"Error,uso: %s a \n",argv[0]);
exit(1);
}
a = atoi(argv[1]);
per = perimetro(a);
sup = area(a);
printf("El perimetro del cuadrado es %d \n",per);
printf("El area del cuadrado es %g \n",sup);
}
Dr. Luis Enrique Colmenares

Diapo. No. 32

RPC: Remote Procedure Call

Cdigo
Cdigodel
delservidor
servidorlocal:
local:servidor.c
servidor.c
#include cuad.h
int perimetro(int a)
{
int res;
res = 4*a;
return(res);
}
double area(int a)
{
double res;
res = a*a;
return(res);
}

Dr. Luis Enrique Colmenares

Diapo. No. 33

RPC: Remote Procedure Call

Cdigo
Cdigodel
delcliente
clientelocal:
local:cliente.c
cliente.c
#include <stdio.h>
#include <stdlib.h>
#include cuad.h
main(int argc, char *argv[])
{
int a;
int per;
double sup;
if (argc !=2 ) {
fprintf(stderr,"Error, uso: %s a \n",argv[0]);
exit(1);
}
a = atoi(argv[1]);
per = perimetro(a);
sup = area(a);
printf("El perimetro del cuadrado es %d \n",per);
printf("El area del cuadrado es %g \n",sup);
Dr. Luis Enrique Colmenares

Diapo. No. 34

RPC: Remote Procedure Call

El
Elarchivo
archivode
deencabezado
encabezadocuad.h
cuad.h

int perimetro(int);
double area(int);

Dr. Luis Enrique Colmenares

Diapo. No. 35

RPC: Remote Procedure Call

Compilando y ejecutando

rogomez@cuba:93>gcc cliente.c servidor.c -o cuadro


rogomez@cuba:94>./cuadro 5
El perimetro del cuadrado es 20
El area del cuadrado es 25
rogomez@cuba:95>./cuadro 2
El perimetro del cuadrado es 8
El area del cuadrado es 4
rogomez@cuba:96>

Dr. Luis Enrique Colmenares

Diapo. No. 36

RPC: Remote Procedure Call

Paso II
Diseo del archivo
de configuracin y
uso de rpcgen

Dr. Luis Enrique Colmenares

Diapo. No. 37

RPC: Remote Procedure Call

El
Elarchivo
archivode
deespecificacin
especificacincuadro.x
cuadro.x

/*Nombre archivo:
cuadro.x */

/*Nombre archivo:
cuadro.x */

program CUADRO_PROG {
version CUADRO_VERS{
int PERIMETRO(int)
= 1;
double AREA(int) =
2;
} = 1;
} = 0x311445566;

program CUADRO_PROG {
version CUADRO_VERS{
int PERIMETRO(int)
= 1;
double AREA(int) =
2;
} = 1;
} = 2;

Dr. Luis Enrique Colmenares

Diapo. No. 38

RPC: Remote Procedure Call

Nmeros
Nmeros de
de programas
programas remotos
remotos

Rango (hexadecimal)

Administrador

Tiempo de vida

Distribucin

00000000 - 1FFFFFFF
20000000 - 3FFFFFFF
40000000 - 5FFFFFFF
50000000 - 7FFFFFFF
80000000 - 9FFFFFFF
A0000000 - BFFFFFFF
C0000000 - DFFFFFFF
E0000000 - FFFFFFFF

Sun
Local
Desarrollador
Reservado
Reservado
Reservado
Reservado
Reservado

Permanente
Desconocido
Temporal

Pblica
Local
Local

Dr. Luis Enrique Colmenares

Diapo. No. 39

RPC: Remote Procedure Call

Sintxis
Sintxisdel
delrpcgen
rpcgen

rpcgen infile
rpcgen [ -a ] [ -A ] [ -b ] [ -C ] [-D name [ = value] ]
[ -i size ] [ -I [ -K seconds ] ] [ -L ]
[ -M ] [ -N ] [ -T ] [ -Y pathname ] infile
rpcgen [ -c | -h | -m | -t | -Sc | - Ss | -Sm ]
[ -o outfile ] [ infile ]
rpcgen [ -s nettype ] [ -o outfile ] [ infile]
rpcgen [ -n netid ] [ -o outfile ] [ infile ]

Dr. Luis Enrique Colmenares

Diapo. No. 40

RPC: Remote Procedure Call

Opciones rpcgen
-Dnombre[=valor]
-I
-K segundos
-L
-T
-s transporte
-o archivo-salida
-c
-h
-l
-m
-t
-a
-b
-C
-i tamao
-N
-Sc
-Ss
-Y path
Dr. Luis Enrique Colmenares

Define un smbolo (igual que #define)


Genera un cdigo para soporte de inted en el servidor (SunOS 4.1)
Servidor existe despus de segundos de inactividad
Los errores del servidor sern impresos en el syslog
Genera cdigo para soportar tablas de atencin de RPC
Genera el cdigo del servidor que soporta el transporte
Nombre del archivo de salida
Slo genera rutinas XDR
Slo genera el archivo de encabezado
Slo genera los stubs del cliente
Slo genera los stubs del servidor
Genera la tabla de atencin de RPC
Genera todos los archivos
Modo backward de compatibilidad (genera cdigo para SunOS4.1)
Genera lenguaje C de ANSI
Tamao a partir del cual se empieza a generar cdigo in-line
Soporta varios argumentos y llamado por valor
Genera esqueleto cliente que usa procedimientos remotos
Genera esqueleto servidor que define los procedimientos remotos
Nombre del directorio para encontrar pre-procesadores de C (cpp)
Diapo. No. 41

RPC: Remote Procedure Call

Archivos
Archivosgenerados
generadospor
porrpcgen
rpcgen

Comando a ejecutar:

$ rpcgen -C -a cuadro.x
Archivos generados:
Makefile.cuadro
makefile para compilar el cdigo del cliente y del servidor.
cuadro_clnt.c
contiene el stub del cliente, el cual usualmente no es modificado.
cuadro_svc.c
contiene stub servidor
cuadro.h
contiene todos los tipos XDR generados a partir de la especificacin.

Dr. Luis Enrique Colmenares

Diapo. No. 42

RPC: Remote Procedure Call

Archivos
Archivosgenerados
generadospor
porrpcgen
rpcgen

cuadro_client.c
programa esqueleto del cliente con llamadas dummy al servicio remoto.
Inserta cdigo para asignar los valores de los argumentos para el servicio
remoto.
cuadro_server.c
contiene stubs para servicios remotos. Inserta cdigo para la versin local
dentro de los stubs.
cuadro_xdr.c
contiene filtros XDR necesarios para los stubs del cliente y servidor.

Dr. Luis Enrique Colmenares

Diapo. No. 43

RPC: Remote Procedure Call

Archivos
Archivosgenerados
generadospor
porrpcgen
rpcgendel
delarchivo
archivocuadro.x
cuadro.x

cuadro_server.c
cuadro_svc.c

archivos servidor

cuadro_xdr.c
cuadro.x

rpcgen

cuadro.h

archivos comunes

Makefile.cuadro
cuadro_clnt.c

archivos cliente

cuadro_client.c

Dr. Luis Enrique Colmenares

Diapo. No. 44

RPC: Remote Procedure Call

Paso III
Insertar cdigo en
archivos generados
por rpcgen

Dr. Luis Enrique Colmenares

Diapo. No. 45

RPC: Remote Procedure Call

Programa
Programacuadro_client.c
cuadro_client.cgenerado
generadopor
porrpcgen
rpcgen
/*
* This is sample code generated by rpcgen.
* These are only templates and you can use them
* as a guideline for developing your own functions.
*/
#include "cuadro.h"
void
cuadro_prog_1(char *host)
{
CLIENT *clnt;
int *result_1;
int perimetro_1_arg;
double *result_2;
int area_1_arg;
Dr. Luis Enrique Colmenares

Diapo. No. 46

RPC: Remote Procedure Call

#ifndef DEBUG
clnt = clnt_create (host, CUADRO_PROG, CUADRO_VERS, "udp");
if (clnt == NULL) {
clnt_pcreateerror (host);
exit (1);
}
#endif /* DEBUG */
result_1 = perimetro_1(&perimetro_1_arg, clnt);
if (result_1 == (int *) NULL) {
clnt_perror (clnt, "call failed");
}
result_2 = area_1(&area_1_arg, clnt);
if (result_2 == (double *) NULL) {
clnt_perror (clnt, "call failed");
}
#ifndef
DEBUG
clnt_destroy (clnt);
#endif /* DEBUG */
}

Dr. Luis Enrique Colmenares

Diapo. No. 47

RPC: Remote Procedure Call

int
main (int argc, char *argv[])
{
char *host;
if (argc < 2) {
printf ("usage: %s server_host\n", argv[0]);
exit (1);
}
host = argv[1];
cuadro_prog_1 (host);
exit (0);
}

Dr. Luis Enrique Colmenares

Diapo. No. 48

RPC: Remote Procedure Call

Versin
Versinfinal
finaldel
delprograma
programa cuadro_client.c
cuadro_client.c
#include "cuadro.h"
int main (int argc, char *argv[])
{
CLIENT *clnt;
char *host;
int a;
int *per;
double *sup;
if (argc !=3 ) {
fprintf(stderr,"Error, uso: %s a host \n",argv[0]);
exit(1);
}
a = atoi(argv[1]);
host = argv[2];
Dr. Luis Enrique Colmenares

Diapo. No. 49

RPC: Remote Procedure Call

clnt = clnt_create (host, CUADRO_PROG, CUADRO_VERS, "udp");


if (clnt == NULL) {
clnt_pcreateerror (host);
exit (1);
}
per = perimetro_1(&a, clnt);
if (per == (int *) NULL) {
clnt_perror (clnt, "call failed");
}
sup = area_1(&a, clnt);
if (sup == (double *) NULL) {
clnt_perror (clnt, "call failed");
}
printf("El perimetro del cuadrado es %d \n",*per);
printf("El area del cuadrado es %f \n",*sup);
clnt_destroy(clnt);
}
Dr. Luis Enrique Colmenares

Diapo. No. 50

RPC: Remote Procedure Call

Archivo
Archivoesqueleto
esqueletode
decuadro_server.c
cuadro_server.c generado
generadopor
porrpcgen
rpcgen
#include "cuadro.h"
int * perimetro_1_svc(int *argp, struct svc_req *rqstp)
{
static int result;
/*
* insert server code here
*/
return &result;
}
double * area_1_svc(int *argp, struct svc_req *rqstp)
{
static double result;
/*
* insert server code here
*/
return &result;
}
Dr. Luis Enrique Colmenares

Diapo. No. 51

RPC: Remote Procedure Call

Versin
Versinfinal
finaldel
delprograma
programaservidor
servidor
#include "cuadro.h"
int * perimetro_1_svc(int *argp, struct svc_req *rqstp)
{
static int result;
result = 4* (*argp);
return &result;
}
double * area_1_svc(int *argp, struct svc_req *rqstp)
{
static double result;
result = (*argp) * (*argp);
return &result;
}

Dr. Luis Enrique Colmenares

Diapo. No. 52

RPC: Remote Procedure Call

Paso IV
Compilando y
ejecutando los
programas

Dr. Luis Enrique Colmenares

Diapo. No. 53

RPC: Remote Procedure Call

1. Usar makefile generado por rpcgen:


rogomez@costarica:281>make -f Makefile.cuadro
cc g -c cuadro_clnt.c -o cuadro_clnt.o
cc -g -c cuadro_client.c -o cuadro_client.o
cc -g -o cuadro_client cuadro_clnt.o cuadro_client.o -lnsl
cc -g -c cuadro_svc.c -o cuadro_svc.o
cc -g -c cuadro_server.c -o cuadro_server.o
cc -g -o cuadro_server cuadro_svc.o cuadro_server.o -lnsl
rogomez@costarica:282>
2. Se producen dos archivos:ejecutables:
cuadro_client y
cuadro_server

Dr. Luis Enrique Colmenares

Diapo. No. 54

RPC: Remote Procedure Call

2. Registrando al servidor de generacin de nmeros aleatorios


rogomez@costarica:282>./cuadro_server
rogomez@costarica:283>ps -aux | grep cuadro
rogomez 8600 1.0 732
308 pts/4 R 23:10:13 0:00 grep cuadro
rogomez 8068 3.4 1564 1012
?
S 23:10:27 0:00
./cuadro_server
rogomez@costarica:284>

3. Ejecutando el programa cliente:


rogomez@cuba:26>./cuadro_client 5 costarica
El perimetro del cuadrado es 20
El area del cuadrado es 25
rogomez@cuba:27>./cuadro_client 2 costarica
El perimetro del cuadrado es 8
El area del cuadrado es 4
rogomez@cuba:28>

Dr. Luis Enrique Colmenares

Diapo. No. 55

RPC: Remote Procedure Call

Ejemplos
de
cdigos
de stub

Dr. Luis Enrique Colmenares

Diapo. No. 56

RPC: Remote Procedure Call

Ejemplo de archivo stub-cliente: cuadro-clnt.c

/*
* Please do not edit this file.
* It was generated using rpcgen.
*/
#include <memory.h> /* for memset */
#include "cuadro.h"
/* Default timeout can be changed using clnt_control() */
static struct timeval TIMEOUT = { 25, 0 };

Dr. Luis Enrique Colmenares

Diapo. No. 57

RPC: Remote Procedure Call

int *
perimetro_1(int *argp, CLIENT *clnt)
{
static int clnt_res;
memset((char *)&clnt_res, 0, sizeof(clnt_res));
if (clnt_call (clnt, PERIMETRO,
(xdrproc_t) xdr_int, (caddr_t) argp,
(xdrproc_t) xdr_int, (caddr_t) &clnt_res,
TIMEOUT) != RPC_SUCCESS) {
return (NULL);
}
return (&clnt_res);
}

Dr. Luis Enrique Colmenares

Diapo. No. 58

RPC: Remote Procedure Call

double *
area_1(int *argp, CLIENT *clnt)
{
static double clnt_res;
memset((char *)&clnt_res, 0, sizeof(clnt_res));
if (clnt_call (clnt, AREA,
(xdrproc_t) xdr_int, (caddr_t) argp,
(xdrproc_t) xdr_double, (caddr_t) &clnt_res,
TIMEOUT) != RPC_SUCCESS) {
return (NULL);
}
return (&clnt_res);
}

Dr. Luis Enrique Colmenares

Diapo. No. 59

RPC: Remote Procedure Call

Ejemplo archivo stub-servidor: cuadro_svc.c


/*
* Please do not edit this file.
* It was generated using rpcgen.
*/
#include "cuadro.h"
#include <stdio.h>
#include <stdlib.h>
:
:
static void
cuadro_prog_1(struct svc_req *rqstp, register SVCXPRT *transp)
{
union {
int perimetro_1_arg;
int area_1_arg;
} argument;
char *result;
xdrproc_t _xdr_argument, _xdr_result;
char *(*local)(char *, struct svc_req *);
Dr. Luis Enrique Colmenares

Diapo. No. 60

RPC: Remote Procedure Call

switch (rqstp->rq_proc) {
case NULLPROC:
(void) svc_sendreply (transp, (xdrproc_t) xdr_void,
(char *)NULL);
return;
case PERIMETRO:
_xdr_argument = (xdrproc_t) xdr_int;
_xdr_result = (xdrproc_t) xdr_int;
local = (char *(*)(char *, struct svc_req *))
perimetro_1_svc;
break;
case AREA:
_xdr_argument = (xdrproc_t) xdr_int;
_xdr_result = (xdrproc_t) xdr_double;
local = (char *(*)(char *, struct svc_req *))
area_1_svc;
break;
Dr. Luis Enrique Colmenares

Diapo. No. 61

RPC: Remote Procedure Call

int main (int argc, char **argv)


{
register SVCXPRT *transp;
:
if (!svc_register(transp, CUADRO_PROG, CUADRO_VERS,
cuadro_prog_1, IPPROTO_UDP)) {
fprintf (stderr, "%s", "unable to register (CUADRO_PROG,
CUADRO_VERS, udp).");
exit(1);
}
:
svc_run ();
fprintf (stderr, "%s", "svc_run returned");
exit (1);
/* NOTREACHED */
}

Dr. Luis Enrique Colmenares

Diapo. No. 62

RPC: Remote Procedure Call

Ejemplo archivo encabezado: cuadro.h


/*
* Please do not edit this file.
* It was generated using rpcgen.
*/
#ifndef _CUADRO_H_RPCGEN
#define _CUADRO_H_RPCGEN
#include <rpc/rpc.h>
#ifdef __cplusplus
extern "C" {
#endif
#define CUADRO_PROG 0x31111111
#define CUADRO_VERS 1

Dr. Luis Enrique Colmenares

Diapo. No. 63

RPC: Remote Procedure Call

Ejemplo archivo encabezado: cuadro.h


#if defined(__STDC__) || defined(__cplusplus)
#define PERIMETRO 1
extern int * perimetro_1(int *, CLIENT *);
extern int * perimetro_1_svc(int *, struct svc_req *);
#define AREA 2
extern double * area_1(int *, CLIENT *);
extern double * area_1_svc(int *, struct svc_req *);
extern int cuadro_prog_1_freeresult (SVCXPRT *,xdrproc_t,caddr_t);
#else /* K&R C */
#define PERIMETRO 1
extern int * perimetro_1();
extern int * perimetro_1_svc();
#define AREA 2
extern double * area_1();
extern double * area_1_svc();
extern int cuadro_prog_1_freeresult ();
#endif /* K&R C */
:
:
Dr. Luis Enrique Colmenares

Diapo. No. 64

RPC: Remote Procedure Call

Llamadas con ms de un
parmetro
problemas y soluciones

Dr. Luis Enrique Colmenares

Diapo. No. 65

RPC: Remote Procedure Call

Ejemplo aplicacin: solucin ecuaciones 2do. grado

a,b,c

:
res1 = raiz(a,b,c)
:
res2 = complejo(a,b,c)
:

Dr. Luis Enrique Colmenares

r1, r2
real, imag

b b 24 ac
res=
2a
b ( b 24 ac )
complex =

j
2a
2a

Diapo. No. 66

RPC: Remote Procedure Call

Diseo del servicio a nivel local


Cdigo del servidor
Cdigo del cliente
Contenido del archivo encabezado
Compilacin y ejecucin

Dr. Luis Enrique Colmenares

Diapo. No. 67

RPC: Remote Procedure Call

Servidor Local
#include "encabeza.h"
struct raiz resuelve(a,b,c)
float a,b,c;
{
int temp;
struct raiz res;
res.error=0;
temp = (b*b) - (4*a*c);
if (temp < 0)
res.error=1;
else {
res.r1 = (-b + sqrt((double)temp)) / (2*a);
res.r2 = (-b - sqrt((double)temp)) / (2*a);
}
return res;

struct complex complejo(a,b,c)


float a,b,c;
{
float temp;
struct complex res;
temp = (b*b) - (4*a*c);
res.real = (-b)/(2*a);
res.imag = (temp)/(2*a);
return(res);
}

}
Dr. Luis Enrique Colmenares

Diapo. No. 68

RPC: Remote Procedure Call

Cliente Local
#include "encabeza.h"
#include stdio.h
#include stdlib.h
main(argc, argv)
int argc;
char *argv[];
struct complex rescom;
struct raiz result;
float a,b,c;
if (argc != 4) {
fprintf(stderr,"Error, uso: %s a b c\n",
argv[0]);
exit(1);
}

Dr. Luis Enrique Colmenares

a=(float)atoi(argv[1]);
b=(float)atoi(argv[2]);
c=(float)atoi(argv[3]);
result=resuelve(a,b,c);
if ( ! result.error ) {
printf("La solucion de (%.1f %.1f %.1f)\n",a,b,c);
printf("es %.5f y %.5f\n",result.r1, result.r2);
}
else {
rescom=complejo(a,b,c);
printf("La solucion de (%.1f %.1f %.1f)\n",a,b,c);
printf("es (%.5f %.5fj) y (%.5f %.5fj)\n",
rescom.real, rescom.imag,
rescom.real, (-1)*rescom.imag);
}
}

Diapo. No. 69

RPC: Remote Procedure Call

Archivo de encabezado local


#include <stdio.h>
#include <math.h>
struct raiz {
float r1;
float r2;
int error;
};
struct complex {
float real;
float imag;
};

Dr. Luis Enrique Colmenares

Diapo. No. 70

RPC: Remote Procedure Call

Compilando y ejecutando

rogomez@armagnac:156>cc cliente.c servicio.c -lm -o toto


rogomez@armagnac:157>./toto 1 -1 1
La solucion de (1.0 -1.0 1.0)
es (0.50000 -1.50000j) y (0.50000 1.50000j)
rogomez@armagnac:158>./toto 1 9 14
La solucion de (1.0 9.0 14.0)
es -2.00000 y -7.00000
rogomez@armagnac:159>./toto 1 1 1
La solucion de (1.0 1.0 1.0)
es (-0.50000 -1.50000j) y (-0.50000 1.50000j)
rogomez@armagnac:160>./toto 1 2 2
La solucion de (1.0 2.0 2.0)
es (-1.00000 -2.00000j) y (-1.00000 2.00000j)
rogomez@armagnac:161>
Dr. Luis Enrique Colmenares

Diapo. No. 71

RPC: Remote Procedure Call

Diseo del sistema a nivel remoto

Dr. Luis Enrique Colmenares

Especificacin del archivo raiz.x


Compilacin con rpcgen
Reescritura del archivo servidor remoto
Reescritura del archivo cliente remoto
Compilacin y ejecucin

Diapo. No. 72

RPC: Remote Procedure Call

Archivo especificacin raiz.x


struct datos{
float a;
float b;
float c;
};
struct raiz {
float r1;
float r2;
int error;
};
struct complex {
float real;
float imag;
};

Dr. Luis Enrique Colmenares

program RAIZ_PROG {
version RAIZ_VERS{
struct raiz RESUELVE(datos) = 1;
struct complex COMPLEJO(datos) = 2;
} = 1;
} = 0x31112345;
Esta parte o esta otra
program RAIZ_PROG {
version RAIZ_VERS{
struct raiz RESUELVE(datos) = 1;
struct complex COMPLEJO(datos) = 2;
} = 1;
} = 2;

Diapo. No. 73

RPC: Remote Procedure Call

Esqueleto del servidor


#include "raiz.h"
#include <stdio.h>
#include <stdlib.h> /* getenv, exit */
#include <signal.h>
struct raiz *
resuelve_1_svc(datos *argp,
struct svc_req *rqstp)
{
static struct raiz result;
/*
* insert server code here
*/

struct complex *
complejo_1_svc(datos *argp,
struct svc_req *rqstp)
{
static struct complex result;
/*
* insert server code here
*/
return (&result);
}

return (&result);
}
Dr. Luis Enrique Colmenares

Diapo. No. 74

RPC: Remote Procedure Call

Servidor remoto
#include "raiz.h"
struct raiz *
resuelve_1_svc(datos *argp, struct svc_req *rqstp)
{
static struct raiz res;
int temp;

struct complex *
complejo_1_svc(datos *argp, struct svc_req *rqstp)
{
static struct complex res;
float temp;

temp = (argp->b*argp->b) - (4*argp->a*argp->c);


res.error=0;
res.real = (-argp->b)/(2*argp->a);
temp = (argp->b*argp->b) - (4*argp->a*argp->c);
res.imag = (temp)/(2*argp->a);
if (temp < 0)
res.error=1;
return (&res);
else {
}
res.r1=(-argp->b + sqrt((double)temp))/ (2*argp->a);
res.r2=(-argp->b - sqrt((double)temp))/(2*argp->a);
}
return (&res);
}

Dr. Luis Enrique Colmenares

Diapo. No. 75

RPC: Remote Procedure Call

Esqueleto del cliente


#include "raiz.h"
#include <stdio.h>
#include <stdlib.h> /* getenv, exit */
void raiz_prog_1(char *host)
{
CLIENT *clnt;
struct raiz *result_1;
datos resuelve_1_arg;
struct complex *result_2;
datos complejo_1_arg;
#ifndef DEBUG
clnt = clnt_create(host, RAIZ_PROG, RAIZ_VERS, "netpath");
if (clnt == (CLIENT *) NULL) {
clnt_pcreateerror(host);
exit(1);
}
#endif /* DEBUG */
Dr. Luis Enrique Colmenares

Diapo. No. 76

RPC: Remote Procedure Call

#ifndef
#endif
}

result_1 = resuelve_1(&resuelve_1_arg, clnt);


if (result_1 == (struct raiz *) NULL) {
clnt_perror(clnt, "call failed");
}
result_2 = complejo_1(&complejo_1_arg, clnt);
if (result_2 == (struct complex *) NULL) {
clnt_perror(clnt, "call failed");
}
DEBUG
clnt_destroy(clnt);
/* DEBUG */
main(int argc, char *argv[])
{
char *host;
if (argc < 2) {
printf("usage: %s server_host\n", argv[0]);
exit(1);
}
host = argv[1];
raiz_prog_1(host);
}

Dr. Luis Enrique Colmenares

Diapo. No. 77

RPC: Remote Procedure Call

Cliente remoto

#include "raiz.h"
CLIENT *clnt;
struct raiz *raices;
datos data;
struct complex *rescom;
main(argc, argv)
int argc;
char *argv[];
{
char *host;

Dr. Luis Enrique Colmenares

if (argc !=5) {
printf("uso: %s host a b c \n", argv[0]);
exit(1);
}
host = argv[1];
data.a =(float)atoi(argv[2]);
data.b =(float)atoi(argv[3]);
data.c =(float)atoi(argv[4]);
clnt = clnt_create(host, RAIZ_PROG, RAIZ_VERS, "netpath");
if (clnt == (CLIENT *) NULL) {
clnt_pcreateerror(host);
exit(1);
}
raices = resuelve_1(&data, clnt);
if (raices == (struct raiz *) NULL) {
clnt_perror(clnt, "call failed");
}

Diapo. No. 78

RPC: Remote Procedure Call

if ( ! raices->error ) {
printf("La solucion de (%.1f %.1f %.1f)\n",data.a,data.b,data.c);
printf("es %.5f y %.5f\n",raices->r1, raices->r2);
}
else {
rescom = complejo_1(&data, clnt);
if (rescom == (struct complex *) NULL) {
clnt_perror(clnt, "call failed");
}
printf("La solucion de (%.1f %.1f %.1f)\n",data.a,data.b,data.c);
printf("es (%.5f %.5fj) y (%.5f %.5fj)\n",rescom->real, rescom->imag,
rescom->real, (-1)*(rescom->imag));
}
clnt_destroy(clnt);
}

Dr. Luis Enrique Colmenares

Diapo. No. 79

RPC: Remote Procedure Call

Compilacin y resultados ejecucin


rogomez@costarica:81>make -f makefile.raiz
cc -g -c raiz_clnt.c -o raiz_clnt.o
cc -g -c raiz_client.c -o raiz_client.o
cc -g -c raiz_xdr.c -o raiz_xdr.o
cc -g -o raiz_client raiz_clnt.o raiz_client.o raiz_xdr.o -lnsl
cc -g -c raiz_svc.c -o raiz_svc.o
cc -g -c raiz_server.c -o raiz_server.o
raiz_server.c: In function `resuelve_1_svc':
raiz_server.c:20: warning: type mismatch in implicit declaration for built-in function `sqrt'
cc -g -o raiz_server raiz_svc.o raiz_server.o raiz_xdr.o -lnsl
Undefined
first referenced
symbol
in file
sqrt
raiz_server.o
ld: fatal: Symbol referencing errors. No output written to raiz_server
make: *** [raiz_server] Error 1
[1] - Done
/usr/4local/bin/xvile raiz.x
rogomez@costarica:82>!ma
make -f makefile.raiz
cc -g -o raiz_server raiz_svc.o raiz_server.o raiz_xdr.o -lnsl -lm
rogomez@costarica:84>
Dr. Luis Enrique Colmenares

Diapo. No. 80

RPC: Remote Procedure Call

Makefile generado por rpcgen


# This is a template makefile generated
# Parameters
CLIENT = raiz_client
SERVER = raiz_server

by rpcgen

SOURCES_CLNT.c =
SOURCES_CLNT.h =
SOURCES_SVC.c =
SOURCES_SVC.h =
SOURCES.x = raiz.x
TARGETS_SVC.c = raiz_svc.c raiz_server.c raiz_xdr.c
TARGETS_CLNT.c = raiz_clnt.c raiz_client.c raiz_xdr.c
TARGETS = raiz.h raiz_xdr.c raiz_clnt.c raiz_svc.c raiz_client.c raiz_server.c
OBJECTS_CLNT = $(SOURCES_CLNT.c:%.c=%.o) $(TARGETS_CLNT.c:%.c=%.o)
OBJECTS_SVC = $(SOURCES_SVC.c:%.c=%.o) $(TARGETS_SVC.c:%.c=%.o)
# Compiler flags
CFLAGS += -g
LDLIBS += -lnsl -lm
RPCGENFLAGS =
Dr. Luis Enrique Colmenares

Diapo. No. 81

RPC: Remote Procedure Call

Ejecucin mquina servidor


rogomez@cuba:28>./raiz_server
rogomez@cuba:29>

Dr. Luis Enrique Colmenares

Ejecucin mquina cliente


rogomez@costarica:84>./raiz_client cuba 1 -1 1
La solucion de (1.0 -1.0 1.0)
es (0.50000 -1.50000j) y (0.50000 1.50000j)
rogomez@costarica:85>./raiz_client cuba 1 9 14
La solucion de (1.0 9.0 14.0)
es -2.00000 y -7.00000
rogomez@costarica:86>./raiz_client cuba 1 1 1
La solucion de (1.0 1.0 1.0)
es (-0.50000 -1.50000j) y (-0.50000 1.50000j)
rogomez@costarica:87>./raiz_client cuba 1 2 2
La solucion de (1.0 2.0 2.0)
es (-1.00000 -2.00000j) y (-1.00000 2.00000j)
rogomez@costarica:88>./raiz_client cuba 1 -3 40
La solucion de (1.0 -3.0 40.0)
es (1.50000 -75.50000j) y (1.50000 75.50000j)
rogomez@costarica:89>./raiz_client cuba 1 -3 -40
La solucion de (1.0 -3.0 -40.0)
es 8.00000 y -5.00000
rogomez@costarica:90>./raiz_client cuba 4 2 -1
La solucion de (4.0 2.0 -1.0)
es 0.30902 y -0.80902

Diapo. No. 82

RPC: Remote Procedure Call

Rutinas para el diseo de stubs


de los RPCs
Funciones de alto nivel

Dr. Luis Enrique Colmenares

Diapo. No. 83

RPC: Remote Procedure Call

Llamadas de alto y bajo nivel


lado del cliente
llamadas
de
alto nivel

callrpc()

clnt_destroy()
clnt_call()
clnt_control()
clnt_freeres()

Dr. Luis Enrique Colmenares

R
E
D

registerrpc()
svc_run()
Librera de Transporte

clnt_create()
clntudp_create()
clntcp_create()
clntraw_create()

Librera de Transporte

llamadas
de
bajo nivel

lado del servidor


llamadas
de
alto nivel

svc_udp_create()
svc_tcp_create()
svcraw_create()
svc_destroy()

llamadas
de
bajo nivel

svc_register()
svc_unregister()
svc_getargs()
svc_sendreply()

Diapo. No. 84

RPC: Remote Procedure Call

Diseo de filtros
para envo y
recepcin de datos
en RPC

Dr. Luis Enrique Colmenares

Diapo. No. 85

RPC: Remote Procedure Call

Funciones librera XDR


Conjunto funciones que convierten datos entre representaciones locales y XDR

formato XDR

little endian

big endian

Dos grupos de funciones:


- Creacin y manipulacin de streams XDR
- Conversin y transferencia de datos a y de streams XDR (filtros)
Forma ms simple de crear un filtro:
utilizar opcion -c del rpcgen

Dr. Luis Enrique Colmenares

Diapo. No. 86

RPC: Remote Procedure Call

Rutinas creacin y manejo streams XDR


Funcin

Descripcin

xdrmem_create()
xdrrec_create()
xdrstdio_create()

Crea un stream XDR en memoria


Crea un stream orientado registro
Crea un stream conectado a un archivo a travs
mecanismos E/S
Destruye un stream, des-asignando recursos
Regresa posicin en el stream XDR de tipo byte
Regresa apuntador a una pieza contigua del stream
Marca un registro como completo
Prueba de EOF despus del siguiente registro
Lee un nmero de bytes de un stream
Salta al principio del siguiente registro
Cuando es posible, reposiciona en un stream

xdr_destroy()
xdr_getpos()
xdr_inline()
xdrrec_endofrcord()
xdrrec_eof()
xdrrec_readbytes()
xdrrec_skiprecord()
xdr_setpos()

Dr. Luis Enrique Colmenares

Diapo. No. 87

RPC: Remote Procedure Call

Los filtros de XDR


Sintaxis:
bool_t xdrproc(XDR *xdrs, <tipo> argesp)

TRUE todo paso bien


FALSE si recibio datos malos

Filtros para tipos simples:


Tipo en C
char
short int
unsigned short int
int
unsigned int
long
unsigned long
float
double
void
enum
Dr. Luis Enrique Colmenares

Filtro
xdr_char()
xdr_short()
xdr_u_short()
xdr_int()
xdr_u_int()
xdr_long()
xdr_u_long()
xdr_float()
xdr_double()
xdr_void()
xdr_enum()

Tipo XDR
int
int
unsigned int
int
unsigned int
int
unsigned int
float
double
void
int
Diapo. No. 88

RPC: Remote Procedure Call

Filtros para datos complejos

Tipo de dato compuesto


Arreglo longitud variable con elemento
de tamao arbitrario
Arreglo de bytes de tamao variable
Datos de longitud fija (sin interpretar)
Referencias a objetos incluyendo apuntadores a NULL
Referencias a objetos
Arreglos de caracteres terminados en NULL
Unin discriminada, (unin con una enumeracin
que acta como discriminante)
Arreglo de longitud fija con elementos de
tamao arbitrario
Arreglo de caracteres terminado en NULL de
longitud arbitraria

Dr. Luis Enrique Colmenares

Filtro
xdr_array()
xdr_bytes()
xdr_opaque()
xdr_pointer()
xdr_reference()
xdr_string()
xdr_union()
xdr_vector()
xdr_wrapstring()

Diapo. No. 89

RPC: Remote Procedure Call

Ejemplo de filtros a la medida

struct netuser {
char *nu_hostname;
int nu_uid;
u_int
nu_glen;
int *nu_gids;
};
#define NLEN 255
/* host names < 256 caracteres */
#define NGRPS 20
/* usuario no puede estar en mas de 20 grupos */
bool_t xdr_netuser(xdr_handelp, nup)
XDR
*xdr_handlep;
struct netuser *nup;
{
if ( xdr_int(xdr_handlep, &nup-> nu_uid) == FALSE )
return(FALSE);
if ( xdr_string(xdr_handlep, &nup-> nu_hostname, NLEN) == FALSE )
return(FALSE)
if (xdr_u_int(xdr_handlep, &nup-> nu_glen) == FALSE )
return(FALSE)
return(xdr_array(xdr_handlep, &nup->nu_gids, &nup->nu_glen, NGRPS, sizeof(int),
xdr_int));
}
Dr. Luis Enrique Colmenares

Diapo. No. 90

RPC: Remote Procedure Call

Funciones
de
Alto Nivel

Dr. Luis Enrique Colmenares

Diapo. No. 91

RPC: Remote Procedure Call

La llamada callrpc()
Funcin que llama un procedimiento dado de alta en un host, a partir de su nmero
de programa, versin y procedimiento.
Sintaxis:
int callrpc(host, prognum, versnum, procnum, inproc, in, outproc, out)
char * host;
nombre mquina que ofrece el servicio
u_long prognum; nmero de programa
u_long versnum; nmero de versin
u_long procnum; nmero de procedimienrto
xdrproc_t inproc;
direccin filtro XDR que codifica los argumentos
char *in;
argumentos de entrada
xdrproc_t outproc; direccin filtro XDR que decofica valores regreso
char *out;
direccin de los valores de regreso

Dr. Luis Enrique Colmenares

Diapo. No. 92

RPC: Remote Procedure Call

Valor de regreso:
- de tipo entero;
- puede castearse a un tipo clnt_stat definido en <rpc/rpc.h> y pasarlo
a clnt_sperrno() para obtener un mensaje de error
- clnt_stat es un tipo enumeracin de C, que contiene los posibles
valores de regreso del RPC
Intenta llamar cinco veces, (cada cinco segundos), si no recibe nada en 25 segs,
regresa un valor clnt_stat de RPC_TIMEOUT
Ejemplo uso:
enum clnt_stat algo;
:
algo = callrpc(host, TOTOPROG, TOTOVERS, TOTO,xdr_toto, toto_in, xdr_toto,
toto_out);
if (algo != 0)
clnt_perror(algo);
:
Dr. Luis Enrique Colmenares

Diapo. No. 93

RPC: Remote Procedure Call

La llamada registerrpc()
Funcin para registrar un procedimiento, (procname), en el servicio de registro del
servicio de red, (i.e. portmapper)
Sintaxis:
int register(prognum, versnum, procnum, procname, inproc, outproc)
u_long prognum;
nmero del programa
u_long versnum; nmero de versin
u_long procnum;
nmero de procedimiento
char *(*procname)(); procedimiento que otorga el servicio
xdrproc_t inproc;
direccin filtro decodica argumentos entrada
xdrproc_t outproc;
direccin filtro codifica argumentos salida
Valor regreso:
0: si todo sali bien
-1: en caso de error
Dr. Luis Enrique Colmenares

Diapo. No. 94

RPC: Remote Procedure Call

Ejemplo:
:
if (registerrpc (TOTOPROG, TOTOVERS, TOTO, toto, xdr_toto,
xdr_toto) == -1) {
< rutina de error >
La funcin toto() atender las peticiones que se haga a la combinacin
TOTOPROG, TOTOVERS y TOTO

Dr. Luis Enrique Colmenares

Diapo. No. 95

RPC: Remote Procedure Call

La llamada svc_run
Rutina que provoca que el proceso se ponga a escuchar peticiones
Rutina nunca regresa control a la funcin que la invoca a menos que un error
fatal se detecte
No toma argumentos y no regresa ningn resultado
Rutina llamada una vez que se registr exitosamente el procedimiento
Representa el despachador/expedidor de la librera de RPCs
Espera a que reciba una peticin, para enviarla despus al procedimiento
adecuado
Sintaxis:
svc_run();

Ejemplo uso:
:
registerrpc(PROGNUM, VERSNUM, PROC, toto, xdr_toto, xdr_toto);
svc_run();
fprintf(stderr, Error en la llamada de svc_run \n);
}
Dr. Luis Enrique Colmenares

Diapo. No. 96

RPC: Remote Procedure Call

Ejemplo: diseo de un sistema de lectura de


directorios remotos
area( )
perimetro( )

Dr. Luis Enrique Colmenares

Diapo. No. 97

RPC: Remote Procedure Call

Pasos para el diseo del sistema

Diseo de un servidor local


Diseo del cliente local
Compilacin y ejecucin programas locales
Asignacin de los servicios
numero de programa, versin
nombre procedimiento y paramtros

Diseo programa servidor


Diseo stub del servidor
Diseo programa cliente
Diseo stub del cliente
Compilacin programas
Prueba del sistema

Dr. Luis Enrique Colmenares

Diapo. No. 98

RPC: Remote Procedure Call

Calculo permetro y rea de un cuadrado


#include <stdio.h>

int perimetro(int a)
{
return 4*a;
}
double area (int a)
{
return a*a;
}

main(int argc, char *argv[])


{
int lado;
int per;
float sup;
if (argc !=2 ) {
fprintf(stderr,"Error,uso: %s lado \n",argv[0]);
exit(1);
}
lado = atoi(argv[1]);
per = perimetro(lado);
sup = area(lado);
printf("El perimetro del cuadrado es %d \n",per);
printf("El area del cuadrado es %f \n",sup);
}
Dr. Luis Enrique Colmenares

Diapo. No. 99

RPC: Remote Procedure Call

Archivo encabezado: cuadro.h

/* nmero de programa */
#define CUADROPROG ((u_long) 0x3111445566)
/* nmero de versin */
#define CUADROVERS
((u_long) 1)
/* procedimiento 1 */
#define PERIMETRO

((u_long) 1)

/* procedimiento 2 */
#define AREAS
((u_long) 2)

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Las funciones del servidor


/* Nombre del archivo: server_clnt.c */
int *perimetro(int *lado)
{
static int res;
result = 4* (*lado);
return &res;
}
float *area(int *lado)
{
static double res;
result = (*lado) * (*lado);
return &res;
}
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

El stub del servidor


/* Nombre del archivo: servidor.c */
#include <rpc/rpc.h>
#include cuadro.h
main()
{
printf(Dando de alta el servicio \n);
registerrpc(CUADROPROG, CUADROVERS, PERIMETRO
perimetro, xdr_int, xdr_int);
registerrpc(CUADROPROG, CUADROVERS, AREA,
area, xdr_int, xdr_float);
printf(En espera de peticiones \n);
svc_run();
}

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

El stub del cliente (1)


/* Nombre archivo: client_clnt.c */
int *perimetro(char *host, int *lado)
{
static int res;
enum clnt_stat status;
status = callrpc(host, CUADROPROG, CUADROVERS, PERIMETRO,
(xdrproc_t)xdr_int, (char *)lado,
(xdrproc_t)xdr_int, (char *)&res);
if (status !=0 ) {
clnt_perrno(status);
return -1;
}
return &res;
}
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

El stub del cliente (2)


/* Nombre archivo: client_clnt.c */
float *area(char *host, int *lado)
{
static float res;
enum clnt_stat clnt_stat;
clnt_stat = callrpc(host, CUADROPROG, CUADROVERS, AREA,
(xdrproc_t) xdr_int, (char *)lado,
(xdrproc_t)xdr_float, (char*)&res);
if (clnt_stat !=0 )
{
clnt_perrno(clnt_stat);
return -1;
}
return res;
}
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Cdigo del cliente


#include <stdio.h>
#include <rpc/rpc.h>
/* Nombre archivo: cliente.c
* /
#include cuadro.h
main(int argc, char *argv[])
{
int lado;
int *per;
float *sup;
char *host;
if (argc !=3 ) {
fprintf(stderr,"Error, uso: %s lado host \n",argv[0]);
exit(1);
}
lado = atoi(argv[1]);
host = argv[2];
per = perimetro(host, &lado);
sup = area(host, &lado);
printf("El perimetro del cuadrado es %d \n",*per);
printf("El area del cuadrado es %d \n",*sup);
}Enrique Colmenares
Dr. Luis
Diapo. No.

RPC: Remote Procedure Call

Compilando y ejecutando

En el servidor (armagnac):
rogomez@armagnac:129>gcc servidor.c server_clnt.c -o server
rogomez@armagnac:130>./server
Dado de alta el servicio
En espera de peticiones

En el cliente (tequila):
rogomez@tequila:85>gcc cliente.c client_clnt.c -o client
rogomez@tequila:86>./client 5 armagnac
El perimetro del cuadrado es 20
El area del cuadrado es 25.000000
rogomez@tequila:87>./client 10 armagnac
El perimetro del cuadrado es 40
El area del cuadrado es 100.000000
rogomez@tequila:88>
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

El RPC en presencia de fallas


Consecuencias y comportamiento

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Posibles fallas en un RPC


1. El cliente es incapaz de localizar al servidor.
2. El mensaje de peticin del cliente al servidor se perdi.
3. El mensaje de respuesta del servidor al cliente se perdi.
4. El servidor fall (crashes) despus de recibir una peticin.
5. El cliente fall (crashes) despus de enviar una peticin.

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

1. Cliente incapaz localizar servidor


Uso de timeouts
Cliente puede recibir un -1 en caso de falla, y usar
errno para aclaracin
Problema: que pasa si el resultado del servicio es
el mismo que el cdigo de error
Alternativa: alcanzar una excepcin (no todos los
lenguajes soportan excepciones)
Lenguaje ADA lo soporta
La excepcin es alcanzada por el stub del cliente no por
el proceso cliente

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

2. Perdida mensaje peticin


Ncleo empieza un timer cuando se enva el mensaje
Si el timer expira antes de recibir respuesta o un ack,
el kernel envia la peticin de nuevo
No se alcanza una excepcin, ya que es el ncleo el
que retransmite
Si el mensaje se perdi: el servidor no podra
establecer la diferencia entre el primer mensaje
enviado y el resto
Tambin es posible que se perdan muchos mensajes
y el ncleo concluya errneamente que el servidor
esta inactivo
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

3. Perdida mensaje respuesta


Ms difcil de tratar
Solucin obvia: timer
Problema: kernel cliente no sabe por que no hay
respuesta
Caracterstica peticin: idempotencia
Otra solucin: numeracin de las peticiones de tal
forma que el servidor pueda diferenciar las peticiones
Otra ms: usar un bit en el encabezado del mensaje
para diferenciar peticiones iniciales de las
retransmisiones
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

4. Cada del servidor


Pet

Pet
Recibir
Ejecutar
Contestar

Resp

(a) Caso Normal

No
Resp

Recibir
Ejecutar
Crash
(b) Crash despus ejecucin

Pet
Recibir
Crash
No
Resp
Dr. Luis Enrique Colmenares

(c) Crash antes ejecucin


Diapo. No.

RPC: Remote Procedure Call

Estrategas cada servidor


At least once (semntica de al menos una vez)
esperar a que el servidor reviva

At most once (semntica de a lo ms una vez)


se da por vencido inmediatamente

Ninguna garanta
servidor no reporta nada

Exactamente una vez


poltica tec: todo bien y a la primera

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

5. Cada del cliente


A quin se le entrega el resultado del servicio solicitado?
La comunicacin esta activa y ningn pariente esta
esperando el resultado
El proceso o la comunicacin reciben el nombre de
hurfano, con los siguientes problemas.
desperdicio ciclos CPU
bloqueo recursos
confusin cuando el cliente se recupera

Deteccin cada cliente: timeouts o esperar que el cliente


reinicialize y anuncie su presencia

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Tratamiento de hurfanos
En el cliente:
Cuando el cliente revive este limpia todos sus clculos
previos de hurfanos.
Esto requiere de tener conocimiento de las pasadas
actividades de RPC no terminadas y la habilidad de
localizarlas (checkpoints, logs, etc.)

El servidor:
Ocasionalmente intenta localizar los propietarios de sus
operaciones remotas y aborta aquellas de las que no
puede encontrar su dueo

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Se requiere de un revocacin (vuelta hacia atrs) de los


roles del cliente y servidor, que puede complicar el
diseo simple del RPC

Principales tcnicas

Exterminacin
Reencarnacin
Reencarnacin gentil
Expiracin
Adopcin

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Exterminacin
Antes que stub-cliente enve un RPC realiza una
copia:
la copia se hace en disco
se le conoce como logging message
incluye de que se trata todo el mensaje

Despus de reestablecerse el loggin es verificado y el


hurfano es exterminado
Desventajas:
hurfanos que realizaron otras llamadas son imposibles de
localizar
gasto de escritura en un disco para cada RPC

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Reencarnacin
No es necesario escribir en disco
Dividir tiempo en pocas secuencialmente
numeradas
Cuando cliente re-vive hace un broadcast a todas las
mquinas declarando el comienzo de una nueva
poca
Cuando el broadcast llega, todas las comunicaciones
remotas son eliminadas
Algunos hurfanos pueden sobrevivir si el nmero
de poca no coincide
Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Reencarnacin Gentil
Cuando un broadcast de poca llega, cada
mquina verifica si no hay comunicaciones
remotas, si es as intenta localizar a su dueo
Solo si el dueo no puede localizarse el clculo es
abortado

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Expiracin
A cada RPC se le asocia un tiempo T para realizar
un trabajo
La operacin es abortada cuando se alcanza dicho
tiempo T
Por otro lado, si despus de una cada el servidor
espera un tiempo T antes de que el cliente reviva,
todos los hurfanos ya se habrn ido.
Es posible que el cliente solicite tiempo adicional
Problema: elegir un buen valor de T

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Adopcin
Tcnica basada en redundancia
Se cuenta con un proceso, vigilante, que vigila lo
que otro esta realizando
el proceso vigilante pregunta al proceso activo
el proceso activo informa al proceso vigilante

Si el proceso activo cae, el proceso vigilante toma


su lugar
Tcnica usada en clusters

Dr. Luis Enrique Colmenares

Diapo. No.

RPC: Remote Procedure Call

Las peticiones autocontenidas y el


concepto de atomicidad
Es posible que un hurfano deje al servidor en un
estado inconsistente
cliente puede poner candados en archivos servidor

Solucin: peticiones autocontenidas


una sola peticin contiene todos los pasos necesarios
para satisfacer el servicio requerido

Caracterstica: atomicidad
toda la peticin se satisface, o no se hace nada
Dr. Luis Enrique Colmenares

Diapo. No.

También podría gustarte