1 #ifndef CROMP_SERVER_CLASS
2 #define CROMP_SERVER_CLASS
4 /*****************************************************************************\
6 * Name : cromp_server *
7 * Author : Chris Koeritz *
11 * Services request commands from CROMP clients. Derived objects supply *
12 * the specific services that a CROMP server implements by providing a set *
13 * of tentacles that handle the requests. These are added directly to the *
14 * server's octopus base class. *
16 *******************************************************************************
17 * Copyright (c) 2000-$now By Author. This program is free software; you can *
18 * redistribute it and/or modify it under the terms of the GNU General Public *
19 * License as published by the Free Software Foundation; either version 2 of *
20 * the License or (at your option) any later version. This is online at: *
21 * http://www.fsf.org/copyleft/gpl.html *
22 * Please send any updates to: fred@gruntose.com *
23 \*****************************************************************************/
25 #include "cromp_common.h"
27 #include <octopus/octopus.h>
28 #include <processes/ethread.h>
29 #include <timely/time_stamp.h>
30 #include <sockets/internet_address.h>
32 #include <tentacles/encryption_tentacle.h>
33 #include <tentacles/login_tentacle.h>
34 #include <processes/thread_cabinet.h>
39 class client_dropping_thread;
40 class connection_management_thread;
41 class cromp_client_list;
42 class cromp_client_record;
44 class cromp_transaction;
46 class cromp_server : public cromp_common
49 cromp_server(const sockets::internet_address &where,
50 int accepting_threads = DEFAULT_ACCEPTERS(),
51 bool instantaneous = true,
52 int max_per_entity = DEFAULT_MAX_ENTITY_QUEUE);
53 // creates a server that will open servers on the location "where". the
54 // number of connections that can be simultaneously handled is passed in
55 // "accepting_threads". if the "instantaneous" parameter is true, then
56 // any infotons that need to be handled will be passed to the octopus for
57 // immediate handling rather than being handled later on a thread.
59 virtual ~cromp_server();
61 DEFINE_CLASS_NAME("cromp_server");
63 int clients() const; // returns number of active clients.
65 static sockets::internet_address any_address(int port);
66 // returns an internet_address that should work on any interface that a
69 sockets::internet_address location() const;
70 // returns the network location where this server is supposed to reside,
71 // passed in the constructor.
73 bool instantaneous() const { return _instantaneous; }
74 // reports whether this server uses immediate handling or delayed handling.
76 bool enabled() const { return _enabled; }
77 // reports whether this server has been cranked up or not yet.
79 basis::outcome enable_servers(bool encrypt, cromp_security *security = NULL_POINTER);
80 // this must be called after construction to start up the object before it
81 // will accept client requests. if "encrypt" is on, then packets will
82 // be encrypted and no unencrypted packets will be allowed. if the
83 // "security" is passed as NULL_POINTER, then a default security manager is created
84 // and used. otherwise, the specified "security" object is used and will
85 // _not_ be destroyed when this object goes away.
87 void disable_servers();
88 // shuts down the server sockets that this object owns and disables the
89 // operation of this object overall. the next step is destruction.
91 bool find_entity(const octopi::octopus_entity &id, sockets::internet_address &found);
92 // given an "id" that is currently connected, find the network address
93 // where it originated and put it in "found". true is returned if the
94 // entity was located.
96 bool disconnect_entity(const octopi::octopus_entity &id);
97 //!< returns true if the "id" can be found and disconnected.
99 basis::outcome send_to_client(const octopi::octopus_request_id &id, octopi::infoton *data);
100 // blasts a command back to the client identified by the _entity member in
101 // the "id". this allows the controlling object of the server object to
102 // asynchronously inject data into the client's incoming stream. the
103 // client had better know what's going on or this will just lead to
104 // ignored data that eventually gets trashed.
106 basis::outcome get_from_client(const octopi::octopus_request_id &id, octopi::infoton * &data,
108 // attempts to locate a command with the request "id". if it is found
109 // within the timeout period, then "data" is set to the command. the
110 // "data" pointer must be deleted after use.
112 // basis::outcome get_any_from_client(const octopi::octopus_entity &ent, octopi::infoton * &data,
114 // attempts to grab any waiting package for the entity "ent".
116 bool get_sizes(const octopi::octopus_entity &id, int &items, int &bytes);
117 // promoted from our octopus' entity_data_bin in order to provide some
118 // accounting of what is stored for the "id".
120 basis::astring responses_text_form() const;
121 // returns a printout of the responses being held here.
123 static int DEFAULT_ACCEPTERS();
124 // the default number of listening threads.
126 // internal use only...
128 void look_for_clients(processes::ethread &requester);
129 // meant to be called by an arbitrary number of threads that can block
130 // on accepting a new client. control flow will not return from this
131 // method until the thread's cancel() method has been called.
133 void drop_dead_clients();
134 // called by a thread to manage dead or dying connections.
136 bool encrypting() const { return !!_encrypt_arm; }
137 // true if this object is encrypting transmissions.
139 octopi::infoton *wrap_infoton(octopi::infoton * &request, const octopi::octopus_entity &ent);
140 // when we're encrypting, this turns "request" into an encryption_wrapper.
141 // if NULL_POINTER is returned, then nothing needed to happen to the "request".
144 cromp_client_list *_clients; // the active set of clients.
145 processes::thread_cabinet *_accepters; // the list of accepting threads.
146 basis::mutex *_list_lock; // protects our lists.
147 timely::time_stamp *_next_droppage; // times cleanup for dead clients.
148 bool _instantaneous; // true if the octopus gets driven hard.
149 sockets::internet_address *_where; // where does the server live.
150 int _accepting_threads; // the number of accepters we keep going.
151 client_dropping_thread *_dropper; // cleans our lists.
152 bool _enabled; // records if this is running or not.
153 octopi::encryption_tentacle *_encrypt_arm; // the handler for encryption.
154 cromp_security *_default_security; // used in lieu of other provider.
155 octopi::login_tentacle *_security_arm; // handles security for the logins.
157 basis::outcome accept_one_client(bool wait);
158 // tries to get just one accepted client. if "wait" is true, then the
159 // routine will pause until the socket accept returns.