===================================================================== Notes on generated files and their interfaces with the etch runtime ===================================================================== Each service XXXX will include the following generated and/or user-created (i.e. not runtime) files: base_XXXX_client default stub functions for all client implementations base_XXXX_server default stub functions for all server implementations impl_XXXX_client user's implementation of base_XXXX_client functions impl_XXXX_server user's implementation of base_XXXX_server functions main_XXXX_client executable entry point for client main_XXXX_listener executable entry point for server XXXX class representation of user IDL for service XXXX XXXX_client interface defining client-directed functions to be implemented XXXX_server interface defining server functions to be implemented XXXX_helper static methods, interfaces and constants for creation of server and client instances remote_XXXX send(), begin_call(), end_call(), transport control (start , stop, etc), plus async wrapper remote_XXXX_client client extension of remote_XXXX remote_XXXX_server server extension of remote_XXXX; async service method implementations stub_XXXX base stub for service XXXX stub_XXXX_client client stub stub_XXXX_server server stub; thread procs for each message type, calling service impl methods. value_factory_XXXX type declarations, type map, class to type map, type serializers, validators, extends default vf -------------------------------------------------------- java binding's instantiation of a listener -------------------------------------------------------- 1. XXXXHelper.newListener(uri, rex, funcNewXXXXServer) 2. transportFactory.getListener(uri, resx, funcNewServer) 3. TransportFactory f = tcpfactory. 4. tcpfactory.newListener(funcNewServer): 5. define onAccepted, which will create the delivery service 6. tcpfactory.newListener() will return the Transport interface, which is a TcpListener implementing a Transport 1. JAVA MAIN calls transport = helper.newListener(main_new_perf_server) 2. HELPER.newListener (main_new_perf_server) a. init resources, create perfVF and put to resx b. transport = TransportFactory.getListener (helper_new_server) c. return transport 3. TransportFactory.getListener (helper_new_server) a. return TcpTransportFactory.newListener(resx, helper_new_server); 4. TcpTransportFactory.newListener(resx, helper_new_server); a. new SessionListener() b. new TcpListener(resx); c. TcpListener.setSession(SessionListener); d. return TcpListener - TcpListener.OnSessionAccepted(clientsocket) a. deliverysvc = newTransport() b. CALLBACK to helper_new_server(delivery); c. delivery.TransportControl(START); 5. HELPER_new_server(delivery) a. new RemotePerfClient(... b. PerfServer server = CALLBACK to MAIN_new_perf_server(remoteclient); c. new StubPerfServer(delivery, server); main () // pseudocode for server executable { // see above comments for flow. we pass around the accepted handler which will construct the specific server side components i_sessionlistener* lxr = XXXX_helper.new_listener (uri, NULL, funcptr(new_XXXX_server)); result = lxr->transport_control (lxr, START_WAITUP, nseconds); } etch_transport* new_listener (uri, resources, funcptr(new_XXXX_server) ) // from PerfHelper.newListener { etch_resources* resx = init_resx(resx); valuefactory_XXXX = new_valuefactory_XXXX(); i_server_factory* iserverfact = new_server_factory_interface (thisx, sessionobj, isession, funcptr_new_server); // PASSING func below i_sessionlistener* lxr = new_etch_listener ( uri, resx, iserverfact ); return lxr; // actually we may need to return the lxr's itransport* } void new_server (thisx, delivery_service) // from PerfHelper.newListener, the "server_factory" passed to new_etch_listener { // This is the "server_factory" passed to new_etch_listener, which is the java TransporFactory.getListener. // This function is called by the tcp server's accept handler, through the server factory interface. // it is currently virtual to the tcp server object, where it is called by etch_tcpsvr_acceptproc. // this function needs access to the uri, resources, and impl_factory function passed to new_listener, // and to the vf instantiated by new_listener. TODO FIGURE OUT HOW remote_XXX_client* client = new_remote_XXXX_client(dsvc, vf); // TODO XXXX_server* server = funcptr_new_XXXX_server(client); new_stub_XXXX_server(dsvc, server, pool, pool); } XXXX_server* new_XXXX_server (remote_XXXX_client* client) // our implementation of XXXX_server_factory { // our implementation of XXXX_server_factory (which is just funcptr(new_XXXX_server)) return new_impl_XXXX_server (client); } typedef struct impl_XXXX_server { remote_XXXX_client* client; i_objsession* iobjsession; _session_control(); _session_notify(); _session_query(); // objsession stuff i_XXXX_server* ixxxxserver; etch_int32 (*add) (etch_int32* x, etch_int32* y); // XXXX_server stuff // etc. more XXXX functions // these interfaces must be explicit as well as embedded }; XXXX_server* new_impl_XXXX_server (remote_XXXX_client* client) { impl_XXXX_server * newserver = new_object(...... newserver->client = client; newserver->add = myaddfunc; // etc. plug in all service virtuals return newserver->ixxxserver; } ------------------------------------------------------------------------------ notes on symmetry ------------------------------------------------------------------------------ =============================== SERVER SIDE =============================== main: ImplXxxxServer (XxxxServer) = serverFactory = callback to new ImplXxxxServer ( RemoteXxxxClient client ); Transport listener = helper.newListener(uri, callback); /* or "remote client", for symmetry */ helper: RemoteXxxxClient client = new RemoteXxxxClient (ds, vf); XxxxServer server = call back to new ImplXxxxServer (client ); new StubXxxxServer (ds, server, pool, pool); - - - - - - - - - - - - remote/local symmetry - - - - - - - - - - - - RemoteXxxxClient extends RemoteXxxx implements XxxxClient RemoteXxxx extends RemoteBase implements Xxxx RemoteBase (ds, vf ) XxxxClient extends Xxxx /* server-directed interfaces plus any client-directed */ ImplXxxxServer extends BaseXxxxServer RemoteXxxxClient client; BaseXxxxServer implements XxxxServer, ObjSession interface XxxxServer extends Xxxx =============================== CLIENT SIDE =============================== main: ImplXxxxClient = implFactory = callback to new ImplXxxxClient ( ); RemoteXxxxServer server = helper.newServer ( uri, callback ) // **** new_perf_remote_server() in c helper::newServer() // **** c binding new_remote_server() deliveryService ds = TransportFactory.getTransport(uri,resx); RemoteXxxxServer server = new RemoteXxxxServer (ds, vf); XxxxClient client = callback to newXxxxClient (server); new StubXxxxClient (ds, client, pool, pool) - - - - - - - - - - - - remote/local symmetry - - - - - - - - - - - - RemoteXxxxServer extends RemoteXxxx implements XxxxServer interface XxxxServer extends Xxxx /* also used by ImplXxxxServer */ ImplXxxxClient extends BaseXxxxClient RemoteXxxxServer server; BaseXxxxClient implements XxxxClient, ObjSession XxxxClient extends Xxxx /* also used by RemoteXxxxClient */ =============================== COMMONALITIES =============================== 1. XxxxClient by ImplXxxxClient, RemoteXxxxClient 2. XxxxServer by ImplXxxxServer, RemoteXxxxServer 3. RemoteXxxx by RemoteXxxxClient, RemoteXxxxServer 4. Xxxx by everything =============================== INHERITANCE =============================== IMPL_XXXX_CLIENT | RemoteXxxxServer* server; - BASE_XXXX_CLIENT |- XXXX_CLIENT: XXXX (interfaces) |- /* client-directed methods if any */ |- myfoo(); mybar(); etc. /* service XXXX interfaces */ |- mydata; - OBJSESSION | _sessionControl(), _sessionNotify(), _sessionQuery() IMPL_XXXX_SERVER | RemotePerfClient* client; | myfoo() { } etc; { /* service method implementations */ } | mydata; - BASE_XXXX_SERVER | myfoo(); mybar(); etc. /* service method empty stubs */ |- XXXX_SERVER: XXXX (interfaces) |- myfoo(); mybar(); etc. /* service method interfaces */ | mydata; - OBJSESSION | _sessionControl(), _sessionNotify(), _sessionQuery() =========================== C BINDING IMPLEMENTATION =========================== SERVER SIDE ----------- xxxx_remote_client.h i_perf_client* perf_client_base; perf_remote* perf_remote_base; xxxx_listener_main: i_sessionlistener* listener = new_etch_listener (callbacks); i_perf_server* new_server (void* thisx, etch_server_factory* p) perf_server_impl* newserver = new_perf_server_impl (remoteclient); new_remote_client () /* perf_remote_client.c */ rc->perf_remote_base = new_perf_remote (); /* perf_remote.c */ * establish ds, vf, start and stop methods. * establish transport, send, begincall, endcall methods * copy stubs from remote.iperf rc->perf_client_base = new_perf_client_base (); /* perf_client.c */ * instantiate perf service interface, copy default method impls * TODO don't re-implement service interface - pass existing iperf CLIENT SIDE ----------- xxxx_remote_server.h i_perf_server* perf_server_base; /* owned */ perf_remote* perf_remote_base; /* owned */ xxxx_client_main: new_perf_remote_server () rc->perf_remote_base = new_perf_remote (thisx, ids, vf); rc->perf_server_base = new_perf_server_base ();