aboutsummaryrefslogtreecommitdiff
path: root/src/connection.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/connection.h')
-rw-r--r--src/connection.h387
1 files changed, 387 insertions, 0 deletions
diff --git a/src/connection.h b/src/connection.h
new file mode 100644
index 0000000..efb8630
--- /dev/null
+++ b/src/connection.h
@@ -0,0 +1,387 @@
1/**\file
2 * Contains the Connection class.
3 *@author Mike Buland
4 */
5
6#ifndef CONNECTION_H
7#define CONNECTION_H
8
9#include "multilog.h"
10#include "flexbuf.h"
11#include "protocol.h"
12
13/** Represents a single connection on a network. While these connections
14 * may be treated more or less just like files, occasionally problems arise
15 * when writing data at any time you feel like. Therefore you run all your
16 * data through a Connection, which buffers all data and makes sure no
17 * buffers are exceeded and nothing inappropriate for the recipient of the
18 * data is sent.
19 *@author Mike Buland
20 */
21class Connection
22{
23public:
24 /**
25 * Construct a blank and non-connected Connection. The created object is
26 * not yet connected to anything, and most of the functions except open are
27 * unusable.
28 */
29 Connection();
30
31 /**
32 * Destroy the connection, clean up all pending data requests and close the
33 * contained socket. This does not send out pending data, especially since
34 * such an operation could take considerable time, depending on the pending
35 * data and state of the receiving end.
36 */
37 ~Connection();
38
39 /**
40 * Open a connection to a remote server. This sets up this connection as
41 * a client instead of a server and does all of the work that needs to be
42 * done to actually open an INET_AF connection, which is a lot of work.
43 *@param sAddr The address to connect to. This can be in any format
44 * normally understood by your system to be an address, ip, domain name,
45 * etc.
46 *@param nPort The port number to connect to on the remote server.
47 *@returns True if the connection was successful and everything is setup,
48 * false if there were any of a dozen errors and the connection is not set.
49 *@todo Make this function add log entries to a standard MultiLog if
50 * something goes wrong.
51 */
52 bool open( const char *sAddr, int nPort );
53
54 /** Append the given data to the output. The data is presumed to be null
55 * terminated. To put binary data into the stream, use the other
56 * appendOutput function. This should be the only method used to
57 * communicate with the socket.
58 *@param lpOutput The data to add to the output queue.
59 *@param nSize How much data is in the lpOutput buffer. If this value
60 * is -1 then the program treats lpOutput as a null-terminated string.
61 *@returns True if everything is ok, false otherwise.
62 */
63 bool appendOutput( const char *lpOutput, int nSize=-1 );
64
65 /**
66 * Append the character to the output.
67 *@param lOutput The character to add to the output queue.
68 *@returns True if everything is ok, false otherwise.
69 */
70 bool appendOutput( const char lOutput );
71
72 /**
73 * Append the short to the output.
74 *@param lOutput The short to add to the output queue.
75 *@returns True if everything is ok, false otherwise.
76 */
77 bool appendOutput( const short lOutput );
78
79 /**
80 * Append the int to the output.
81 *@param lOutput The int to add to the output queue.
82 *@returns True if everything is ok, false otherwise.
83 */
84 bool appendOutput( const int lOutput );
85
86 /**
87 * Append the long to the output.
88 *@param lOutput The long to add to the output queue.
89 *@returns True if everything is ok, false otherwise.
90 */
91 bool appendOutput( const long lOutput );
92
93 /**
94 * Append the float to the output.
95 *@param lOutput The float to add to the output queue.
96 *@returns True if everything is ok, false otherwise.
97 */
98 bool appendOutput( const float lOutput );
99
100 /**
101 * Append the double to the output.
102 *@param lOutput The double to add to the output queue.
103 *@returns True if everything is ok, false otherwise.
104 */
105 bool appendOutput( const double lOutput );
106
107 /**
108 * Append the unsigned char to the output.
109 *@param lOutput The unsigned char to add to the output queue.
110 *@returns True if everything is ok, false otherwise.
111 */
112 bool appendOutput( const unsigned char lOutput );
113
114 /**
115 * Append the unsigned short to the output.
116 *@param lOutput The unsigned short to add to the output queue.
117 *@returns True if everything is ok, false otherwise.
118 */
119 bool appendOutput( const unsigned short lOutput );
120
121 /**
122 * Append the unsigned int to the output.
123 *@param lOutput The unsigned int to add to the output queue.
124 *@returns True if everything is ok, false otherwise.
125 */
126 bool appendOutput( const unsigned int lOutput );
127
128 /**
129 * Append the unsigned long to the output.
130 *@param lOutput The unsigned long to add to the output queue.
131 *@returns True if everything is ok, false otherwise.
132 */
133 bool appendOutput( const unsigned long lOutput );
134
135 /**
136 * Writes all input data in the buffer in a dual-view ascii and hex display
137 * to a file. There are a number of options that also help with debugging.
138 *@param lpPrefix Text to be added to the begining of every line written
139 * out. The default is a blank string.
140 *@param fh The file to write the data to in text mode. This is stdout by
141 * default, but could be any already open file handle.
142 *@param nBytesMax The maximum number of bytes to write to the output. The
143 * amount of data can be overwhelming sometimes, so you can limit it. The
144 * default value is -1, which is also unlimited.
145 */
146 void printInputDebug( const char *lpPrefix="", FILE *fh=stdout, int nBytesMax=-1 );
147
148 /**
149 * Writes all output data in the buffer in a dual-view ascii and hex display
150 * to a file. There are a number of options that also help with debugging.
151 *@param lpPrefix Text to be added to the begining of every line written
152 * out. The default is a blank string.
153 *@param fh The file to write the data to in text mode. This is stdout by
154 * default, but could be any already open file handle.
155 *@param nBytesMax The maximum number of bytes to write to the output. The
156 * amount of data can be overwhelming sometimes, so you can limit it. The
157 * default value is -1, which is also unlimited.
158 */
159 void printOutputDebug( const char *lpPrefix="", FILE *fh=stdout, int nBytesMax=-1 );
160
161 /**
162 * This is the low-level generic function that is called by both
163 * printInputDebug and printOutputDebug. It works effectively just like
164 * both of them, except that you can give it a raw pointer to the data to
165 * print out. This probably doesn't belong in this class, but this was
166 * where I was when I needed it.
167 *@param pData A pointer to the data to write. This is not treated as a
168 * null terminated string, so make sure that the nDataLen param is set
169 * properly.
170 *@param nDataLen The number of bytes that are in pData and that you want to
171 * see.
172 *@param lpName The name of the data, this is used in the header where it
173 * says "Displaying nnn bytes of <lpName>." A good example would be input
174 * or output.
175 *@param lpPrefix Text to put before every line output. This just makes it
176 * easier to tell large blocks apart in the output.
177 *@param fh The file handle to write all data to.
178 *@param nBytesMax The maximum number of bytes. This parameter is stupid.
179 * If it is set to -1, then nDataLen is used, otherwise the smaller value is
180 * used as the number of bytes to output.
181 *@todo Put this function somewhere more deserving.
182 *@todo Remove the nBytesMax param, we need that in the other functions,
183 * not this one!
184 */
185 void printDataDebug( const unsigned char *pData, long nDataLen, const char *lpName, const char *lpPrefix, FILE *fh, int nBytesMax );
186
187 /** Append the given data to the input. The data is presumed to be null
188 * terminated. To put binary data into the stream, use the other
189 * appendInput function. This is mainly used by internal routines.
190 *@param lpInput The data to add to the input queue.
191 *@param nSize How much data is in the lpInput buffer. If this value
192 * is -1 then the program treats lpOutput as a null-terminated string.
193 *@returns True if everything is ok, false otherwise.
194 */
195 bool appendInput( const char *lpInput, int nSize=-1 );
196
197 /** Searches through the current pending input for a certain character.
198 * This is useful for finding out where exactly the end of a line is, for
199 * example, to see if a command has been entered yet.
200 *@param cTarget The character to search for.
201 *@returns The position of the target relative to the begining of the input
202 * or -1 if the target wasn't found.
203 */
204 int scanInputFor( char cTarget );
205
206 /** Gets a pointer to the output buffer. This is mainly used by internal
207 * routines, and is cleared every click when data is sent out again.
208 *@returns A pointer to the buffer holding the pending output data.
209 */
210 const char *getOutput();
211
212 /** Gets a pointer to the start of the input buffer's active data
213 * section. Use this to gain access to the input you need to do
214 * your job.
215 *@returns A pointer to the data in the input buffer. Do not delete this.
216 */
217 const char *getInput();
218
219 /** Clears all pending output, this is mainly just used internally.
220 *@returns True if operation was a success, otherwise false.
221 */
222 bool clearOutput();
223
224 /** Clears all pending input, weather it's been used or not. Please
225 * refrain from calling this during normal operation, use usedInput
226 * instead, it's much safer.
227 *@returns True if the operation was a success, false otherwise.
228 */
229 bool clearInput();
230
231 /** Sets the socket that should be used internally.
232 *@param nNewSocket The new socket to work with.
233 */
234 void setSocket( int nNewSocket );
235
236 /** Gets the handle (number) of the working socket. This can be a
237 * dangerous function to call, please refrain from calling it directly
238 * if any alternative can be found.
239 *@returns The number of the working socket.
240 */
241 int getSocket();
242
243 /** Determines if the connection is still active.
244 *@returns True if the connection is active, false otherwise.
245 */
246 bool isActive();
247
248 /** Clears all buffers and sets up the connection to be reused.
249 * Does not actually close the socket, that's handled by the
250 * ConnectionManager
251 */
252 void close();
253
254 /** Opens a socket. Really just sets up the connection for use since
255 * the socket itself was created and opened by the ConnectionManager.
256 * This also calls setSocket so you don't have to.
257 *@param nNewSocket The socket to assosiate with.
258 */
259 bool open( int nNewSocket );
260
261 /**
262 * Reads all pending input from the connection. If this is called outside
263 * of the ConnectionManager it will usually block indefinately waiting for
264 * new data. The only way to change this behaviour is to modify the socket
265 * low-level when you connect it manually, or, preferably use the other
266 * readInput function to control blocking time.
267 *@returns True socket is still connected, otherwise false.
268 */
269 bool readInput();
270
271 /**
272 * Reads all pending input from the connection, blocking up to nSec
273 * seconds and nUSec micro-seconds for the data. This uses select to
274 * simulate blocking, but has the same effect as standard io blocking.
275 * If you don't want to block, just set both values to zero.
276 *@param nSec Max seconds to wait.
277 *@param nUSec Max micro-seconds to wait.
278 */
279 bool readInput( int nSec, int nUSec );
280
281 /** Writes all data that is pending to the socket.
282 *@returns True if all data was written succesfully, false otherwise.
283 */
284 bool writeOutput();
285
286 /** Determines if the connection has output waiting to go out.
287 *@returns true if there is pending output, otherwise false.
288 */
289 bool hasOutput();
290
291 /** Sets internal flags so that this connection will be deleted next
292 * time through the ConnectionManager.
293 */
294 void disconnect();
295
296 /** Determines if this connection is ready to be disconnected or not.
297 *@returns True if it is time to disconnect, false if it isn't.
298 */
299 bool needDisconnect();
300
301 /** Tells the caller if there is pending input waiting to be processed.
302 *@returns True if there is pending input that has not been used, returns
303 * false if there isn't.
304 */
305 bool hasInput();
306
307 /** Removes bytes from the begining of the input queue. Use this after
308 * getting the input and processing as much as you need to.
309 *@param nAmount The number of bytes used.
310 *@returns true if the update was successful, otherwise false.
311 */
312 bool usedInput( int nAmount );
313
314 /** Sets the protocol to be used by this connection. All data in and out
315 * passes through the protocol object, which may process that data to
316 * filter out and process any special messages that may have been
317 * included. Everything that isn't processed can be accessed in the
318 * standard method.
319 *@param pNewProtocol A pointer to a protocol object that you want to
320 * use.
321 */
322 void setProtocol( class Protocol *pNewProtocol );
323
324 /** Gets the number of bytes that are waiting in the input queue, the data
325 * that has yet to be processed.
326 *@returns The number of bytes in the input queue.
327 */
328 int getInputAmnt();
329
330 /** Gets the number of bytes that are waiting in the output queue, the data
331 * that has yet to be sent to the connected socket.
332 *@returns The number of bytes in the input queue.
333 */
334 int getOutputAmnt();
335
336 /** Gets a pointer to the protocol that is attatched to this connection
337 * object. This is useful to set modes, and send special commands in
338 * addition to the standard raw data reads and writes that are normally
339 * permitted. In fact, in everything besides a raw telnet protocol all
340 * data should be sent through the protocol and not the connection object.
341 *@returns A pointer to the Protocol assosiated with this connection.
342 */
343 class Protocol *getProtocol();
344
345private:
346 /**
347 * A buffer to keep data read from the socket in. This is filled in by
348 * the function readInput, which is automatically called by the
349 * ConnectionManager whenever new data is ready.
350 */
351 FlexBuf xInputBuf;
352
353 /**
354 * A buffer to keep data that should be sent to the socket. This is filled
355 * in by using the AppendOutput functions and is sent to the socket using
356 * the writeOutput function, which is automatically called every cycle by
357 * the ConnectionManager when there is pending data.
358 */
359 FlexBuf xOutputBuf;
360
361 /**
362 * The socket that the user is connected to. This is not the same as the
363 * socket number of the listening socket, this is the unique socket on the
364 * system that the data is coming to.
365 */
366 int nSocket;
367
368 /**
369 * True=active connection, False=connection lost
370 */
371 bool bActive;
372
373 /**
374 * True=disconnect next cycle (after data is transmitted), Flse=keep going.
375 */
376 bool bDisconnectMe;
377
378 /**
379 * A pointer to a protocol handler that can automatically process the data
380 * in the buffers. This is optional if you use the connections on your own
381 * but reccomended if you use this with the rest of the ConnectionManager
382 * system.
383 */
384 class Protocol *pProtocol;
385};
386
387#endif