Serves RPC services over one or more transport listeners.
A Server owns three things: the service registry, the set of transport listeners, and the connections those listeners accept. Inbound request packets are resolved against the service registry and dispatched to the matching method.
Listeners and services may be registered before the server is started; they are activated by Start().
Server and everything reachable from it — its services' method bodies, the Reader, Writer, and UnaryWriter handles they are given, and every future those produce — belong to the dispatcher passed to the constructor, and may only be touched from the thread running that dispatcher. There is no locking.The functions below are the only exceptions. They may be called from any thread at any point in the server's life, including concurrently with the dispatcher and with each other:
Each of these hands a request to the server's dispatcher and returns; nothing is allocated on the calling thread. RegisterService() needs no completion signal, since a queued registration cannot fail. Unlike other pw_rpc2 futures, the ControlFuture the others return may be moved between threads or dropped on any thread. The *Blocking() forms instead block the calling thread until the operation finishes, and so must not be called from the dispatcher thread once started.
Before Start() there is no dispatcher thread to hand requests to, so listener registrations are applied on the calling thread instead and their futures come back already resolved. This is the one time Server touches its allocator off the dispatcher.
Close() and run the dispatcher until the returned future resolves, or call CloseBlocking() from a non-dispatcher thread. ~Server crashes otherwise. Closing unregisters every service and frees every listener and connection.Server instead. Public Member Functions | |
| constexpr | Server (Allocator &allocator, async2::Dispatcher &dispatcher) |
| Server (const Server &)=delete | |
| Server & | operator= (const Server &)=delete |
| Server (Server &&)=delete | |
| Server & | operator= (Server &&)=delete |
| RpcStatus | RegisterService (Service &service) |
| ControlFuture | RegisterListener (transport::ReliableDatagramListener &listener) |
| RpcStatus | RegisterListenerBlocking (transport::ReliableDatagramListener &listener) |
| ControlFuture | Close () |
| void | CloseBlocking () |
| void | Start () |
|
inlineconstexpr |
|
inline |
Tears down the server: stops every listener, closes every connection and the calls on it, and unregisters every service.
Callable from any thread. The returned future resolves to kOk once all of that has happened on the dispatcher. Calls still running end with kClosed. Closing is terminal; the server cannot be restarted.
|
inline |
Close(), but blocks the calling thread until teardown is complete.
Works on a server that was never started, in which case it returns immediately.
|
inline |
Starts accepting connections on listener.
Callable from any thread. The returned future resolves to:
kOk: the listener is registered.kClosed: the server is closing or closed.kResourceExhausted: the listener's bookkeeping could not be allocated.Dropping the future before it resolves withdraws the request.
Before Start(), the registration is applied on the calling thread and the future is returned already resolved; the listener begins accepting when the server starts.
|
inline |
RegisterListener(), but blocks the calling thread until the listener is registered. Returns the same codes as RegisterListener().
Registers a service with the server so its methods can be invoked.
Callable from any thread.
kOk: the registration is queued. The dispatcher applies it before processing any further packets.kClosed: the server is closing or closed.Registering a service whose ID is already registered is a fatal error, detected when the dispatcher applies the registration. The service stays registered until the server closes, and must outlive the server.
|
inline |
Starts the server on the dispatcher it was constructed with.
Callable from any thread, but only once, and not after Close().