1.Program C locates S by network address (including port) such that an initial request can be sent.
2. Program S deciphers message from C and responds
3. Cdeciphers message from S and responds if needed
Repeat 2,3 until done
Client/Server contexts I
Remote file systems -- operating system interface. Special hardware runs gamut from high-performance (e.g., striping) to low-performance (e.g., older machine, small memory -- no user interface, no graphics)
File servers --- application level service -- e.g. using serialization of objects
Client/Server contexts II
Database servers -- often direct, no opsys support
Network time servers -- obtain a time within limits. Simple case: time will fall between request and response for non-swapping process.
Program C locates S by network address (including port) such that an initial request can be sent.
Program S deciphers message from C and responds, but the response does not get through.
Meanwhile program C waits for response...
Many ways for something to go wrong, and programmers had to take many similar steps to account for these
Need for RPC
A number of the problems with requesting remote services are the same as when a procedure is called, or can be made to look like this.
If remote computing can be made to look like a procedure call, a familiar programming paradigm can be used to deal with the problems arising.
LPC / RPC transparency
Agreed goal was to make remote computing look as much like local computing as possible.
Using an Interface Definition Language (IDL) describe the interface between the local and remote programs. Compile with a special compiler. Generate stubs in which the real code is to be written.
Code was being written anyway, so adopted as a de facto standard before fully understood.
Not that easy
Semantics of RPC allow it to either look like LPC (local procedure call) or run efficiently, but not both.
Standard, embodied in millions of lines of code is flawed.
Failure of remote system
RPC works well if there are no failures, but it can be difficult to understand behaviors, and build robust code, in cases where failures occur. The question is then -- is the system under consideration one where failures might occur? (!)
Semantics of RPC are much better understood now.
A major re-engineering of RPC might be called for, but…
With alternative constructs such as CORBA, RMI, and possibly DCOM, probably not worth it.
Distributed stress… I
Distributed Stress…. II
Distributed Stress… III
Semantics for distributed systems
On the one hand… use modern theoretical understanding to build robust, reliable system
On the other hand… remember the lessons of the Web.
Easy RPC programming, hard application programming… restrictive form
Easy application programming (maybe), hard RPC considerations… flexible form
Restrictive RPC format
Restrictive RPC. Limits on the types of data, and on size of args passed. Fast, easy, on RPC side. Might be fine --- until some dynamic data object takes on a larger size (years later?) and major logic changes must be instituted to break up the data into smaller chunks.
Flexible RPC format
Flexible RPC -- complex RPC code, and not necessarily easy application writing. Loop with a single reference to a large data object ---
Copy to remote site each time
Cache at remote site
Tradeoff is between inefficiency (possibly fatal) and complicated code.
Marshalling and data types I
ASN.1 (Abstract Syntax Notation) -- self-describing data types (e.g., like old IBM variable-length strings)
XDR (external data representation) SUN NFS RPC format.
Marshalling and data types II
64-bit, 32-bit, 16-bit, integers/pointers
Big Endian, Little Endian (next slide)
Data alignment (word boundaries, byte boundaries?) Efficiency vs. storage space. Different needs for different systems. Different systems likely for different services.
Big-Endian -most significant byte on the left end of the word. Motorola.
copy no pointer-referenced data objects, but fetch them if referenced remotely (lazy)
What about LISP, etc., where everything is a pointer? -- Garbage collection?
Leave up to the user (complex user code)
Marshalling -- Null pointer
If you decide to copy everything, either proactively or in a lazy manner, your marshalling algorithm still may need to know application specifics. For example, what happens in a linked structure (e.g., tree) which has null pointers?
Each new client request to a server spawns a new thread to handle it.
Have to be careful to avoid synchronization problems, just as with operating systems resources
RPC and deadlock
Without threads, A binds to B which binds to C which in turn needs A, which is busy waiting for B.
With threads this can be avoided, unless A is bound to a non-sharable resource.
RPC and events
Windowing systems (like Win95 and Windows NT) use an event dispatch model, wherein, e.g., the code attached to a window will receive a call from the operating system (a callback) telling it to handle the fact that a mouse button was pushed. RPC can be invoked this way as well.
Threads vs. events
If a thread has been sleeping (blocking), and then wakes up to resume processing a client request, it has its state with it, and hence knows what to do next.
If an event is called to resume processing the next step in some client request, it must first restore the state of that request.