SUN RPC basierte Client/Server
Das RPC-Modell sieht vor, dass entfernte Prozeduren, d.h. solche deren Programmcode auf einem anderen Rechner liegt, genau wie lokale Prozeduren aufgerufen werden können. Man sieht hier eine Analogie zum Client/Server-Modell, bei dem ein Server einen Dienst erbringt, der vom Client in Anspruch genommen wird. Ein solcher Dienst entspricht einer entfernten Prozedur im RPC Modell. Das Übertragen einer request-Nachricht entspricht dem Prozeduraufruf mit Parameterbergabe und die reply-Nachricht der Rückkehr aus der aufgerufenen Prozedur mit der Übergabe eines oder mehrerer Rückgabewerte. An der daraus resultierenden Kommunikation sind die folgenden Softwareschichten beteiligt:
- lokale Applikation
- Aufrufstumpf (subs)
- RPC-Library
- XDR-Library
- Sockets
Für den Programmierer sind diese Vorgänge jedoch weitgehend
transparent (unsichtbar). Er verwendet den Codegenerator
rpcgen
um aus einer
RPCL-Beschreibung
der bereitgestellten Prozeduren und Datentypen die Client- und Serverstubs
zu generieren. Diese enthalten wiederum Aufrufe der
RPC-Bibliotheksfunktionen.
Bei der Umsetzung eines RPC Client/Server-Modells wird dementsprechend wie folgt vorgegangen:
- Erzeugung einer RPCL-Beschreibung.
- Generierung der Client-/Serverstubs mit Hilfe von
rpcgen
. - Implementierung der bereitgestellten Client- bzw. Serverstubs.
RPCL-Beschreibung
Zur Beschreibung der Datentypen von Parametern und der Rückgabewerten
der RPCs wird die Syntax aus dem
XDR RFC
verwendet. Dazu die folgenden Beispiele:
typedef string filename<255>; /* Eine Definition eines neuen Typs */
struct Point /* ein Struktur */
{
int x; /* Strukturen werden oft benoetigt, da nur ein Parameter */
int y; /* bzw. Rueckgabewert verwendet werden darf. Strukturen sind deshalb erlaubt. */
}
const DOZEN = 12 /* Eine Konstante */
void /* Rueckgabewert fuer Prozeduren ohne Parameter */
enum color { RED=0, GREEN=1 } /* Ein Aufzaehlungstyp */
int zahlen <12> /* Ein Array von int-Wert mit maximal 12 Elementen */
int z2 <> /* Ein beliebig langes Array */
int z3 [12] /* Ein Array mit genau 12 Elementen */
string strlist <30><> /* Ein beliebig langes Array von Strings mit einer Maximallaenge von 30 Zeichen */
opaque diskblock[512] /* opaque steht fuer Daten, die bei der Uebertragung nicht von XDR veraendert werden */
Bei der Umsetzung einer Programmbeschreibung in RPCL ist zu beachten, das Kommentare im C-Stil sind erlaubt sind. Desweiteren muss jedes Programm eine 32-Bit Nummer haben, mit der es eindeutig identifiziert werden kann. Diese ProgrammID ist im Wertebereich von 0x00000000 bis 0x1fffffff von Sun für Standardprogramme reserviert, die bei Sun registriert wurden. Örtliche Systemadminstratoren können die ProgrammID im Wertebereich von 0x20000000 bis 0x3fffffff vergeben. Dieser Bereich kann auch für die Übung verwendet werden. Ab 0x40000000 bis 0x5fffffff steht der Wertebereich der ProgrammIDs für temporäre Programme zur Verfügung. Alle weiteren Nummern sind für zukünftige RPC-Erweiterungen reserviert.
Die Verwendung von Progamm- (IDs), Versions- sowie Prozedurnummern
erlaubt es mehreren Versionen eines Programms gleichzeitig aktiv zu sein,
da die Identifikation einer Prozedur durch ein Tripel aus Programm-, Versions-
und Prozedurnummer erfolgt. Dabei erfolgt die Umsetzung von Programm- und
Versionsnummern auf Ports dynamisch mit Hilfe des so genannten
Portmappers, der das einzige RPC-Serverprogramm mit festem Port
(111) ist.
Die RPCL-Beschreibung eines Programms, das die Methoden
long procA (void)
und string procB (int>
zur
Verfügung stellt, kann dann wie folgt aussehen:
/* P.x */
program P_PROG
{
version P_VERS
{
long procA (void) = 1;
string procB (int) = 2;
} = 1;
} = 0x31234567;
Generierung der Client-/Serverstubs
Mit Hilfe einer RPCL-Beschreibung können die Client- und Serverstubs
eines Programms durch das Kommando rpcgen
generiert werden (wobei P jeweils durch den eigenen
Programmnamen zu ersetzen ist).
Nach dem Aufruf des Kommandos rpcgen
enthalten die Dateien
P_clnt.c
und P_svc.c
die Client- bzw. Serverstubs,
die für die transparente Netzwerkkommunikation beim Prozeduraufruf sorgen.
Falls komplexe XDR-Datentypen als Parameter oder Rückgabewert verwendet
werden, werden entsprechende Filterfunktionen generiert, die in
P_xdr.c
zu finden sind.
Die Deklarationen der Stub-Funktionen findet man in P.h
, d.h.
ein Client, der eine entfernte Prozedur aufrufen soll, muss P.h
mit include
einbinden.
Wenn man unter Linux beim Aufruf von rpcgen
die Option
'-a'
angibt, werden außerdem die Quelldateien für einen
Beispielclient und -server entsprechend der in P.x
festgelegten Signatur generiert. Im Quellcode des Beispielservers müssen
jetzt nur noch die leer angelegten Prozedurrümpfe mit dem
anwendungsspezifischen Programmcode gefüllt werden, um einen
lauffähigen Server zu erhalten.
Hinweis: Da die RPC-Bibliothek sowie die XDR-Bibliothek ein Teil der Standard-C-Bibliothek unter Linux sind, müssen beim Linken keine spezielles Parameter angegeben werden.