aboutsummaryrefslogtreecommitdiff
path: root/src/old
diff options
context:
space:
mode:
Diffstat (limited to 'src/old')
-rw-r--r--src/old/cgi.cpp644
-rw-r--r--src/old/cgi.h196
-rw-r--r--src/old/configmanagerbase.cpp63
-rw-r--r--src/old/configmanagerbase.h24
-rw-r--r--src/old/confpair.cpp2
-rw-r--r--src/old/confpair.h81
-rw-r--r--src/old/confpairbase.cpp17
-rw-r--r--src/old/confpairbase.h24
-rw-r--r--src/old/conftree.cpp9
-rw-r--r--src/old/conftree.h19
-rw-r--r--src/old/connection.cpp564
-rw-r--r--src/old/connection.h411
-rw-r--r--src/old/connectionmanager.cpp397
-rw-r--r--src/old/connectionmanager.h169
-rw-r--r--src/old/connectionmonitor.cpp10
-rw-r--r--src/old/connectionmonitor.h47
-rw-r--r--src/old/flexbuf.cpp229
-rw-r--r--src/old/flexbuf.h162
-rw-r--r--src/old/formula.cpp262
-rw-r--r--src/old/formula.h77
-rw-r--r--src/old/http.cpp377
-rw-r--r--src/old/http.h273
-rw-r--r--src/old/httpget.cpp263
-rw-r--r--src/old/httpget.h44
-rw-r--r--src/old/linkedlist.cpp210
-rw-r--r--src/old/linkedlist.h87
-rw-r--r--src/old/linkmessenger.cpp41
-rw-r--r--src/old/linkmessenger.h32
-rw-r--r--src/old/list.cpp10
-rw-r--r--src/old/list.h101
-rw-r--r--src/old/md5.cpp190
-rw-r--r--src/old/md5.h81
-rw-r--r--src/old/multilog.cpp102
-rw-r--r--src/old/multilog.h130
-rw-r--r--src/old/multilogchannel.cpp13
-rw-r--r--src/old/multilogchannel.h46
-rw-r--r--src/old/multilogtext.cpp188
-rw-r--r--src/old/multilogtext.h70
-rw-r--r--src/old/ordhash.cpp1
-rw-r--r--src/old/ordhash.h104
-rw-r--r--src/old/pqueue.cpp33
-rw-r--r--src/old/pqueue.h48
-rw-r--r--src/old/protocol.cpp20
-rw-r--r--src/old/protocol.h62
-rw-r--r--src/old/protocoltelnet.cpp316
-rw-r--r--src/old/protocoltelnet.h77
-rw-r--r--src/old/queue.cpp26
-rw-r--r--src/old/queue.h45
-rw-r--r--src/old/ringlist.cpp106
-rw-r--r--src/old/ringlist.h112
-rw-r--r--src/old/sbuffer.cpp67
-rw-r--r--src/old/sbuffer.h40
-rw-r--r--src/old/serializerbinary.cpp63
-rw-r--r--src/old/serializerbinary.h24
-rw-r--r--src/old/serializerbzip2.cpp88
-rw-r--r--src/old/serializerbzip2.h27
-rw-r--r--src/old/serializerconnection.cpp15
-rw-r--r--src/old/serializerconnection.h24
-rw-r--r--src/old/serializertext.cpp170
-rw-r--r--src/old/serializertext.h49
-rw-r--r--src/old/sha1.cpp161
-rw-r--r--src/old/sha1.h42
-rw-r--r--src/old/stack.cpp33
-rw-r--r--src/old/stack.h50
-rw-r--r--src/old/staticstring.cpp282
-rw-r--r--src/old/staticstring.h63
-rw-r--r--src/old/stringrep.cpp19
-rw-r--r--src/old/stringrep.h17
-rw-r--r--src/old/tests/clistress.cpp20
-rw-r--r--src/old/tests/confpair.cpp19
-rw-r--r--src/old/tests/connect.cpp38
-rw-r--r--src/old/tests/exception.cpp16
-rw-r--r--src/old/tests/formula.cpp13
-rw-r--r--src/old/tests/hash.cpp116
-rw-r--r--src/old/tests/hashtest.cpp107
-rw-r--r--src/old/tests/hashtest2.cpp15
-rw-r--r--src/old/tests/httpsrv/httpconnectionmonitor.cpp88
-rw-r--r--src/old/tests/httpsrv/httpconnectionmonitor.h16
-rw-r--r--src/old/tests/httpsrv/main.cpp22
-rw-r--r--src/old/tests/log.cpp29
-rw-r--r--src/old/tests/md5test.cpp19
-rw-r--r--src/old/tests/ordhash.cpp48
-rw-r--r--src/old/tests/param.cpp46
-rw-r--r--src/old/tests/param.h21
-rw-r--r--src/old/tests/plugin/main.cpp14
-rw-r--r--src/old/tests/plugin/plugin.cpp10
-rw-r--r--src/old/tests/plugin/plugin.h14
-rw-r--r--src/old/tests/qsort.cpp228
-rw-r--r--src/old/tests/sbuffer.cpp27
-rw-r--r--src/old/tests/serialize.cpp30
-rw-r--r--src/old/tests/serializetext.cpp28
-rw-r--r--src/old/tests/sha1.cpp44
-rw-r--r--src/old/tests/sptr.cpp55
-rw-r--r--src/old/tests/srvstress.cpp91
-rw-r--r--src/old/tests/strhash.cpp12
-rw-r--r--src/old/tests/teltest/main.cpp21
-rw-r--r--src/old/tests/teltest/telnetmonitor.cpp54
-rw-r--r--src/old/tests/teltest/telnetmonitor.h26
-rw-r--r--src/old/tests/xmlreadtest.cpp29
-rw-r--r--src/old/tests/xmlrepltest.cpp31
-rw-r--r--src/old/tests/xmlwritetest.cpp48
-rw-r--r--src/old/tokenstring.cpp163
-rw-r--r--src/old/tokenstring.h114
-rw-r--r--src/old/tqsort.h207
-rw-r--r--src/old/unit/hashtable/hashtable.cpp107
-rw-r--r--src/old/unit/xml/xml.cpp59
-rw-r--r--src/old/xmldocument.cpp145
-rw-r--r--src/old/xmldocument.h165
-rw-r--r--src/old/xmlfilereader.cpp58
-rw-r--r--src/old/xmlfilereader.h47
-rw-r--r--src/old/xmlfilewriter.cpp28
-rw-r--r--src/old/xmlfilewriter.h45
-rw-r--r--src/old/xmlnode.cpp403
-rw-r--r--src/old/xmlnode.h207
-rw-r--r--src/old/xmlreader.cpp604
-rw-r--r--src/old/xmlreader.h144
-rw-r--r--src/old/xmlstringreader.cpp38
-rw-r--r--src/old/xmlstringreader.h49
-rw-r--r--src/old/xmlstringwriter.cpp23
-rw-r--r--src/old/xmlstringwriter.h50
-rw-r--r--src/old/xmlwriter.cpp167
-rw-r--r--src/old/xmlwriter.h96
122 files changed, 0 insertions, 12163 deletions
diff --git a/src/old/cgi.cpp b/src/old/cgi.cpp
deleted file mode 100644
index 1fecbbe..0000000
--- a/src/old/cgi.cpp
+++ /dev/null
@@ -1,644 +0,0 @@
1#include <string.h>
2#include <stdlib.h>
3#include <stdio.h>
4#include <stdarg.h>
5#include <sys/stat.h>
6
7#include "cgi.h"
8
9Cgi::Cgi( const char *strSource ) :
10 aContent( new HashFunctionString(), 151, true )
11{
12 int length, j, k, mode = 0, slen = 0;
13 char hexbuf[3] = { 0, 0, 0 };
14 char *buf, chr;
15 Item *cur = NULL;
16 int nCur = 0;
17
18 if( strSource != NULL )
19 {
20 loadContent( strSource );
21 }
22
23 if( ( getenv( "CONTENT_LENGTH" ) ) )
24 {
25 if( !strcmp
26 ( getenv( "CONTENT_TYPE" ),
27 "application/x-www-form-urlencoded" ) )
28 {
29 length = atoi( getenv( "CONTENT_LENGTH" ) );
30 buf = new char[length + 1];
31 fread( buf, 1, length, stdin );
32 cur = new Item( );
33 aVars.append( cur );
34 cur->type = VAR_STDINPUT;
35 for( j = 0; j < length; j++ )
36 {
37 switch ( buf[j] )
38 {
39 case '=':
40 cur->name = new char[slen + 1];
41 slen = 0;
42 break;
43
44 case '&':
45 cur->value = new char[slen + 1];
46 cur->len = slen;
47 slen = 0;
48 cur = new Item( );
49 aVars.append( cur );
50 cur->type = VAR_STDINPUT;
51 break;
52
53 default:
54 switch ( buf[j] )
55 {
56 case '%': /* per-cents mean a hex-code for an ASCII char */
57 j += 2;
58 slen++;
59 break;
60
61 default: /* Nothing special, move along, folks... */
62 slen++;
63 break;
64 }
65 break;
66 }
67 }
68 cur->value = new char[slen + 1];
69 cur->len = slen;
70 slen = 0;
71 mode = 0;
72 cur = ( Item * ) aVars.getAt( 0 );
73 k = 0;
74 nCur = 0;
75 for( j = 0; j < length; j++ )
76 {
77 switch ( buf[j] )
78 {
79 case '=':
80 mode = 1;
81 k = 0;
82 break;
83
84 case '&':
85 mode = 0;
86 k = 0;
87 nCur++;
88 cur = ( Item * ) aVars.getAt( nCur );
89 break;
90
91 default:
92 switch ( buf[j] )
93 {
94 case '%': /* per-cents mean a hex-code for an ASCII char */
95 hexbuf[0] = buf[++j];
96 hexbuf[1] = buf[++j];
97 chr = ( char ) ( strtol( hexbuf, NULL, 16 ) );
98 break;
99
100 case '+': /* Pluses mean spaces, odd, I know... */
101 chr = ' ';
102 break;
103
104 default: /* Nothing special, move along, folks... */
105 chr = buf[j];
106 break;
107 }
108 if( mode == 0 )
109 {
110 cur->name[k] = chr;
111 cur->name[++k] = '\0';
112 }
113 else
114 {
115 cur->value[k] = chr;
116 cur->value[++k] = '\0';
117 }
118 break;
119 }
120 }
121 delete buf;
122 }
123 else if( !strncmp
124 ( getenv( "CONTENT_TYPE" ), "multipart/form-data;", 20 ) )
125 {
126 char *boundary, *oname;
127 int blen, j, k, olen;
128
129 length = atoi( getenv( "CONTENT_LENGTH" ) );
130 buf = new char[length + 1];
131 fread( buf, 1, length, stdin );
132 for( blen = 0; buf[blen + 1] != '\n'; blen++ );
133 boundary = new char[blen + 1];
134 memcpy( boundary, buf, blen );
135 boundary[blen] = '\0';
136 j = blen + 2;
137 for( ;; )
138 {
139 cur = new Item( );
140 aVars.append( cur );
141 cur->type = VAR_STDINPUT;
142 if( !strncmp
143 ( buf + j, "Content-Disposition: form-data; name=\"",
144 38 ) )
145 {
146 j += 38;
147 for( k = 0; buf[j + k] != '\"'; k++ );
148 oname = cur->name = new char[k + 1];
149 memcpy( cur->name, buf + j, k );
150 olen = k;
151 cur->name[k] = '\0';
152 j += k + 1;
153 if( !strncmp( buf + j, "; filename=\"", 12 ) ) /* Must be a file */
154 {
155 /* Acquire file name */
156 j += 12;
157 for( k = 0; buf[j + k] != '\"'; k++ );
158 cur->value = new char[k + 1];
159 memcpy( cur->value, buf + j, k );
160 cur->value[k] = '\0';
161 cur->len = k;
162 j += k + 3;
163
164 /* Acquire content type */
165 if( !strncmp( "Content-Type: ", buf + j, 14 ) )
166 {
167 j += 14;
168 cur = new Item( );
169 aVars.append( cur );
170 cur->type = VAR_STDINPUT;
171 cur->name = new char[olen + 1];
172 memcpy( cur->name, oname, olen + 1 );
173 for( k = 0; buf[j + k + 1] != '\n'; k++ );
174 cur->value = new char[k + 1];
175 memcpy( cur->value, buf + j, k );
176 cur->value[k] = '\0';
177 cur->len = k;
178 j += k;
179 }
180 else
181 {
182 cur = new Item( );
183 aVars.append( cur );
184 cur->type = VAR_STDINPUT;
185 cur->name = new char[olen + 1];
186 memcpy( cur->name, oname, olen + 1 );
187 cur->value = new char[1];
188 cur->value[0] = '\0';
189 cur->len = 0;
190 }
191 j += 4;
192
193 /* Acquire content */
194 cur = new Item( );
195 aVars.append( cur );
196 cur->type = VAR_STDINPUT;
197 cur->name = new char[olen + 1];
198 memcpy( cur->name, oname, olen + 1 );
199 if( !strncmp( buf + j + k, boundary, blen ) )
200 {
201 cur->value = new char[1];
202 cur->value[0] = '\0';
203 j += blen + 4;
204 }
205 else if( !strncmp( buf + j + k + 1, boundary, blen ) )
206 {
207 cur->value = new char[1];
208 cur->value[0] = '\0';
209 j += blen + 5;
210 }
211 else
212 {
213 for( k = 0;
214 strncmp( buf + j + k + 2, boundary, blen );
215 k++ );
216 cur->value = new char[k + 1];
217 memcpy( cur->value, buf + j, k );
218 cur->value[k] = '\0';
219 cur->len = k;
220 j += k + blen + 4;
221 }
222 }
223 else
224 {
225 j += 4;
226 for( k = 0;
227 strncmp( buf + j + k + 2, boundary, blen );
228 k++ );
229 cur->value = new char[k + 1];
230 memcpy( cur->value, buf + j, k );
231 cur->value[k] = '\0';
232 cur->len = k;
233 j += k + blen + 4;
234 }
235 if( buf[j + 1] == '\n' )
236 j += 2;
237 if( j >= length )
238 break;
239 }
240 else
241 {
242 cur->name = ( char * ) "ERROR";
243 cur->value = ( char * ) "Error here";
244 }
245 }
246 }
247 delete buf;
248 }
249
250 if( ( buf = getenv( "HTTP_COOKIE" ) ) )
251 {
252 int lbase = aVars.getSize( );
253 length = strlen( buf );
254 cur = new Item( );
255 aVars.append( cur );
256 cur->type = VAR_COOKIE;
257 for( j = 0; j < length; j++ )
258 {
259 switch ( buf[j] )
260 {
261 case '=':
262 cur->name = new char[slen + 1];
263 slen = 0;
264 break;
265
266 case ';':
267 cur->value = new char[slen + 1];
268 cur->len = slen;
269 slen = 0;
270 cur = new Item( );
271 aVars.append( cur );
272 cur->type = VAR_COOKIE;
273 break;
274
275 default:
276 switch ( buf[j] )
277 {
278 case '%': /* per-cents mean a hex-code for an ASCII char */
279 j += 2;
280 slen++;
281 break;
282
283 default: /* Nothing special, move along, folks... */
284 slen++;
285 break;
286 }
287 break;
288 }
289 }
290 cur->value = new char[slen + 1];
291 cur->len = slen;
292 slen = 0;
293 cur = ( Item * ) aVars.getAt( lbase );
294 mode = 0;
295 k = 0;
296 nCur = lbase;
297 for( j = 0; j < length; j++ )
298 {
299 switch ( buf[j] )
300 {
301 case '=':
302 mode = 1;
303 k = 0;
304 break;
305
306 case ';':
307 mode = 0;
308 k = 0;
309 nCur++;
310 cur = ( Item * ) aVars.getAt( nCur );
311 break;
312
313 default:
314 switch ( buf[j] )
315 {
316 case '%': /* per-cents mean a hex-code for an ASCII char */
317 hexbuf[0] = buf[++j];
318 hexbuf[1] = buf[++j];
319 chr = ( char ) ( strtol( hexbuf, NULL, 16 ) );
320 break;
321
322 case '+': /* Pluses mean spaces, odd, I know... */
323 chr = ' ';
324 break;
325
326 case ' ':
327 continue;
328 break;
329
330 default: /* Nothing special, move along, folks... */
331 chr = buf[j];
332 break;
333 }
334 if( mode == 0 )
335 {
336 cur->name[k] = chr;
337 cur->name[++k] = '\0';
338 }
339 else
340 {
341 cur->value[k] = chr;
342 cur->value[++k] = '\0';
343 }
344 break;
345 }
346 }
347 }
348
349 if( ( buf = getenv( "QUERY_STRING" ) ) )
350 {
351 if( strlen( buf ) > 0 )
352 {
353 int lbase = aVars.getSize( );
354 length = strlen( buf );
355 cur = new Item( );
356 aVars.append( cur );
357 cur->type = VAR_CMDLINE;
358 for( j = 0; j < length; j++ )
359 {
360 switch ( buf[j] )
361 {
362 case '=':
363 cur->name = new char[slen + 1];
364 slen = 0;
365 break;
366
367 case '&':
368 cur->value = new char[slen + 1];
369 cur->len = slen;
370 slen = 0;
371 cur = new Item( );
372 aVars.append( cur );
373 cur->type = VAR_CMDLINE;
374 break;
375
376 default:
377 switch ( buf[j] )
378 {
379 case '%': /* per-cents mean a hex-code for an ASCII char */
380 j += 2;
381 slen++;
382 break;
383
384 default: /* Nothing special, move along, folks... */
385 slen++;
386 break;
387 }
388 break;
389 }
390 }
391 cur->value = new char[slen + 1];
392 cur->len = slen;
393 slen = 0;
394 cur = ( Item * ) aVars.getAt( lbase );
395 nCur = lbase;
396 mode = 0;
397 k = 0;
398 for( j = 0; j < length; j++ )
399 {
400 switch ( buf[j] )
401 {
402 case '=':
403 mode = 1;
404 k = 0;
405 break;
406
407 case '&':
408 mode = 0;
409 k = 0;
410 nCur++;
411 cur = ( Item * ) aVars.getAt( nCur );
412 break;
413
414 default:
415 switch ( buf[j] )
416 {
417 case '%': /* per-cents mean a hex-code for an ASCII char */
418 hexbuf[0] = buf[++j];
419 hexbuf[1] = buf[++j];
420 chr = ( char ) ( strtol( hexbuf, NULL, 16 ) );
421 break;
422
423 case '+': /* Pluses mean spaces, odd, I know... */
424 chr = ' ';
425 break;
426
427 default: /* Nothing special, move along, folks... */
428 chr = buf[j];
429 break;
430 }
431 if( mode == 0 )
432 {
433 cur->name[k] = chr;
434 cur->name[++k] = '\0';
435 }
436 else
437 {
438 cur->value[k] = chr;
439 cur->value[++k] = '\0';
440 }
441 break;
442 }
443 }
444 }
445 }
446}
447
448Cgi::~Cgi( )
449{
450}
451
452char *Cgi::getVarValue( const char *name, int skip, unsigned char type )
453{
454 for( int j = 0; j < aVars.getSize( ); j++ )
455 {
456 Item *cur = ( Item * ) aVars.getAt( j );
457 if( !strcmp( cur->name, name ) )
458 {
459 if( ( cur->type & type ) )
460 {
461 if( skip <= 0 )
462 {
463 return cur->value;
464 }
465 else
466 {
467 skip--;
468 }
469 }
470 }
471 }
472 return NULL;
473}
474
475int Cgi::getVarLength( const char *name, int skip, unsigned char type )
476{
477 for( int j = 0; j < aVars.getSize( ); j++ )
478 {
479 Item *cur = ( Item * ) aVars.getAt( j );
480 if( !strcmp( cur->name, name ) )
481 {
482 if( ( cur->type & type ) )
483 {
484 if( skip <= 0 )
485 {
486 return cur->len;
487 }
488 else
489 {
490 skip--;
491 }
492 }
493 }
494 }
495 return -1;
496}
497
498void Cgi::writeDebugInfo()
499{
500 printf( "<pre>\n" );
501 printf( "0x%02X - stdInput | 0x%02X - cookie | 0x%02X - cmdLine\n\n",
502 VAR_STDINPUT, VAR_COOKIE, VAR_CMDLINE );
503 for( int j = 0; j < aVars.getSize( ); j++ )
504 {
505 Item *item = ( Item * ) aVars.getAt( j );
506 printf("[%s] = \"%s\" [0x%02X]\n", item->name,
507 item->value, item->type );
508 }
509 printf( "</pre>\n" );
510}
511
512void Cgi::writeContentHeader( int type )
513{
514 switch( type )
515 {
516 case headerHTML:
517 printf("Content-type: text/html\n\n");
518 break;
519 }
520}
521
522void Cgi::writeContent( const char *name, ...)
523{
524 char *templ = (char *)aContent.get(name);
525
526 if( templ )
527 {
528 va_list ap;
529
530 va_start (ap, name);
531 vprintf (templ, ap);
532 va_end (ap);
533 }
534 else
535 {
536 printf("Error finding content labeled \"%s\"\n", name );
537 }
538}
539
540void Cgi::loadContent( const char *strSource )
541{
542 FILE *fh = NULL;
543 if( strSource == NULL )
544 {
545 extern char *program_invocation_short_name;
546 char *tmpName = new char[strlen(program_invocation_short_name)+10];
547 memset( tmpName, 0, strlen(program_invocation_short_name)+10 );
548 strcpy( tmpName, program_invocation_short_name );
549 strcat( tmpName, ".content" );
550 fh = fopen( tmpName, "rt" );
551 delete tmpName;
552 }
553 else
554 {
555 fh = fopen( strSource, "rt" );
556 }
557
558 if( fh == NULL ) return;
559
560 struct stat xStats;
561
562 fstat( fileno( fh ), &xStats );
563
564 char *bigBuf = new char[xStats.st_size+1];
565 memset( bigBuf, 0, xStats.st_size+1 );
566 fread( bigBuf, 1, xStats.st_size, fh );
567 fclose( fh );
568
569 // Now we can actually load stuff from the file, first we need to make us up a format...
570 int lSize=0;
571 struct Content
572 {
573 char *name;
574 char *value;
575 } xCont;
576 int j = 0;
577 while( j < xStats.st_size )
578 {
579 // We're looking for a content-block init statement
580 for( ; j < xStats.st_size; j++ )
581 {
582 if( bigBuf[j] == '#' )
583 {
584 if( bigBuf[j+1] == '{' )
585 {
586 break;
587 }
588 }
589 }
590 j=j+2;
591 if( j >= xStats.st_size ) break;
592 for( ; bigBuf[j] == ' ' || bigBuf[j] == '\t'; j++ );
593 for( lSize = 0; lSize+j < xStats.st_size && bigBuf[lSize+j] != '\n' && bigBuf[lSize+j] != '\r'; lSize++ );
594 xCont.name = new char[lSize+1];
595 memset( xCont.name, 0, lSize+1 );
596 memcpy( xCont.name, &bigBuf[j], lSize );
597 j += lSize+1;
598
599 for( lSize = 0; lSize+j < xStats.st_size; lSize++ )
600 {
601 if( bigBuf[lSize+j] == '#' )
602 {
603 if( bigBuf[lSize+j+1] == '}' )
604 {
605 break;
606 }
607 }
608 }
609 xCont.value = new char[lSize+1];
610 memset( xCont.value, 0, lSize+1 );
611 memcpy( xCont.value, &bigBuf[j], lSize );
612
613 aContent.insert( xCont.name, xCont.value );
614
615 j += lSize + 2;
616 }
617}
618
619void Cgi::writeCookie( char const *name, char const *value, char const *expires, char const *path, char const *domain, bool secure )
620{
621 printf("Set-Cookie: %s=%s", name, value );
622
623 if( expires != NULL )
624 {
625 printf("; expires=%s", expires );
626 }
627
628 if( path != NULL )
629 {
630 printf("; path=%s", path );
631 }
632
633 if( domain != NULL )
634 {
635 printf("; domain=%s", domain );
636 }
637
638 if( secure )
639 {
640 printf("; secure");
641 }
642
643 printf("\n");
644}
diff --git a/src/old/cgi.h b/src/old/cgi.h
deleted file mode 100644
index 01142b5..0000000
--- a/src/old/cgi.h
+++ /dev/null
@@ -1,196 +0,0 @@
1/**\file cgi.h
2 * Describes extra params needed to use the Cgi class as well as the class
3 * itself.
4 *@author Mike Buland
5 */
6
7#include "linkedlist.h"
8#include "hashtable.h"
9#include "hashfunctionstring.h"
10
11#define VAR_STDINPUT 0x01 /**< Variable came from stdinput, web form */
12#define VAR_COOKIE 0x02 /**< Variable came from a cookie */
13#define VAR_CMDLINE 0x04 /**< Variable came from commandline / uri */
14#define VAR_ANY 0xFF /**< Mask including all other types */
15
16/**
17 * Cgi header processor originally designed for apache cgi programs. When used
18 * from apache with what I beleive are some sort of standard set of command
19 * line parameters and environment variables. This always worked for all of my
20 * purposes. This class will automatically extract all data from the system
21 * that you need and places it into tables and things for easy access.
22 * There are three types of input that data can come from, StandardInput,
23 * CommandLine, and Cookies. StandardInput is when you get formdata in
24 * multi-part forms, Cookies should usually be cookies that you set, and
25 * command line is everything after the question mark in the URL.
26 * This also contains some simple helpers for putting templated data into the
27 * HTTP data feed.
28 *@author Mike Buland
29 */
30class Cgi
31{
32public:
33 /**
34 * Create a complete CGI object, this object will automatically read data
35 * from all available sources and be ready for use on the very next line!
36 * If strSource is filled in it will also automatically read in a content
37 * file, which is a simple file format containing named blocks of reusable
38 * templates.
39 *@param strSource Set to a filename in order to load up a content file.
40 */
41 Cgi( const char *strSource = NULL );
42
43 /**
44 * Destroy the cgi object.
45 */
46 virtual ~Cgi( );
47
48 /**
49 * Get's the value for a variable as a character string. The name is the
50 * name that was given on the URL or in the form or cookie. Skip can be
51 * set to any value above zero to retreive subsequent variables with the
52 * same name. The most obvious use of this is when dealing with file
53 * uploads, each file upload sends you three variables with the same name
54 * and different content. Finally the variable type determines where you
55 * will accept this variable from. This is generally a bit of a security
56 * thing, if you store login info in a cookie and don't want people getting
57 * in by faking the appropriate URL.
58 *@param name The name of the variable you wish to retreive.
59 *@param skip THe number of variables with the given name to skip before
60 * returning something meaningful. The only way to determine how many
61 * variables with the same name there are is to skip until you get a NULL
62 * value returned.
63 *@param type Can be set to any combination of VAR_STDINPUT, VAR_COOKIE,
64 * VAR_CMDLINE, or just VAR_ANY. This takes bitflags, so you can or the
65 * values together. If a variable is found but came from the wrong source
66 * it won't match any other criteria and will be treated as though it
67 * doesn't exist.
68 *@returns A null-terminated string representing the value of the requested
69 * variable, or NULL if the variable did not exist. If a variable does
70 * exist but has no value the string returned will start with a NULL char,
71 * but be a valid string.
72 */
73 char *getVarValue( const char *name, int skip=0, unsigned char type=VAR_ANY );
74
75 /**
76 * This functions identically in every way to getVarValue, except that
77 * instead of returning a pointer to the variable's value, it returns the
78 * length of the variable's value string. The params are the same and so
79 * a call to both functions with the same params should yeild a value and
80 * a corresponding length.
81 *@param name The name of the variable you wish to retreive.
82 *@param skip THe number of variables with the given name to skip before
83 * returning something meaningful. The only way to determine how many
84 * variables with the same name there are is to skip until you get a NULL
85 * value returned.
86 *@param type Can be set to any combination of VAR_STDINPUT, VAR_COOKIE,
87 * VAR_CMDLINE, or just VAR_ANY. This takes bitflags, so you can or the
88 * values together. If a variable is found but came from the wrong source
89 * it won't match any other criteria and will be treated as though it
90 * doesn't exist.
91 *@returns The length of the value-string of the requested variable. If
92 * the requested variable is not found, -1 is returned.
93 */
94 int getVarLength( const char *name, int skip=0, unsigned char type=VAR_ANY );
95
96 /**
97 * A handy little function that writes a load of debug info related to
98 * parsing CGI params to the standard output in html. This is generally
99 * best used at the end of a page.
100 */
101 void writeDebugInfo();
102
103 /**
104 * Write a content header to the standard output. This should also be the
105 * first thing that you do (except for writing cookies) after initializing
106 * the Cgi class. You can select a type of header or content from the
107 * header enum, and a properly formatted header will show up on the
108 * standard output.
109 *@param type Any value from the header enum in this class. The default is
110 * to write an html header, probably the most common as well.
111 */
112 void writeContentHeader( int type=headerHTML );
113
114 /**
115 * Write content to the stnadard output. The content variable should have
116 * been loaded during construction of the Cgi object or with the
117 * loadContent function. The content variable should be formatted just like
118 * a printf string, so that anything you want to put into it will have a %
119 * symbol replacement code, like %s, %d, etc. Since this actually uses a
120 * type of printf function everything from those docs work here.
121 *@param name The name of the content variable to format and write to
122 * stnadard output.
123 *@param ... As many params as you want to include, ala printf.
124 */
125 void writeContent( const char *name, ...);
126
127 /**
128 * Load a content file. I don't want to describe the format here, you can
129 * just read the code or find an example for now. Sorry.
130 *@param strSource The name of the file to open and read in to get the
131 * content loaded.
132 */
133 void loadContent( const char *strSource = NULL );
134
135 /**
136 * Write a cookie-set header to the output stream. This should be done
137 * before any other content-headers are written. The specifics of this
138 * function are very simple, since I rely on the user's understanding of
139 * how standard HTTP/1.1 or HTTP/1.0 cookie syntax works. If you don't
140 * care then just use the name and value and the defaults should keep you
141 * in good stead for a long time.
142 *@param name The name of the cookie variable to set.
143 *@param value The value to set to that variable.
144 *@param expires The formatted string value for the date and time this
145 * cookie should expire. A NULL here will put a "until the browser closes"
146 * tag in.
147 *@param path The path (URL) that this cookie belongs to. If you run a lot
148 * of hosted servers or sub-sites that may have some shared URL bits then
149 * you may want to set this. The cookie should only be sent to URL's that
150 * match this as their first part.
151 *@param domain The domain that is allowed to read this, if not set, it's
152 * the domain the web browser contacted when they got the cookie.
153 *@param secure I'm not sure, I think it's something to tell if the cookie
154 * is safe to keep because any potentially valuable data is encypted or
155 * otherwise unusable. I could be wrong.
156 */
157 void writeCookie( char const *name, char const *value, char const *expires=NULL, char const *path=NULL, char const *domain=NULL, bool secure=false );
158
159 /**
160 * A simple helper class to contain variable data.
161 */
162 class Item
163 {
164 public:
165 /**
166 * Build an empty Item.
167 */
168 Item( )
169 {
170 name = NULL;
171 value = NULL;
172 len = 0;
173 type = 0;
174 }
175 /** The name of the item. */
176 char *name;
177 /** The value of the item. */
178 char *value;
179 /** The length of the item's value. */
180 unsigned long len;
181 /** The type of the item (where it came from). */
182 unsigned char type;
183 };
184
185 /** Header values */
186 enum
187 {
188 headerHTML
189 };
190
191private:
192 /** Keeps track of all contained variables. */
193 LinkedList aVars;
194 /** Keeps track of all content variables. */
195 HashTable aContent;
196};
diff --git a/src/old/configmanagerbase.cpp b/src/old/configmanagerbase.cpp
deleted file mode 100644
index ac55fe0..0000000
--- a/src/old/configmanagerbase.cpp
+++ /dev/null
@@ -1,63 +0,0 @@
1#include <stdlib.h>
2#include <string.h>
3#include "xmlnode.h"
4#include "xmlfilereader.h"
5#include "configmanagerbase.h"
6
7ConfigManagerBase::ConfigManagerBase()
8{
9}
10
11ConfigManagerBase::~ConfigManagerBase()
12{
13}
14
15void ConfigManagerBase::addSearchPath( const std::string &sPath )
16{
17 lSearchPath.push_back( sPath );
18}
19
20void ConfigManagerBase::loadConfig( const std::string &sFileName, const char *lpProfile )
21{
22 // Try a few locations...
23 std::list<std::string>::const_iterator i;
24 for( i = lSearchPath.begin(); i != lSearchPath.end(); i++ )
25 {
26 if( parseConfig( (*i + sFileName).c_str(), lpProfile ) )
27 {
28 break;
29 }
30 }
31}
32
33bool ConfigManagerBase::parseConfig( const char *lpFileName, const char *lpProfile )
34{
35 XmlNode *pRoot, *pCur;
36 XmlFileReader doc( lpFileName );
37
38 pRoot = doc.getRoot();
39 if( pRoot == NULL )
40 {
41 return false;
42 }
43
44 if( strcmp("config", pRoot->getName() ) )
45 {
46 return false;
47 }
48
49 for( int j = 0;; j++ )
50 {
51 pCur = pRoot->getChild( "profile", j );
52 if( pCur == NULL )
53 return false;
54
55 if( !strcmp( pCur->getProperty("id"), lpProfile ) )
56 {
57 return processProfile( pCur );
58 }
59 }
60
61 return false;
62}
63
diff --git a/src/old/configmanagerbase.h b/src/old/configmanagerbase.h
deleted file mode 100644
index 381cc1f..0000000
--- a/src/old/configmanagerbase.h
+++ /dev/null
@@ -1,24 +0,0 @@
1#ifndef CONFIG_MANAGER_BASE_H
2#define CONFIG_MANAGER_BASE_H
3
4#include <string>
5#include <list>
6
7class ConfigManagerBase
8{
9public:
10 ConfigManagerBase();
11 virtual ~ConfigManagerBase();
12
13public:
14 void addSearchPath( const std::string &sPath );
15 void loadConfig( const std::string &sFileName, const char *lpProfile="default" );
16
17private:
18 bool parseConfig( const char *lpFileName, const char *lpProfile );
19 virtual bool processProfile( class XmlNode *pBase )=0;
20
21 std::list<std::string> lSearchPath;
22};
23
24#endif
diff --git a/src/old/confpair.cpp b/src/old/confpair.cpp
deleted file mode 100644
index 4741401..0000000
--- a/src/old/confpair.cpp
+++ /dev/null
@@ -1,2 +0,0 @@
1#include "confpair.h"
2
diff --git a/src/old/confpair.h b/src/old/confpair.h
deleted file mode 100644
index 56eb06e..0000000
--- a/src/old/confpair.h
+++ /dev/null
@@ -1,81 +0,0 @@
1#ifndef CONF_PAIR_H
2#define CONF_PAIR_H
3
4#include <stdint.h>
5#include <string>
6#include <sstream>
7#include "confpairbase.h"
8
9/**
10 *
11 */
12template<class T>
13class ConfPair : public ConfPairBase
14{
15public:
16 ConfPair( const std::string &sName ) :
17 sName( sName )
18 { }
19
20 virtual ~ConfPair()
21 { }
22
23 T &value()
24 {
25 return tValue;
26 }
27
28 const std::string &name()
29 {
30 return sName;
31 }
32
33 virtual void setFromString( const std::string &sStr )
34 {
35 std::stringstream(sStr) >> tValue;
36 }
37
38 virtual std::string getAsString()
39 {
40 std::stringstream tmp;
41 tmp << tValue;
42 return tmp.str();
43 }
44
45private:
46 std::string sName;
47 T tValue;
48};
49
50template<>
51void ConfPair<std::string>::setFromString( const std::string &sStr )
52{
53 tValue = sStr;
54}
55
56template<>
57std::string ConfPair<std::string>::getAsString()
58{
59 return tValue;
60}
61
62template<>
63void ConfPair<bool>::setFromString( const std::string &sStr )
64{
65 if( !strcasecmp( sStr.c_str(), "true" ) ||
66 !strcasecmp( sStr.c_str(), "yes" ) ||
67 !strcasecmp( sStr.c_str(), "on" ) )
68 tValue = true;
69 else
70 tValue = false;
71}
72
73template<>
74std::string ConfPair<bool>::getAsString()
75{
76 if( tValue == true )
77 return "True";
78 return "False";
79}
80
81#endif
diff --git a/src/old/confpairbase.cpp b/src/old/confpairbase.cpp
deleted file mode 100644
index 1203dc0..0000000
--- a/src/old/confpairbase.cpp
+++ /dev/null
@@ -1,17 +0,0 @@
1#include "confpairbase.h"
2
3ConfPairBase::ConfPairBase()
4{
5}
6
7ConfPairBase::~ConfPairBase()
8{
9}
10
11ConfPairBase &ConfPairBase::operator=( const std::string &s )
12{
13 setFromString( s );
14
15 return *this;
16}
17
diff --git a/src/old/confpairbase.h b/src/old/confpairbase.h
deleted file mode 100644
index 2530756..0000000
--- a/src/old/confpairbase.h
+++ /dev/null
@@ -1,24 +0,0 @@
1#ifndef CONF_PAIR_BASE_H
2#define CONF_PAIR_BASE_H
3
4#include <stdint.h>
5#include <string>
6#include <ostream>
7#include <istream>
8
9class ConfPairBase
10{
11public:
12 ConfPairBase();
13 virtual ~ConfPairBase();
14
15 virtual void setFromString( const std::string &sStr )=0;
16 virtual std::string getAsString()=0;
17
18 ConfPairBase &operator=( const std::string &s );
19
20private:
21
22};
23
24#endif
diff --git a/src/old/conftree.cpp b/src/old/conftree.cpp
deleted file mode 100644
index d9a3a3f..0000000
--- a/src/old/conftree.cpp
+++ /dev/null
@@ -1,9 +0,0 @@
1#include "conftree.h"
2
3ConfTree::ConfTree()
4{
5}
6
7ConfTree::~ConfTree()
8{
9}
diff --git a/src/old/conftree.h b/src/old/conftree.h
deleted file mode 100644
index 197b1ef..0000000
--- a/src/old/conftree.h
+++ /dev/null
@@ -1,19 +0,0 @@
1#ifndef CONF_TREE_H
2#define CONF_TREE_H
3
4#include <stdint.h>
5
6/**
7 *
8 */
9class ConfTree
10{
11public:
12 ConfTree();
13 virtual ~ConfTree();
14
15private:
16
17};
18
19#endif
diff --git a/src/old/connection.cpp b/src/old/connection.cpp
deleted file mode 100644
index efef144..0000000
--- a/src/old/connection.cpp
+++ /dev/null
@@ -1,564 +0,0 @@
1#include "connection.h"
2#include <string.h>
3#include <stdio.h>
4#include <errno.h>
5#include <stdlib.h>
6#include <unistd.h>
7#include <sys/types.h>
8#include <sys/socket.h>
9#include <sys/time.h>
10#include <netinet/in.h>
11#include <netdb.h>
12#include <arpa/inet.h>
13#include <errno.h>
14#include <fcntl.h>
15#include "exceptions.h"
16
17// Read buffer size...maybe fix wierd issues...
18#define RBS (1024*10)
19
20Connection::Connection()
21{
22 nSocket = -1;
23 bActive = false;
24 bDisconnectMe = false;
25 pProtocol = NULL;
26}
27
28Connection::~Connection()
29{
30 if( pProtocol != NULL ) delete pProtocol;
31}
32
33void Connection::ensureCapacity( int nSize )
34{
35 xOutputBuf.ensureCapacity( nSize );
36}
37
38bool Connection::appendOutput( const char *lpOutput, int nSize )
39{
40 return xOutputBuf.appendData( lpOutput, nSize );
41}
42
43bool Connection::appendOutput( const char lOutput )
44{
45 return xOutputBuf.appendData( lOutput );
46}
47
48bool Connection::appendOutput( const short lOutput )
49{
50 return xOutputBuf.appendData( lOutput );
51}
52
53bool Connection::appendOutput( const int lOutput )
54{
55 return xOutputBuf.appendData( lOutput );
56}
57
58bool Connection::appendOutput( const long lOutput )
59{
60 return xOutputBuf.appendData( lOutput );
61}
62
63bool Connection::appendOutput( const float lOutput )
64{
65 return xOutputBuf.appendData( lOutput );
66}
67
68bool Connection::appendOutput( const double lOutput )
69{
70 return xOutputBuf.appendData( lOutput );
71}
72
73bool Connection::appendOutput( const unsigned char lOutput )
74{
75 return xOutputBuf.appendData( lOutput );
76}
77
78bool Connection::appendOutput( const unsigned short lOutput )
79{
80 return xOutputBuf.appendData( lOutput );
81}
82
83bool Connection::appendOutput( const unsigned long lOutput )
84{
85 return xOutputBuf.appendData( lOutput );
86}
87
88bool Connection::appendOutput( const unsigned int lOutput )
89{
90 return xOutputBuf.appendData( lOutput );
91}
92
93bool Connection::appendInput( const char *lpInput, int nSize )
94{
95 return xInputBuf.appendData( lpInput, nSize );
96}
97
98int Connection::scanInputFor( char cTarget )
99{
100 const char *lpTmp = xInputBuf.getData();
101 int jMax = xInputBuf.getLength();
102
103 for( int j = 0; j < jMax; j++ )
104 {
105 if( lpTmp[j] == cTarget )
106 {
107 return j;
108 }
109 }
110
111 return -1;
112}
113
114const char *Connection::getOutput()
115{
116 return xOutputBuf.getData();
117}
118
119const char *Connection::getInput()
120{
121 return xInputBuf.getData();
122}
123
124void Connection::setSocket( int nNewSocket )
125{
126 nSocket = nNewSocket;
127}
128
129int Connection::getSocket()
130{
131 return nSocket;
132}
133
134bool Connection::isActive()
135{
136 return bActive;
137}
138
139void Connection::close()
140{
141 //printf("Close called, socket is: %s\n", bActive?"Active":"Inactive" );
142 if( bActive )
143 {
144 fsync( nSocket );
145 ::close( nSocket );
146 //printf("Socket closed.\n");
147 }
148 bActive = false;
149 //nSocket = -1;
150 xInputBuf.clearData();
151 xOutputBuf.clearData();
152 if( pProtocol != NULL )
153 {
154 delete pProtocol;
155 pProtocol = NULL;
156 }
157}
158
159bool Connection::open( int nNewSocket )
160{
161 bActive = true;
162 setSocket( nNewSocket );
163 bDisconnectMe = false;
164
165 return true;
166}
167
168bool Connection::open( const char *sAddr, int nPort, int nSec )
169{
170 struct sockaddr_in xServerName;
171 bActive = false;
172
173 /* Create the socket. */
174 nSocket = socket( PF_INET, SOCK_STREAM, 0 );
175
176 if( nSocket < 0 )
177 {
178 bActive = false;
179 return false;
180 }
181
182 // These lines set the socket to non-blocking, a good thing?
183 int flags;
184 flags = fcntl(nSocket, F_GETFL, 0);
185 flags |= O_NONBLOCK;
186 if (fcntl(nSocket, F_SETFL, flags) < 0)
187 {
188 return false;
189 }
190
191 /* Connect to the server. */
192 //printf("Resolving hostname (%s)...\n", sAddr );
193 {
194 struct hostent *hostinfo;
195
196 xServerName.sin_family = AF_INET;
197 xServerName.sin_port = htons( nPort );
198 hostinfo = gethostbyname( sAddr );
199 if (hostinfo == NULL)
200 {
201 return false;
202 }
203 xServerName.sin_addr = *(struct in_addr *) hostinfo->h_addr;
204 }
205
206 //printf("Making actual connection...");
207 //fflush( stdout );
208 connect(
209 nSocket,
210 (struct sockaddr *)&xServerName,
211 sizeof(xServerName)
212 );
213 //printf("Connected.\n");
214
215 bActive = true;
216 bDisconnectMe = false;
217
218 if( nSec > 0 )
219 {
220 fd_set rfds, wfds, efds;
221 int retval;
222
223 FD_ZERO(&rfds);
224 FD_SET(nSocket, &rfds);
225 FD_ZERO(&wfds);
226 FD_SET(nSocket, &wfds);
227 FD_ZERO(&efds);
228 FD_SET(nSocket, &efds);
229
230 struct timeval tv;
231 tv.tv_sec = nSec;
232 tv.tv_usec = 0;
233
234 retval = select( nSocket+1, &rfds, &wfds, &efds, &tv );
235
236 if( retval == 0 )
237 {
238 close();
239 throw ExceptionBase("Connection timeout.\n");
240 }
241
242 }
243
244 /*
245 if( ret < 0 )
246 {
247 return false;
248 }*/
249
250 return true;
251}
252
253int Connection::readInput()
254{
255 char buffer[RBS];
256 int nbytes;
257 int nTotalRead=0;
258
259 for(;;)
260 {
261 //memset( buffer, 0, RBS );
262
263 nbytes = read( nSocket, buffer, RBS );
264 if( nbytes < 0 && errno != 0 && errno != EAGAIN )
265 {
266 //printf("errno: %d, %s\n", errno, strerror( errno ) );
267 /* Read error. */
268 //perror("readInput");
269 throw ConnectionException( excodeReadError, "Read error: %s", strerror( errno ) );
270 }
271 else
272 {
273 if( nbytes <= 0 )
274 break;
275 nTotalRead += nbytes;
276 appendInput( buffer, nbytes );
277 /* Data read. */
278 if( nbytes < RBS )
279 {
280 break;
281 }
282
283 /* New test, if data is divisible by RBS bytes on some libs the
284 * read could block, this keeps it from happening.
285 */
286 {
287 fd_set rfds;
288 FD_ZERO(&rfds);
289 FD_SET(nSocket, &rfds);
290 struct timeval tv = { 0, 0 };
291 int retval = select( nSocket+1, &rfds, NULL, NULL, &tv );
292 if( retval == -1 )
293 throw ConnectionException(
294 excodeBadReadError,
295 "Bad Read error"
296 );
297 if( !FD_ISSET( nSocket, &rfds ) )
298 break;
299 }
300
301 }
302 }
303
304 if( pProtocol != NULL && nTotalRead > 0 )
305 {
306 pProtocol->onNewData();
307 }
308
309 return nTotalRead;
310}
311
312bool Connection::readInput( int nSec, int nUSec, int *pnSecBack, int *pnUSecBack )
313{
314 fd_set rfds, efds;
315 struct timeval tv, start, end;
316 struct timezone tz;
317 int retval;
318
319 gettimeofday( &start, &tz );
320
321 FD_ZERO(&rfds);
322 FD_SET(nSocket, &rfds);
323 FD_ZERO(&efds);
324 FD_SET(nSocket, &efds);
325
326 tv.tv_sec = nSec;
327 tv.tv_usec = nUSec;
328
329 //printf("Starting at %d %d\n", nSec, nUSec );
330 retval = select( nSocket+1, &rfds, NULL, NULL, &tv );
331
332 if( retval == -1 )
333 {
334 // Oh my god!!! some kind of horrible problem!!!!
335 throw ConnectionException( excodeBadReadError, "Bad Read error");
336 return false;
337 }
338 else if( retval )
339 {
340 //printf("retval=%d, nSocket=%d,%d, sec=%d, usec=%d\n", retval, nSocket, FD_ISSET( nSocket, &rfds ), tv.tv_sec, tv.tv_usec );
341 // None of them have data, but the connection is still active.
342 if( FD_ISSET( nSocket, &rfds ) )
343 {
344 if( readInput() == 0 )
345 {
346 throw ConnectionException( excodeConnectionClosed, "Connection closed"); }
347 }
348 }
349
350 gettimeofday( &end, &tz );
351
352 int st, ust;
353 st = nSec - ( end.tv_sec - start.tv_sec );
354 if( ( end.tv_usec - start.tv_usec ) > nUSec )
355 {
356 (st)--;
357 ust = 1000000 - (end.tv_usec - start.tv_usec);
358 }
359 else
360 {
361 ust = nUSec - (end.tv_usec - start.tv_usec);
362 }
363
364 if( st < 0 )
365 {
366 st = ust = 0;
367 }
368
369 if( pnSecBack )
370 {
371 *pnSecBack = st;
372 *pnUSecBack = ust;
373 }
374
375 //printf("New time: %d %d\n", *pnSecBack, *pnUSecBack );
376
377 return true;
378}
379
380void Connection::waitForInput( int nBytesIn, int nSec, int nUSec )
381{
382 int rlen = getInputAmnt();
383
384 if( rlen >= nBytesIn )
385 return;
386
387 while( rlen < nBytesIn )
388 {
389 if( nSec == 0 && nUSec == 0 )
390 {
391 throw ConnectionException( excodeSocketTimeout, "Timed out while waiting for %d bytes.", nBytesIn );
392 }
393 readInput( nSec, nUSec, &nSec, &nUSec );
394 rlen = getInputAmnt();
395 }
396}
397
398bool Connection::clearOutput()
399{
400 return xOutputBuf.clearData();
401}
402
403bool Connection::clearInput()
404{
405 return xInputBuf.clearData();
406}
407
408#define min( a, b ) ((a<b)?(a):(b))
409
410bool Connection::writeOutput()
411{
412 //int nBytes = TEMP_FAILURE_RETRY( write( nSocket, xOutputBuf.getData(), min( RBS, xOutputBuf.getLength() ) ) );
413 int nBytes = TEMP_FAILURE_RETRY( write( nSocket, xOutputBuf.getData(), xOutputBuf.getLength() ) );
414 if( nBytes < 0 )
415 {
416 perror("writeOutput");
417 return true;
418 }
419 /*
420 if( nBytes < xOutputBuf.getLength() )
421 {
422 printf("Havn't written all the data (%d/%d/%d%%)\n", nBytes, xOutputBuf.getLength(), nBytes/(xOutputBuf.getLength()*100) );
423 }
424 else
425 {
426 printf("Wrote all pending data.\n");
427 }
428 */
429 xOutputBuf.usedData( nBytes );
430 //clearOutput();
431
432 return true;
433}
434
435bool Connection::writeAllOutput()
436{
437 while( hasOutput() ) writeOutput();
438 return true;
439}
440
441bool Connection::hasOutput()
442{
443 if( xOutputBuf.getLength() == 0 )
444 {
445 return false;
446 }
447 else
448 {
449 return true;
450 }
451}
452
453bool Connection::hasInput()
454{
455 if( xInputBuf.getLength() == 0 )
456 {
457 return false;
458 }
459 else
460 {
461 return true;
462 }
463}
464
465bool Connection::usedInput( int nAmount )
466{
467 return xInputBuf.usedData( nAmount );
468}
469
470bool Connection::needDisconnect()
471{
472 return bDisconnectMe;
473}
474
475void Connection::disconnect()
476{
477 bDisconnectMe = true;
478}
479
480void Connection::setProtocol( class Protocol *pNewProtocol )
481{
482 pProtocol = pNewProtocol;
483 pProtocol->setConnection( this );
484}
485
486int Connection::getInputAmnt()
487{
488 return xInputBuf.getLength();
489}
490
491int Connection::getOutputAmnt()
492{
493 return xOutputBuf.getLength();
494}
495
496class Protocol *Connection::getProtocol()
497{
498 return pProtocol;
499}
500
501void Connection::printInputDebug( const char *lpPrefix, FILE *fh, int nBytesMax )
502{
503 printDataDebug(
504 (const unsigned char *)xInputBuf.getData(),
505 xInputBuf.getLength(),
506 "input",
507 lpPrefix,
508 fh,
509 nBytesMax
510 );
511}
512
513void Connection::printOutputDebug( const char *lpPrefix, FILE *fh, int nBytesMax )
514{
515 printDataDebug(
516 (const unsigned char *)xOutputBuf.getData(),
517 xOutputBuf.getLength(),
518 "output",
519 lpPrefix,
520 fh,
521 nBytesMax
522 );
523}
524
525void Connection::printDataDebug( const unsigned char *pData, long nDataLen, const char *lpName, const char *lpPrefix, FILE *fh, int nBytesMax )
526{
527 if( nBytesMax > 0 )
528 {
529 nDataLen = (nBytesMax<nDataLen)?(nBytesMax):(nDataLen);
530 }
531
532 fprintf( fh, "%sDisplaying %ld bytes of %s.\n", lpPrefix, nDataLen, lpName );
533 int j = 0;
534 fprintf( fh, lpPrefix );
535 for( int l = 0; l < 8*3+2*8+2; l++ ) fprintf( fh, (l!=8*3)?("-"):("+") ); fprintf( fh, "\n");
536 for(;;)
537 {
538 fprintf( fh, lpPrefix );
539 int kmax = 8;
540 if( nDataLen-j < 8 ) kmax = nDataLen-j;
541 for(int k = 0; k < 8; k++ )
542 {
543 if( k < kmax )
544 {
545 fprintf( fh, "%02X ", (int)((unsigned char)pData[j+k]) );
546 }
547 else
548 {
549 fprintf( fh, "-- ");
550 }
551 }
552 printf("| ");
553 for(int k = 0; k < kmax; k++ )
554 {
555 fprintf( fh, "%c ", (pData[j+k]>32 && pData[j+k]<=128)?(pData[j+k]):('.') );
556 }
557 fprintf( fh, "\n");
558 j += kmax;
559 if( j >= nDataLen ) break;
560 }
561 fprintf( fh, lpPrefix );
562 for( int l = 0; l < 8*3+2*8+2; l++ ) fprintf( fh, (l!=8*3)?("-"):("+") ); fprintf( fh, "\n");
563}
564
diff --git a/src/old/connection.h b/src/old/connection.h
deleted file mode 100644
index 0e991c7..0000000
--- a/src/old/connection.h
+++ /dev/null
@@ -1,411 +0,0 @@
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 virtual ~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, int nSec=30 );
53
54 void ensureCapacity( int nSize );
55
56 /** Append the given data to the output. The data is presumed to be null
57 * terminated. To put binary data into the stream, use the other
58 * appendOutput function. This should be the only method used to
59 * communicate with the socket.
60 *@param lpOutput The data to add to the output queue.
61 *@param nSize How much data is in the lpOutput buffer. If this value
62 * is -1 then the program treats lpOutput as a null-terminated string.
63 *@returns True if everything is ok, false otherwise.
64 */
65 bool appendOutput( const char *lpOutput, int nSize=-1 );
66
67 /**
68 * Append the character to the output.
69 *@param lOutput The character to add to the output queue.
70 *@returns True if everything is ok, false otherwise.
71 */
72 bool appendOutput( const char lOutput );
73
74 /**
75 * Append the short to the output.
76 *@param lOutput The short to add to the output queue.
77 *@returns True if everything is ok, false otherwise.
78 */
79 bool appendOutput( const short lOutput );
80
81 /**
82 * Append the int to the output.
83 *@param lOutput The int to add to the output queue.
84 *@returns True if everything is ok, false otherwise.
85 */
86 bool appendOutput( const int lOutput );
87
88 /**
89 * Append the long to the output.
90 *@param lOutput The long to add to the output queue.
91 *@returns True if everything is ok, false otherwise.
92 */
93 bool appendOutput( const long lOutput );
94
95 /**
96 * Append the float to the output.
97 *@param lOutput The float to add to the output queue.
98 *@returns True if everything is ok, false otherwise.
99 */
100 bool appendOutput( const float lOutput );
101
102 /**
103 * Append the double to the output.
104 *@param lOutput The double to add to the output queue.
105 *@returns True if everything is ok, false otherwise.
106 */
107 bool appendOutput( const double lOutput );
108
109 /**
110 * Append the unsigned char to the output.
111 *@param lOutput The unsigned char to add to the output queue.
112 *@returns True if everything is ok, false otherwise.
113 */
114 bool appendOutput( const unsigned char lOutput );
115
116 /**
117 * Append the unsigned short to the output.
118 *@param lOutput The unsigned short to add to the output queue.
119 *@returns True if everything is ok, false otherwise.
120 */
121 bool appendOutput( const unsigned short lOutput );
122
123 /**
124 * Append the unsigned int to the output.
125 *@param lOutput The unsigned int to add to the output queue.
126 *@returns True if everything is ok, false otherwise.
127 */
128 bool appendOutput( const unsigned int lOutput );
129
130 /**
131 * Append the unsigned long to the output.
132 *@param lOutput The unsigned long to add to the output queue.
133 *@returns True if everything is ok, false otherwise.
134 */
135 bool appendOutput( const unsigned long lOutput );
136
137 /**
138 * Writes all input data in the buffer in a dual-view ascii and hex display
139 * to a file. There are a number of options that also help with debugging.
140 *@param lpPrefix Text to be added to the begining of every line written
141 * out. The default is a blank string.
142 *@param fh The file to write the data to in text mode. This is stdout by
143 * default, but could be any already open file handle.
144 *@param nBytesMax The maximum number of bytes to write to the output. The
145 * amount of data can be overwhelming sometimes, so you can limit it. The
146 * default value is -1, which is also unlimited.
147 */
148 void printInputDebug( const char *lpPrefix="", FILE *fh=stdout, int nBytesMax=-1 );
149
150 /**
151 * Writes all output data in the buffer in a dual-view ascii and hex display
152 * to a file. There are a number of options that also help with debugging.
153 *@param lpPrefix Text to be added to the begining of every line written
154 * out. The default is a blank string.
155 *@param fh The file to write the data to in text mode. This is stdout by
156 * default, but could be any already open file handle.
157 *@param nBytesMax The maximum number of bytes to write to the output. The
158 * amount of data can be overwhelming sometimes, so you can limit it. The
159 * default value is -1, which is also unlimited.
160 */
161 void printOutputDebug( const char *lpPrefix="", FILE *fh=stdout, int nBytesMax=-1 );
162
163 /**
164 * This is the low-level generic function that is called by both
165 * printInputDebug and printOutputDebug. It works effectively just like
166 * both of them, except that you can give it a raw pointer to the data to
167 * print out. This probably doesn't belong in this class, but this was
168 * where I was when I needed it.
169 *@param pData A pointer to the data to write. This is not treated as a
170 * null terminated string, so make sure that the nDataLen param is set
171 * properly.
172 *@param nDataLen The number of bytes that are in pData and that you want to
173 * see.
174 *@param lpName The name of the data, this is used in the header where it
175 * says "Displaying nnn bytes of <lpName>." A good example would be input
176 * or output.
177 *@param lpPrefix Text to put before every line output. This just makes it
178 * easier to tell large blocks apart in the output.
179 *@param fh The file handle to write all data to.
180 *@param nBytesMax The maximum number of bytes. This parameter is stupid.
181 * If it is set to -1, then nDataLen is used, otherwise the smaller value is
182 * used as the number of bytes to output.
183 *@todo Put this function somewhere more deserving.
184 *@todo Remove the nBytesMax param, we need that in the other functions,
185 * not this one!
186 */
187 void printDataDebug( const unsigned char *pData, long nDataLen, const char *lpName, const char *lpPrefix, FILE *fh, int nBytesMax );
188
189 /** Append the given data to the input. The data is presumed to be null
190 * terminated. To put binary data into the stream, use the other
191 * appendInput function. This is mainly used by internal routines.
192 *@param lpInput The data to add to the input queue.
193 *@param nSize How much data is in the lpInput buffer. If this value
194 * is -1 then the program treats lpOutput as a null-terminated string.
195 *@returns True if everything is ok, false otherwise.
196 */
197 bool appendInput( const char *lpInput, int nSize=-1 );
198
199 /** Searches through the current pending input for a certain character.
200 * This is useful for finding out where exactly the end of a line is, for
201 * example, to see if a command has been entered yet.
202 *@param cTarget The character to search for.
203 *@returns The position of the target relative to the begining of the input
204 * or -1 if the target wasn't found.
205 */
206 int scanInputFor( char cTarget );
207
208 /** Gets a pointer to the output buffer. This is mainly used by internal
209 * routines, and is cleared every click when data is sent out again.
210 *@returns A pointer to the buffer holding the pending output data.
211 */
212 const char *getOutput();
213
214 /** Gets a pointer to the start of the input buffer's active data
215 * section. Use this to gain access to the input you need to do
216 * your job.
217 *@returns A pointer to the data in the input buffer. Do not delete this.
218 */
219 const char *getInput();
220
221 /** Clears all pending output, this is mainly just used internally.
222 *@returns True if operation was a success, otherwise false.
223 */
224 bool clearOutput();
225
226 /** Clears all pending input, weather it's been used or not. Please
227 * refrain from calling this during normal operation, use usedInput
228 * instead, it's much safer.
229 *@returns True if the operation was a success, false otherwise.
230 */
231 bool clearInput();
232
233 /** Sets the socket that should be used internally.
234 *@param nNewSocket The new socket to work with.
235 */
236 void setSocket( int nNewSocket );
237
238 /** Gets the handle (number) of the working socket. This can be a
239 * dangerous function to call, please refrain from calling it directly
240 * if any alternative can be found.
241 *@returns The number of the working socket.
242 */
243 int getSocket();
244
245 /** Determines if the connection is still active.
246 *@returns True if the connection is active, false otherwise.
247 */
248 bool isActive();
249
250 /** Clears all buffers and sets up the connection to be reused.
251 * Does not actually close the socket, that's handled by the
252 * ConnectionManager
253 */
254 void close();
255
256 /** Opens a socket. Really just sets up the connection for use since
257 * the socket itself was created and opened by the ConnectionManager.
258 * This also calls setSocket so you don't have to.
259 *@param nNewSocket The socket to assosiate with.
260 */
261 bool open( int nNewSocket );
262
263 /**
264 * Reads all pending input from the connection. If this is called outside
265 * of the ConnectionManager it will usually block indefinately waiting for
266 * new data. The only way to change this behaviour is to modify the socket
267 * low-level when you connect it manually, or, preferably use the other
268 * readInput function to control blocking time.
269 *@returns True socket is still connected, otherwise false.
270 */
271 int readInput();
272
273 /**
274 * Reads all pending input from the connection, blocking up to nSec
275 * seconds and nUSec micro-seconds for the data. This uses select to
276 * simulate blocking, but has the same effect as standard io blocking.
277 * If you don't want to block, just set both values to zero. The back
278 * parameters are optional, set to null to not use them. The variables
279 * you pass in through the back parameters will contain the remaining
280 * time if data arrived before the max timeout was reached.
281 *@param nSec Max seconds to wait.
282 *@param nUSec Max micro-seconds to wait.
283 *@param pnSecBack The number of seconds remaining.
284 *@param pnUSecBack The number of micro-seconds remaining.
285 */
286 bool readInput( int nSec, int nUSec, int *pnSecBack=NULL, int *pnUSecBack=NULL );
287
288 /**
289 * Waits until at least nBytesIn are read into the input buffer and ready
290 * to be used. Wait at most nSec seconds plus nUSec micro seconds.
291 * If the timeout is exceeded, this function throws an exception. If this
292 * function returns normally, you are guranteed to have at least nBytesIn
293 * bytes in your input buffer.
294 *@param nBytesIn Number of bytes to read.
295 *@param nSec The max seconds to wait.
296 *@param sUSec The max microseconds to wait.
297 */
298 void waitForInput( int nBytesIn, int nSec, int nUSec );
299
300 /** Writes some data that is pending to the socket.
301 *@returns True if all data was written succesfully, false otherwise.
302 */
303 bool writeOutput();
304
305 /**
306 * Writes all data that is pending on the socekt.
307 */
308 bool writeAllOutput();
309
310 /** Determines if the connection has output waiting to go out.
311 *@returns true if there is pending output, otherwise false.
312 */
313 bool hasOutput();
314
315 /** Sets internal flags so that this connection will be deleted next
316 * time through the ConnectionManager.
317 */
318 void disconnect();
319
320 /** Determines if this connection is ready to be disconnected or not.
321 *@returns True if it is time to disconnect, false if it isn't.
322 */
323 bool needDisconnect();
324
325 /** Tells the caller if there is pending input waiting to be processed.
326 *@returns True if there is pending input that has not been used, returns
327 * false if there isn't.
328 */
329 bool hasInput();
330
331 /** Removes bytes from the begining of the input queue. Use this after
332 * getting the input and processing as much as you need to.
333 *@param nAmount The number of bytes used.
334 *@returns true if the update was successful, otherwise false.
335 */
336 bool usedInput( int nAmount );
337
338 /** Sets the protocol to be used by this connection. All data in and out
339 * passes through the protocol object, which may process that data to
340 * filter out and process any special messages that may have been
341 * included. Everything that isn't processed can be accessed in the
342 * standard method.
343 *@param pNewProtocol A pointer to a protocol object that you want to
344 * use.
345 */
346 void setProtocol( class Protocol *pNewProtocol );
347
348 /** Gets the number of bytes that are waiting in the input queue, the data
349 * that has yet to be processed.
350 *@returns The number of bytes in the input queue.
351 */
352 int getInputAmnt();
353
354 /** Gets the number of bytes that are waiting in the output queue, the data
355 * that has yet to be sent to the connected socket.
356 *@returns The number of bytes in the input queue.
357 */
358 int getOutputAmnt();
359
360 /** Gets a pointer to the protocol that is attatched to this connection
361 * object. This is useful to set modes, and send special commands in
362 * addition to the standard raw data reads and writes that are normally
363 * permitted. In fact, in everything besides a raw telnet protocol all
364 * data should be sent through the protocol and not the connection object.
365 *@returns A pointer to the Protocol assosiated with this connection.
366 */
367 class Protocol *getProtocol();
368
369private:
370 /**
371 * A buffer to keep data read from the socket in. This is filled in by
372 * the function readInput, which is automatically called by the
373 * ConnectionManager whenever new data is ready.
374 */
375 FlexBuf xInputBuf;
376
377 /**
378 * A buffer to keep data that should be sent to the socket. This is filled
379 * in by using the AppendOutput functions and is sent to the socket using
380 * the writeOutput function, which is automatically called every cycle by
381 * the ConnectionManager when there is pending data.
382 */
383 FlexBuf xOutputBuf;
384
385 /**
386 * The socket that the user is connected to. This is not the same as the
387 * socket number of the listening socket, this is the unique socket on the
388 * system that the data is coming to.
389 */
390 int nSocket;
391
392 /**
393 * True=active connection, False=connection lost
394 */
395 bool bActive;
396
397 /**
398 * True=disconnect next cycle (after data is transmitted), Flse=keep going.
399 */
400 bool bDisconnectMe;
401
402 /**
403 * A pointer to a protocol handler that can automatically process the data
404 * in the buffers. This is optional if you use the connections on your own
405 * but reccomended if you use this with the rest of the ConnectionManager
406 * system.
407 */
408 class Protocol *pProtocol;
409};
410
411#endif
diff --git a/src/old/connectionmanager.cpp b/src/old/connectionmanager.cpp
deleted file mode 100644
index ea60b2b..0000000
--- a/src/old/connectionmanager.cpp
+++ /dev/null
@@ -1,397 +0,0 @@
1#include <time.h>
2#include <string.h>
3#include <stdio.h>
4#include <errno.h>
5#include <stdlib.h>
6#include <unistd.h>
7#include <sys/types.h>
8#include <sys/socket.h>
9#include <termios.h>
10#include <netinet/in.h>
11#include <netdb.h>
12#include <arpa/inet.h>
13#include "connectionmanager.h"
14#include <fcntl.h>
15
16ConnectionManager::ConnectionManager( int nInitPool ) :
17 xLog( MultiLog::getInstance() )
18{
19 //nMasterSocket = -1;
20 pMonitor = NULL;
21 for( int j = 0; j < nInitPool; j++ )
22 {
23 lInactive.insert( lInactive.begin(), new Connection() );
24 }
25 FD_ZERO (&fdActive);
26 FD_ZERO (&fdRead);
27 FD_ZERO (&fdWrite);
28 FD_ZERO (&fdException);
29}
30
31ConnectionManager::~ConnectionManager()
32{
33 std::list<Connection *>::const_iterator i;
34 for( i = lActive.begin(); i != lActive.end(); i++ )
35 {
36 delete (*i);
37 }
38 for( i = lInactive.begin(); i != lInactive.end(); i++ )
39 {
40 delete (*i);
41 }
42}
43
44bool ConnectionManager::startServer( int nPort )
45{
46 /* Create the socket and set it up to accept connections. */
47 struct sockaddr_in name;
48
49 /* Give the socket a name. */
50 name.sin_family = AF_INET;
51 name.sin_port = htons( nPort );
52
53 // I think this specifies who we will accept connections from,
54 // a good thing to make configurable later on
55 name.sin_addr.s_addr = htonl( INADDR_ANY );
56
57 return startServer( name );
58}
59
60bool ConnectionManager::startServer( const char *sAddr, int nPort )
61{
62 /* Create the socket and set it up to accept connections. */
63 struct sockaddr_in name;
64
65 /* Give the socket a name. */
66 name.sin_family = AF_INET;
67 name.sin_port = htons( nPort );
68
69 inet_aton( sAddr, &name.sin_addr );
70
71 return startServer( name );
72}
73
74bool ConnectionManager::startServer( struct sockaddr_in &name )
75{
76 /* Create the socket. */
77 int nMasterSocket = socket (PF_INET, SOCK_STREAM, 0);
78 if (nMasterSocket < 0)
79 {
80 xLog.LineLog( MultiLog::LError, "Couldn't create a listen socket.");
81 return false;
82 }
83
84 int opt = 1;
85 setsockopt(
86 nMasterSocket,
87 SOL_SOCKET,
88 SO_REUSEADDR,
89 (char *)&opt,
90 sizeof(opt)
91 );
92
93 if (bind (nMasterSocket, (struct sockaddr *) &name, sizeof (name)) < 0)
94 {
95 xLog.LineLog( MultiLog::LError, "Couldn't bind to the listen socket.");
96 return false;
97 }
98
99 if (listen (nMasterSocket, 40) < 0)
100 {
101 xLog.LineLog( MultiLog::LError, "Couldn't begin listening to the server socket.");
102 return false;
103 }
104
105 /* Initialize the set of active sockets. */
106 FD_SET (nMasterSocket, &fdActive);
107
108 sMasterSocket[nMasterSocket] = name.sin_port;
109
110 return true;
111}
112
113bool ConnectionManager::startServer( int nPort, int nNumTries, int nTimeout )
114{
115 struct timeval xTimeout;
116
117 for( int j = 0; j < nNumTries; j++ )
118 {
119 xLog.LineLog( MultiLog::LStatus, "Attempting to create server socket (attempt [%d/%d])...", j+1, nNumTries );
120 if( startServer( nPort ) == true )
121 {
122 return true;
123 }
124 else if( j < nNumTries-1 )
125 {
126 xLog.LineLog( MultiLog::LStatus, "Waiting for %d secconds to allow port to clear...", nTimeout );
127 xTimeout.tv_sec = nTimeout;
128 xTimeout.tv_usec = 0;
129 if (select(0, (fd_set *) 0, (fd_set *) 0, (fd_set *) 0, &xTimeout) < 0) {
130 xLog.LineLog( MultiLog::LError, "Error using select to sleep for a while.");
131 }
132 usleep( nTimeout );
133 }
134 }
135
136 return false;
137}
138
139bool ConnectionManager::scanConnections( int nTimeout, bool bForceTimeout )
140{
141 struct timeval xTimeout;
142
143 xTimeout.tv_sec = nTimeout / 1000000;
144 xTimeout.tv_usec = nTimeout % 1000000;
145
146 /* Block until input arrives on one or more active sockets. */
147 fdRead = fdActive;
148 fdWrite = fdActive;
149 fdException = fdActive;
150
151 // We removed the write checking because it just checks to see if you *can*
152 // write...that's stupid, they're all open, so it always exits immediately
153 // if there are ANY connections there...
154 if( TEMP_FAILURE_RETRY( select( FD_SETSIZE, &fdRead, (fd_set *)0/*&fdWrite*/, &fdException, &xTimeout ) ) < 0 )
155 {
156 xLog.LineLog( MultiLog::LError, "Error attempting to scan open connections.");
157 perror("ConnectionManager");
158 return false;
159 }
160 // Now we use select to sleep as well as to scan for connections, now we
161 // just need to fix the fact that if there are no connections, the seccond
162 // select call doesn't return until there is a connection...
163 if( bForceTimeout )
164 {
165 if (select(0, (fd_set *) 0, (fd_set *) 0, (fd_set *) 0, &xTimeout) < 0) {
166 xLog.LineLog( MultiLog::LError, "Error using select to sleep for a while.");
167 }
168 }
169
170 /* Service all the sockets with input pending. */
171 for( int i = 0; i < FD_SETSIZE; ++i )
172 {
173 if( FD_ISSET( i, &fdRead ) )
174 {
175 if( sMasterSocket.find( i ) != sMasterSocket.end() )
176 {
177 addConnection( i );
178 }
179 else
180 {
181 Connection *pCon = findActiveConnection( i );
182 if( pCon == NULL )
183 {
184 xLog.LineLog( MultiLog::LError, "A connection object was lost, or never created!");
185 return false;
186 }
187
188 /* Data arriving on an already-connected socket. */
189 if( pCon->readInput() == 0 )
190 {
191 xLog.LineLog( MultiLog::LStatus, "Closing connection due to disconnect.");
192 close( i );
193 FD_CLR( i, &fdActive );
194 pMonitor->onClosedConnection( pCon );
195 pCon->close();
196 }
197 else
198 {
199 // We actually read something...but the connection handles
200 // protocol notification, so we don't need to do anything
201 // here...
202 }
203 }
204 }
205 }
206 std::list<Connection *>::iterator i;
207 for( i = lActive.begin(); i != lActive.end(); i++ )
208 {
209 if( (*i)->isActive() == false )
210 {
211 std::list<Connection *>::iterator l = i;
212 i--;
213 lInactive.insert( lInactive.end(), *l );
214 lActive.erase( l );
215 continue;
216 }
217 (*i)->getProtocol()->poll();
218 if( (*i)->hasOutput() )
219 {
220 (*i)->writeOutput();
221 }
222 if( (*i)->needDisconnect() && !(*i)->hasOutput() )
223 {
224 int prt = (*i)->getSocket();
225 close( prt );
226 FD_CLR( prt, &fdActive );
227 pMonitor->onClosedConnection( *i );
228 (*i)->close();
229 lInactive.insert( lInactive.end(), *i );
230 std::list<Connection *>::iterator l = i;
231 i--;
232 lActive.erase( l );
233 xLog.LineLog( MultiLog::LStatus, "Closing connection due to server request.");
234 }
235 }
236
237 return true;
238}
239
240bool ConnectionManager::shutdownServer()
241{
242 while( !lActive.empty() )
243 {
244 Connection *i = *(lActive.begin());
245 if( i->isActive() )
246 {
247 pMonitor->onClosedConnection( i );
248 i->close();
249 lInactive.insert( lInactive.end(), i );
250 lActive.erase( lActive.begin() );
251 }
252 }
253/*
254 for( int i = 0; i < nPoolSize; i++ )
255 {
256
257 int prt = axConPool[i].getSocket();
258 close( prt );
259// FD_CLR( prt, &fdActive );
260 pMonitor->onClosedConnection( &axConPool[i] );
261 axConPool[i].close();
262 }
263*/
264 std::map<int,int>::iterator i;
265 for( i = sMasterSocket.begin(); i != sMasterSocket.end(); i++ )
266 {
267 int nSocket = (*i).first;
268 shutdown( nSocket, SHUT_RDWR );
269 close( nSocket );
270 }
271
272 return true;
273}
274
275bool ConnectionManager::broadcastMessage( const char *lpData, int nExcludeSocket )
276{
277 std::list<Connection *>::const_iterator i;
278 for( i = lActive.begin(); i != lActive.end(); i++ )
279 {
280 if( (*i)->isActive() &&
281 (*i)->getSocket() != nExcludeSocket )
282 {
283 (*i)->appendOutput( lpData );
284 }
285 }
286
287 return true;
288}
289
290bool ConnectionManager::addConnection( int nSocket )
291{
292 struct sockaddr_in clientname;
293 size_t size;
294 int newSocket;
295
296 size = sizeof( clientname );
297#ifdef __CYGWIN__
298 newSocket = accept( nSocket, (struct sockaddr *) &clientname, (int *)&size );
299#else
300 newSocket = accept( nSocket, (struct sockaddr *) &clientname, &size );
301#endif
302 if( newSocket < 0 )
303 {
304 xLog.LineLog( MultiLog::LError, "Error accepting a new connection!" );
305 return false;
306 }
307// char *tmpa = inet_ntoa(clientname.sin_addr);
308 char tmpa[20];
309 inet_ntop( AF_INET, (void *)&clientname.sin_addr, tmpa, 20 );
310 xLog.LineLog( MultiLog::LStatus, "New connection from host %s, port %hd.", tmpa, ntohs (clientname.sin_port) );
311/*
312 int nCnt = 0;
313 for( int j = 0; j < nPoolSize; j++ )
314 {
315 if( axConPool[j].isActive() )
316 {
317 nCnt++;
318 }
319 }
320 xLog.LineLog( MultiLog::LStatus, "Connections %d/%d.", nCnt, nPoolSize );
321 */
322// free( tmpa );
323 FD_SET( newSocket, &fdActive );
324
325 //void nonblock(socket_t s)
326 {
327 int flags;
328
329 flags = fcntl(newSocket, F_GETFL, 0);
330 flags |= O_NONBLOCK;
331 if (fcntl(newSocket, F_SETFL, flags) < 0)
332 {
333 return false;
334 }
335 }
336
337 Connection *pCon = getInactiveConnection();
338 pCon->open( newSocket );
339
340 pMonitor->onNewConnection( pCon, (*sMasterSocket.find(nSocket)).second );
341 if( pCon->getProtocol() )
342 pCon->getProtocol()->onNewConnection();
343
344 lActive.insert( lActive.end(), pCon );
345
346 return true;
347}
348
349void ConnectionManager::connect(
350 const char *lpAddress,
351 int nPort,
352 int nProtocolPort,
353 Protocol *pNewProto
354 )
355{
356 Connection *pCon = getInactiveConnection();
357 pCon->open( lpAddress, nPort );
358 int nSocket = pCon->getSocket();
359 FD_SET( nSocket, &fdActive );
360
361 pCon->setProtocol( pNewProto );
362 pMonitor->onNewClientConnection( pCon, nProtocolPort );
363 if( pCon->getProtocol() )
364 pCon->getProtocol()->onNewClientConnection();
365
366 lActive.insert( lActive.end(), pCon );
367}
368
369Connection *ConnectionManager::getInactiveConnection()
370{
371 if( lInactive.empty() )
372 {
373 return new Connection();
374 }
375 Connection *pCon = *(lInactive.begin());
376 lInactive.erase( lInactive.begin() );
377 return pCon;
378}
379
380Connection *ConnectionManager::findActiveConnection( int nSocket )
381{
382 std::list<Connection *>::const_iterator i;
383 for( i = lActive.begin(); i != lActive.end(); i++ )
384 {
385 if( (*i)->getSocket() == nSocket )
386 {
387 return *i;
388 }
389 }
390
391 return NULL;
392}
393
394void ConnectionManager::setConnectionMonitor( ConnectionMonitor *pNewMonitor )
395{
396 pMonitor = pNewMonitor;
397}
diff --git a/src/old/connectionmanager.h b/src/old/connectionmanager.h
deleted file mode 100644
index cff036b..0000000
--- a/src/old/connectionmanager.h
+++ /dev/null
@@ -1,169 +0,0 @@
1/**
2 *@file
3 * Contains the ConnectionManager.
4 *@author Mike Buland
5 */
6
7#ifndef CONNECTIONMANAGER_H
8#define CONNECTIONMANAGER_H
9
10#include "multilog.h"
11#include "connection.h"
12#include "connectionmonitor.h"
13#include <sys/types.h>
14#include <list>
15#include <map>
16
17/** Manges incoming network connections as a server. Creates and works with
18 * Connection objects. All operations are performed on TCP/IP v4 right now,
19 * and on a single port, although any number of connections can be handled.
20 *@author Mike Buland
21 */
22class ConnectionManager
23{
24public:
25 /**
26 * Sets up the basics, like storage for the pool, and so on. This does not
27 * actually start a server, bind to a port, or create a connection pool.
28 * That's all handled by startServer().
29 */
30 ConnectionManager( int nInitPool=40 );
31
32 /**
33 * Cleans up everything, and even clears out all still-connected Connection
34 * objects.
35 */
36 virtual ~ConnectionManager();
37
38 /**
39 * Starts a server socket and binds to it, listening for new connections.
40 * Unlike the version of this that takes two parameters, this listens on
41 * all local addresses, or the virtual 0.0.0.0 address if available, which
42 * is mapped to all active local addresses.
43 *@param nPort The port to listen on.
44 *@returns True if the socket was bound to the port and serving was
45 * started. False if there was a problem connecting to the port.
46 */
47 bool startServer( int nPort );
48
49 /**
50 * Starts a server socket and binds to it, listening only on the address
51 * specified. If you want to listen to all local addresses you can enter
52 * "0.0.0.0" for the address, but the version of this with one parameter
53 * is more universal.
54 *@param sAddr The local ip address to bind to
55 *@param nPort The port to listen on.
56 *@returns True if the socket was bound to the port and serving was
57 * started. False if there was a problem connecting to the port.
58 */
59 bool startServer( const char *sAddr, int nPort );
60
61 /**
62 * I recomend probably not using this function on your own too much, it
63 * does the real work of setting up a socket, but requires a properly
64 * prepared sackaddr_in structure. This isn't too hard, but it's easier
65 * to use the other startServer functions. They call this function after
66 * some prepwork.
67 *@param name A properly formed sockaddr_in structure that will not be
68 * modified, but describes how to listen and to what to listen.
69 *@returns True on success.
70 */
71 bool startServer( struct sockaddr_in &name );
72
73 /**
74 * This is identicle to the simpler startServer function except that it
75 * will automatically try to connect multiple times in case the first
76 * attempt or two doesn't work for some reason. Initially this was
77 * written to compensate for server sockets staying locked after they were
78 * closed for a while.
79 *@param nPort The port to listen on.
80 *@param nInitPool The size of the initial connection pool. This will
81 * grow automatically if necesarry.
82 *@param nNumTries The maximum number of times to try to connect.
83 *@param nTimeout The amount of time to wait in-between connection
84 * attempts.
85 *@returns True if the socket was bound to the port and serving was
86 * started. False if there was a problem connecting to the port.
87 */
88 bool startServer( int nPort, int nNumTries, int nTimeout );
89
90 /**
91 * Scans all open connections, halting the calling processes until data
92 * is received or nTimeout ms have gone by. While waiting for the timeout
93 * to complete the process is placed into an idle mode.
94 *@param nTimeout The number of millisecconds to wait if there is nothing
95 * to actually do.
96 *@param bForceTimeout If set to true, this will force the scanner to wait
97 * for the timout to complete before returning, even if there was pending
98 * data.
99 */
100 bool scanConnections( int nTimeout, bool bForceTimeout );
101
102 /** Shutdown the server and all assosiated sockets.
103 *@returns True if every socket was closed without problem.
104 */
105 bool shutdownServer();
106
107 /** Sends a message directly to every connected port.
108 *@param lpData A null-terminated string of data to send.
109 *@param nExcludeSocket An optional socket to exclude from the broadcast.
110 *@returns True if every socket that should have gotten the message did.
111 */
112 bool broadcastMessage( const char *lpData, int nExcludeSocket=-1 );
113
114 /** Sets a monitor for the manager. The monitor is sent notifications
115 * whenever a socket is connected, disconnected, or whenever an error
116 * occurs.
117 *@param pNewMonitor A pointer to a preconstructed ConnectionMonitor
118 */
119 void setConnectionMonitor( ConnectionMonitor *pNewMonitor );
120
121 void connect( const char *lpAddress, int nPort, int nProtocolPort, Protocol *pNewProto );
122
123private:
124 /**
125 * Take care of the work of actually accepting a connection. This will
126 * accept the connection, set the initial modes, and add it to the master
127 * list of active connections, as well as fire off any messages that need
128 * to be handled by anything else.
129 *@param nSocket The handle of the listening socket that had an incoming
130 * connection.
131 *@returns True if everything worked, False otherwise.
132 */
133 bool addConnection( int nSocket );
134
135 /**
136 * Seraches the internal lists of connections for one with a specific
137 * socket.
138 *@param nSocket The socket the connection is using for communication.
139 * This is the unique socket and not the one that the connection was
140 * initially to.
141 *@returns NULL if no connection was found, otherwise a pointer to a live
142 * Connection object.
143 */
144 Connection *findActiveConnection( int nSocket );
145
146 /**
147 * Searches the connection pool for an object that isn't in use yet, and
148 * returns it, ready to be filled in and used.
149 *@returns An unused connection object ready for use.
150 *@todo Check this code over to insure that the pool grows appropriately
151 * when enough extra connections are detected.
152 */
153 Connection *getInactiveConnection();
154
155 std::map<int,int> sMasterSocket;
156 //int nMasterSocket; /**< The listening or server socket. */
157 fd_set fdActive; /**< The active socket set. */
158 fd_set fdRead; /**< The sockets ready for a read. */
159 fd_set fdWrite; /**< The sockets ready for a write. */
160 fd_set fdException; /**< The sockets that have gotten errors. */
161 std::list<Connection *> lInactive; /**< The pool of inactive Connections */
162 std::list<Connection *> lActive; /**< The pool of active Connections */
163 MultiLog &xLog; /**< A handle to the active multilog. */
164
165 /** The ConnectionMonitor to notify of new connections. */
166 ConnectionMonitor *pMonitor;
167};
168
169#endif
diff --git a/src/old/connectionmonitor.cpp b/src/old/connectionmonitor.cpp
deleted file mode 100644
index 4f90ee6..0000000
--- a/src/old/connectionmonitor.cpp
+++ /dev/null
@@ -1,10 +0,0 @@
1#include "connectionmonitor.h"
2
3ConnectionMonitor::ConnectionMonitor()
4{
5}
6
7ConnectionMonitor::~ConnectionMonitor()
8{
9}
10
diff --git a/src/old/connectionmonitor.h b/src/old/connectionmonitor.h
deleted file mode 100644
index 9910556..0000000
--- a/src/old/connectionmonitor.h
+++ /dev/null
@@ -1,47 +0,0 @@
1/**@file
2 * Describes the ConnectionMonitor class.
3 */
4#ifndef CONNECTIONMONITOR_H
5#define CONNECTIONMONITOR_H
6
7#include "connection.h"
8
9/** Connection Monitor defines the base class of the objects that will be
10 * notified whenever a connection is created or destroyed.
11 *@author Mike Buland
12 */
13class ConnectionMonitor
14{
15public:
16 /**
17 * This is only here for completeness. It does nothing.
18 */
19 ConnectionMonitor();
20
21 /**
22 * This is only here for completeness. It does nothing.
23 */
24 virtual ~ConnectionMonitor();
25
26 /** Receives the notification that new connection was received.
27 *@param pCon The connection that was created.
28 *@param nSocket The socket that the client connected to, used to determine
29 * which protocol to apply.
30 *@returns Should return a true value if everything is OK, a false to
31 * force a shutdown.
32 */
33 virtual bool onNewConnection( Connection *pCon, int nPort ) = 0;
34 virtual bool onNewClientConnection( Connection *pCon, int nPort )
35 {
36 return onNewConnection( pCon, nPort );
37 };
38
39 /** Receives the notification that a connection was closed.
40 *@param pCon The connection that was closed.
41 *@returns Should return a true value if everything is OK, a false to
42 * force a shutdown.
43 */
44 virtual bool onClosedConnection( Connection *pCon ) = 0;
45};
46
47#endif
diff --git a/src/old/flexbuf.cpp b/src/old/flexbuf.cpp
deleted file mode 100644
index 6d55294..0000000
--- a/src/old/flexbuf.cpp
+++ /dev/null
@@ -1,229 +0,0 @@
1#include "flexbuf.h"
2#include <string.h>
3
4FlexBuf::FlexBuf()
5{
6 lpBuf = new char[1024];
7 nLastChar = 0;
8 nFirstChar = 0;
9 nSize = 1024;
10 nFill = 0;
11 clearData();
12}
13
14FlexBuf::~FlexBuf()
15{
16 delete[] lpBuf;
17}
18
19bool FlexBuf::appendData( const char *lpData, int nDSize )
20{
21 int nStrLen;
22 if( nDSize < 0 )
23 {
24 nStrLen = strlen( lpData );
25 }
26 else
27 {
28 nStrLen = nDSize;
29 }
30
31 if( nLastChar + nStrLen + 1 > nSize )
32 {
33 if( nFill + nStrLen + 1 < nSize )
34 {
35 memcpy( lpBuf, lpBuf+nFirstChar, nFill );
36 nLastChar -= nFirstChar;
37 nFirstChar = 0;
38 }
39 else
40 {
41 nSize += nStrLen+1;
42 char *lpNewBuf = new char[nSize];
43 memcpy( lpNewBuf, lpBuf+nFirstChar, nFill );
44 delete[] lpBuf;
45 lpBuf = lpNewBuf;
46 nLastChar -= nFirstChar;
47 nFirstChar = 0;
48 }
49 }
50
51 memcpy( &lpBuf[nLastChar], lpData, nStrLen );
52 nLastChar += nStrLen;
53 nFill += nStrLen;
54 lpBuf[nLastChar] = '\0';
55
56 return true;
57}
58
59bool FlexBuf::appendData( const char lData )
60{
61 if( nLastChar + 2 > nSize )
62 {
63 if( nFill+2 < nSize )
64 {
65 memcpy( lpBuf, lpBuf+nFirstChar, nFill );
66 nLastChar -= nFirstChar;
67 nFirstChar = 0;
68 }
69 else
70 {
71 nSize += 1024;
72 char *lpNewBuf = new char[nSize];
73 memcpy( lpNewBuf, lpBuf+nFirstChar, nFill );
74 delete[] lpBuf;
75 lpBuf = lpNewBuf;
76 nLastChar -= nFirstChar;
77 nFirstChar = 0;
78 }
79 }
80
81 lpBuf[nLastChar] = lData;
82 nLastChar++;
83 nFill++;
84 lpBuf[nLastChar] = '\0';
85
86 return true;
87}
88
89bool FlexBuf::appendData( const short lData )
90{
91 return appendData( (const char *)&lData, sizeof(short) );
92}
93
94bool FlexBuf::appendData( const int lData )
95{
96 return appendData( (const char *)&lData, sizeof(int) );
97}
98
99bool FlexBuf::appendData( const long lData )
100{
101 return appendData( (const char *)&lData, sizeof(long) );
102}
103
104bool FlexBuf::appendData( const float lData )
105{
106 return appendData( (const char *)&lData, sizeof(float) );
107}
108
109bool FlexBuf::appendData( const double lData )
110{
111 return appendData( (const char *)&lData, sizeof(double) );
112}
113
114bool FlexBuf::appendData( const unsigned char lData )
115{
116 return appendData( (const char)lData );
117}
118
119bool FlexBuf::appendData( const unsigned short lData )
120{
121 return appendData( (const char *)&lData, sizeof(short) );
122}
123
124bool FlexBuf::appendData( const unsigned long lData )
125{
126 return appendData( (const char *)&lData, sizeof(long) );
127}
128
129bool FlexBuf::appendData( const unsigned int lData )
130{
131 return appendData( (const char *)&lData, sizeof(int) );
132}
133
134bool FlexBuf::clearData()
135{
136 nFirstChar = nLastChar = nFill = 0;
137 lpBuf[nLastChar] = '\0';
138
139 return true;
140}
141
142const char *FlexBuf::getData()
143{
144 return (lpBuf+nFirstChar);
145}
146
147int FlexBuf::getLength()
148{
149 return nFill;
150}
151
152int FlexBuf::getCapacity()
153{
154 return nSize;
155}
156
157bool FlexBuf::usedData( int nAmount )
158{
159 // Remove from the end if negative
160 if( nAmount < 0 )
161 {
162 if( nFill+nAmount < 0 )
163 {
164 nFill = nFirstChar = nLastChar = 0;
165 return true;
166 }
167 nLastChar += nAmount;
168 nFill += nAmount;
169 return true;
170 }
171 if( nAmount > nFill )
172 {
173 nAmount = nSize;
174// return false;
175 }
176
177 //nLastChar -= nAmount;
178 nFirstChar += nAmount;
179 nFill -= nAmount;
180
181 if( nFill == 0 )
182 {
183 nFirstChar = nLastChar = 0;
184 }
185
186 //if( nLastChar > 0 )
187 //{
188 //memmove( lpBuf, &lpBuf[nAmount], nLastChar );
189 //}
190
191 return true;
192}
193
194int FlexBuf::findChar( char cTarget )
195{
196 for( int j = nFirstChar; j < nLastChar; j++ )
197 {
198 if( lpBuf[j] == cTarget )
199 {
200 return j;
201 }
202 }
203
204 return -1;
205}
206
207void FlexBuf::ensureCapacity( int nAmount )
208{
209 if( nLastChar + nAmount + 1 > nSize )
210 {
211 if( nFill + nAmount + 1 < nSize )
212 {
213 memcpy( lpBuf, lpBuf+nFirstChar, nFill );
214 nLastChar -= nFirstChar;
215 nFirstChar = 0;
216 }
217 else
218 {
219 nSize += nAmount+1;
220 char *lpNewBuf = new char[nSize];
221 memcpy( lpNewBuf, lpBuf+nFirstChar, nFill );
222 delete[] lpBuf;
223 lpBuf = lpNewBuf;
224 nLastChar -= nFirstChar;
225 nFirstChar = 0;
226 }
227 }
228}
229
diff --git a/src/old/flexbuf.h b/src/old/flexbuf.h
deleted file mode 100644
index 7d7f11a..0000000
--- a/src/old/flexbuf.h
+++ /dev/null
@@ -1,162 +0,0 @@
1/**\flexbuf.h
2 * Describes the FlexBuf class.
3 *@author Mike Buland
4 */
5
6#ifndef FLEXBUF_H
7#define FLEXBUF_H
8
9/** Stores any amount of data, but starts small, growing as necesarry.
10 * It is optimized to work with stream type situations, with data being
11 * added to the end while it is being taken from the begning.
12 *@todo Set this class up to auto-shrink back to a specified sized buffer each
13 * time it has shrunk below that for enough operations.
14 *@author Mike Buland
15 */
16class FlexBuf
17{
18public:
19 /**
20 * Construct a blank FlexBuf containing about 1k of buffer space.
21 */
22 FlexBuf();
23
24 /**
25 * Clean up the FlexBuf, delete all buffers.
26 */
27 virtual ~FlexBuf();
28
29 /** Appends a whole string of data to the buffer. The string
30 * must be null terminated.
31 *@param lpData The data to append to the buffer.
32 *@param nDSize The size of the data described by lpData. If this
33 * value is -1 lpData is treated as a null-terminated string.
34 *@returns True if no problems occured, false otherwise.
35 */
36 bool appendData( const char *lpData, int nDSize=-1 );
37
38 /** Appends a single character to the end of the buffer.
39 *@param lData The character to append to the buffer.
40 *@returns True if no problems occured, false otherwise.
41 */
42 bool appendData( const char lData );
43
44 /**
45 * Append the short to the buffer.
46 *@param lData The short to add to the buffer queue.
47 *@returns True if everything is ok, false otherwise.
48 */
49 bool appendData( const short lData );
50
51 /**
52 * Append the int to the buffer.
53 *@param lData The int to add to the buffer queue.
54 *@returns True if everything is ok, false otherwise.
55 */
56 bool appendData( const int lData );
57
58 /**
59 * Append the long to the buffer.
60 *@param lData The long to add to the buffer queue.
61 *@returns True if everything is ok, false otherwise.
62 */
63 bool appendData( const long lData );
64
65 /**
66 * Append the float to the buffer.
67 *@param lData The float to add to the buffer queue.
68 *@returns True if everything is ok, false otherwise.
69 */
70 bool appendData( const float lData );
71
72 /**
73 * Append the double to the buffer.
74 *@param lData The double to add to the buffer queue.
75 *@returns True if everything is ok, false otherwise.
76 */
77 bool appendData( const double lData );
78
79 /**
80 * Append the unsigned char to the buffer.
81 *@param lData The unsigned char to add to the buffer queue.
82 *@returns True if everything is ok, false otherwise.
83 */
84 bool appendData( const unsigned char lData );
85
86 /**
87 * Append the unsigned short to the buffer.
88 *@param lData The unsigned short to add to the buffer queue.
89 *@returns True if everything is ok, false otherwise.
90 */
91 bool appendData( const unsigned short lData );
92
93 /**
94 * Append the unsigned int to the buffer.
95 *@param lData The unsigned int to add to the buffer queue.
96 *@returns True if everything is ok, false otherwise.
97 */
98 bool appendData( const unsigned int lData );
99
100 /**
101 * Append the unsigned long to the buffer.
102 *@param lData The unsigned long to add to the buffer queue.
103 *@returns True if everything is ok, false otherwise.
104 */
105 bool appendData( const unsigned long lData );
106
107 /** Removes all pending data from the buffer.
108 *@returns True if no problems occured, false otherwise.
109 */
110 bool clearData();
111
112 /** Gets a pointer to the internal buffer, at the begining of the current
113 * data stream.
114 *@returns A pointer to the internal data buffer.
115 */
116 const char *getData();
117
118 /** Gets the length of the current buffer (how much data is really in the
119 * buffer, not it's current capacity, for that check getCapacity)
120 *@returns The length of the current buffer.
121 */
122 int getLength();
123
124 /** Gets the current capacity of the FlexBuf. If the size nears this value
125 * then the entire buffer is resized to accomidate more data.
126 *@returns The current capacity of the FlexBuf.
127 */
128 int getCapacity();
129
130 /**
131 * Removes nAmount bytes from the begning of the buffer. Actually, if
132 * nAmount happens to be negative it will remove tha absolute value of
133 * nValue bytes from the end of the buffer, like the old delData command.
134 *@param nAmount The number of bytes used.
135 *@returns True if everything was successful, false if there was an error.
136 */
137 bool usedData( int nAmount );
138
139 /** Finds the first instance of the given character in the buffer and
140 * returns an index to it.
141 *@param cTarget The character you're looking for.
142 *@returns The index of the first instance of the given character, or
143 * -1 if it just wasn't found.
144 */
145 int findChar( char cTarget );
146
147 void ensureCapacity( int nAmount );
148
149private:
150 /** The raw storage location of the FlexBuf. */
151 char *lpBuf;
152 /** The real size of the FlexBuf. */
153 int nSize;
154 /** Where the last char is. */
155 int nLastChar;
156 /** Where the first char is. */
157 int nFirstChar;
158 /** The amount of real data in the FlexBuf. This is effectively nLastChar-nFirstChar. */
159 int nFill;
160};
161
162#endif
diff --git a/src/old/formula.cpp b/src/old/formula.cpp
deleted file mode 100644
index cf63cf3..0000000
--- a/src/old/formula.cpp
+++ /dev/null
@@ -1,262 +0,0 @@
1#include "formula.h"
2
3subExceptionDef( ParseException );
4
5Formula::Formula()
6{
7 hVars["pi"] = M_PI;
8 hVars["e"] = M_E;
9
10 hFunc["sin"] = FuncSin();
11}
12
13Formula::~Formula()
14{
15}
16
17double Formula::run( char *sFormula )
18{
19 for(;;)
20 {
21 uint8_t tNum = nextToken( &sFormula );
22 if( tNum == symEOS )
23 break;
24 else if( tNum == symSubtract )
25 {
26 tNum = nextToken( &sFormula );
27 if( tNum != symNumber )
28 throw ParseException("Unary minus must be followed by a number, "
29 "variable, function, or parenthesis.");
30 sValue.top() = -sValue.top();
31 }
32 else if( tNum == symOpenParen )
33 {
34 sOper.push( tNum );
35 continue;
36 }
37
38oppart: uint8_t tOpr = nextToken( &sFormula );
39 if( tOpr == symEOS )
40 {
41 //printf("EOS ");
42 reduce();
43 return sValue.top();
44 break;
45 }
46 if( !sOper.empty() && getPrec( sOper.top() ) > getPrec( tOpr ) )
47 {
48 reduce();
49 }
50 if( tOpr != symCloseParen )
51 {
52 sOper.push( tOpr );
53 }
54 else
55 {
56 reduce( true );
57 goto oppart;
58 }
59 }
60 return sValue.top();
61}
62
63void Formula::reduce( bool bCloseParen )
64{
65 while( !sOper.empty() )
66 {
67 uint8_t nOpr = sOper.top();
68 if( nOpr == symOpenParen )
69 {
70 //printf("Found ( stopping reduction.\n");
71 if( bCloseParen == true )
72 sOper.pop();
73 return;
74 }
75 sOper.pop();
76
77 double dTop = sValue.top();
78 sValue.pop();
79
80 switch( nOpr )
81 {
82 case symAdd:
83 //printf("%f + %f = %f\n", sValue.top(), dTop, sValue.top()+dTop );
84 sValue.top() += dTop;
85 break;
86
87 case symSubtract:
88 //printf("%f - %f = %f\n", sValue.top(), dTop, sValue.top()-dTop );
89 sValue.top() -= dTop;
90 break;
91
92 case symMultiply:
93 //printf("%f * %f = %f\n", sValue.top(), dTop, sValue.top()*dTop );
94 sValue.top() *= dTop;
95 break;
96
97 case symDivide:
98 //printf("%f / %f = %f\n", sValue.top(), dTop, sValue.top()/dTop );
99 sValue.top() /= dTop;
100 break;
101
102 case symExponent:
103 //printf("%f ^ %f = %f\n", sValue.top(), dTop, pow(sValue.top(),dTop) );
104 sValue.top() = pow( sValue.top(), dTop );
105 break;
106
107 case symModulus:
108 //printf("%f %% %f = %f\n", sValue.top(), dTop, fmod(sValue.top(),dTop) );
109 sValue.top() = fmod( sValue.top(), dTop );
110 break;
111 }
112 }
113
114 if( bCloseParen == true )
115 {
116 throw ParseException("Close-paren found without matching open-paren.");
117 }
118}
119
120uint8_t Formula::getPrec( uint8_t nOper )
121{
122 switch( nOper )
123 {
124 case symNumber:
125 case symVariable:
126 case symOpenParen:
127 case symCloseParen:
128 return 0;
129
130 case symAdd:
131 case symSubtract:
132 return 1;
133
134 case symMultiply:
135 case symDivide:
136 case symModulus:
137 return 2;
138
139 case symExponent:
140 return 3;
141
142 default:
143 return 0;
144 }
145}
146
147uint8_t Formula::nextToken( char **sBuf )
148{
149 for(;;)
150 {
151 char cbuf = **sBuf;
152 ++(*sBuf);
153 switch( cbuf )
154 {
155 case '+':
156 return symAdd;
157
158 case '-':
159 return symSubtract;
160
161 case '*':
162 return symMultiply;
163
164 case '/':
165 return symDivide;
166
167 case '^':
168 return symExponent;
169
170 case '%':
171 return symModulus;
172
173 case '(':
174 return symOpenParen;
175
176 case ')':
177 return symCloseParen;
178
179 case ' ':
180 case '\t':
181 case '\n':
182 case '\r':
183 break;
184
185 case '\0':
186 return symEOS;
187
188 default:
189 if( cbuf == '.' || (cbuf >= '0' && cbuf <= '9') )
190 {
191 char num[50]={cbuf};
192 int nPos = 1;
193 bool bDot = false;
194
195 for(;;)
196 {
197 cbuf = **sBuf;
198 if( cbuf == '.' )
199 {
200 if( bDot == false )
201 bDot = true;
202 else
203 throw ParseException(
204 "Numbers cannot have more than one "
205 ". in them."
206 );
207 }
208 if( cbuf == '.' || (cbuf >= '0' && cbuf <= '9') )
209 {
210 num[nPos++] = cbuf;
211 }
212 else
213 {
214 num[nPos] = '\0';
215 sValue.push( strtod( num, NULL ) );
216 return symNumber;
217 }
218 ++(*sBuf);
219 }
220 }
221 else if( (cbuf >= 'a' && cbuf <= 'z') ||
222 (cbuf >= 'A' && cbuf <= 'Z') ||
223 (cbuf == '_') )
224 {
225 char tok[50]={cbuf};
226 int nPos = 1;
227
228 for(;;)
229 {
230 cbuf = **sBuf;
231 if( (cbuf >= 'a' && cbuf <= 'z') ||
232 (cbuf >= 'A' && cbuf <= 'Z') ||
233 (cbuf >= '0' && cbuf <= '9') ||
234 cbuf == '_' || cbuf == '.' || cbuf == ':' )
235 {
236 tok[nPos++] = cbuf;
237 }
238 else
239 {
240 tok[nPos] = '\0';
241 //printf("Checking variable \"%s\"\n", tok );
242 try
243 {
244 sValue.push( hVars[tok] );
245 return symNumber;
246 }
247 catch( HashException &e )
248 {
249 throw ParseException(
250 "No variable named \"%s\" exists.",
251 tok
252 );
253 }
254 }
255 ++(*sBuf);
256 }
257 }
258 break;
259 }
260 }
261}
262
diff --git a/src/old/formula.h b/src/old/formula.h
deleted file mode 100644
index 939eb09..0000000
--- a/src/old/formula.h
+++ /dev/null
@@ -1,77 +0,0 @@
1#ifndef FORMULA_H
2#define FORMULA_H
3
4#include <stdint.h>
5
6#include <math.h>
7#include <stack>
8#include "sbuffer.h"
9
10#include "exceptionbase.h"
11#include "hash.h"
12
13subExceptionDecl( ParseException );
14
15/**
16 * Implements a very simple formula parser that allows use of variables and
17 * custom functions. This is based on a simple calculator-type parser that
18 * executes as it processes, accounting for operator precedence and grouping.
19 */
20class Formula
21{
22public:
23 Formula();
24 virtual ~Formula();
25
26 double run( char *sFormula );
27
28 typedef Hash<std::string, double> varHash;
29 varHash hVars;
30
31 typedef struct Func
32 {
33 double operator()( double x )
34 {
35 return 0.0;
36 }
37 } Func;
38
39 typedef Hash<std::string, Func> funcHash;
40 funcHash hFunc;
41
42 typedef struct FuncSin : Func
43 {
44 double operator()( double x )
45 {
46 return sin( x );
47 }
48 } FuncSin;
49
50private:
51 enum
52 {
53 symEOS,
54 symAdd,
55 symSubtract,
56 symMultiply,
57 symDivide,
58 symOpenParen,
59 symCloseParen,
60 symNumber,
61 symVariable,
62 symExponent,
63 symModulus
64 };
65
66 typedef uint8_t symType;
67
68 std::stack<symType> sOper;
69 std::stack<double> sValue;
70
71private:
72 symType getPrec( symType nOper );
73 symType nextToken( char **sBuf );
74 void reduce( bool bCloseParen = false );
75};
76
77#endif
diff --git a/src/old/http.cpp b/src/old/http.cpp
deleted file mode 100644
index df7dafe..0000000
--- a/src/old/http.cpp
+++ /dev/null
@@ -1,377 +0,0 @@
1#include <string.h>
2#include <stdlib.h>
3#include "http.h"
4#include "hashfunctionstring.h"
5
6Http::Http( Connection *pConnection ) : hReqHeader( new HashFunctionString(), 100 )
7{
8 pCon = pConnection;
9 nParseState = parseInit;
10}
11
12Http::~Http()
13{
14 for( int j = 0; j < lStrings.getSize(); j++ )
15 {
16 delete (std::string *)lStrings[j];
17 }
18}
19
20bool Http::parseRequest()
21{
22 for(;;)
23 {
24 pCon->readInput();
25 switch( nParseState )
26 {
27 case parseInit:
28 {
29 int nLen = pCon->scanInputFor( CR );
30 if( nLen == -1 )
31 {
32 return false;
33 }
34 else
35 {
36 nReqType = getRequestType( pCon->getInput() );
37 pCon->usedInput( pCon->scanInputFor(' ')+1 );
38
39 nLen = pCon->scanInputFor(' ');
40 sReqURI.append( pCon->getInput(), nLen );
41 pCon->usedInput( nLen+1 );
42
43 if( !strncmp( pCon->getInput(), "HTTP/", 5 ) )
44 {
45 char mbuf[2]={'\0','\0'};
46 unsigned char major, minor;
47
48 pCon->usedInput( 5 );
49 mbuf[0] = pCon->getInput()[0];
50 major = (unsigned char)atoi(mbuf);
51 mbuf[0] = pCon->getInput()[2];
52 minor = (unsigned char)atoi(mbuf);
53 setRequestVersion( major, minor );
54 if( checkRequestVer() )
55 {
56 nParseState = parseHeader;
57 }
58 else
59 {
60 setResponseStatus( statusHTTPVersionNotSupported );
61 //printf("Verson not supported.\n");
62 return true;
63 }
64
65 pCon->usedInput( 5 );
66 }
67 else
68 {
69 setResponseStatus( statusBadRequest );
70 }
71
72 //return false;
73 }
74 }
75 break;
76
77 case parseHeader:
78 {
79 int nLen = pCon->scanInputFor( CR );
80 //printf("nLen = %d: :::%s:::\n", nLen, pCon->getInput() );
81 if( nLen == -1 )
82 {
83 pCon->readInput( 1, 0);
84 }
85 else if( nLen == 0 )
86 {
87 // We've got our double-newline, time for content.
88 pCon->usedInput( 2 );
89 setResponseStatus( statusOK );
90 return true;
91 }
92 else
93 {
94 nLen = pCon->scanInputFor(':');
95 if( nLen == -1 )
96 {
97 //printf("No colon? what are you trying to pull?\n");
98 }
99 else
100 {
101 std::string *pName = new std::string( pCon->getInput(), nLen );
102 lStrings.append( pName );
103 pCon->usedInput( nLen+1 );
104
105 nLen = pCon->scanInputFor( CR );
106 std::string *pValue = convSpaceString( pCon->getInput(), nLen );
107 lStrings.append( pValue );
108 pCon->usedInput( nLen+2 );
109
110 hReqHeader.insert(
111 pName->c_str(),
112 pValue->c_str()
113 );
114
115 //printf("::%s = \"%s\"\n",
116 // pName->c_str(),
117 // pValue->c_str()
118 // );
119 }
120 }
121 }
122 break;
123
124 case parseFinished:
125 break;
126 }
127 }
128}
129
130bool Http::buildResponse( short nResponseCode, const char *sResponse )
131{
132 if( nResponseCode > 0 )
133 {
134 nResStatus = nResponseCode;
135 }
136
137 if( sResponse == NULL )
138 {
139 sResStatusStr = "uh yeah";
140 }
141 else
142 {
143 sResStatusStr = sResponse;
144 }
145
146 time_t curTime;
147 time( &curTime );
148 gmtime_r( &curTime, &tResTime );
149
150 sServerStr = "libbu++ Http/0.0.1";
151 bResPersistant = false;
152
153 //char buf[30];
154 //strftime( buf, 30, "%a, %d %b %Y %H:%M:%S GMT", &tResponseTime );
155
156 return true;
157}
158
159bool Http::sendResponse()
160{
161 char buf[256];
162
163 sprintf( buf, "HTTP/1.1 %d %s\r\n", nResStatus, sResStatusStr.c_str() );
164 pCon->appendOutput( buf );
165
166 strftime( buf, 256, "Date: %a, %d %b %Y %H:%M:%S GMT\r\n", &tResTime );
167 pCon->appendOutput( buf );
168
169 sprintf( buf, "Server: %s\r\n", sServerStr.c_str() );
170 pCon->appendOutput( buf );
171
172 if( bResPersistant )
173 {
174 }
175 else
176 {
177 pCon->appendOutput("Connection: close\r\n");
178 }
179
180 sprintf( buf, "Content-Type: %s\r\n", sResMime.c_str() );
181 pCon->appendOutput( buf );
182
183 sprintf( buf, "Content-Length: %d\r\n", sResContent.size() );
184 pCon->appendOutput( buf );
185
186 pCon->appendOutput("\r\n");
187
188 pCon->appendOutput( sResContent.c_str(), sResContent.size() );
189
190 return true;
191}
192
193void Http::setResponsePersistant( bool bPersistant )
194{
195 bResPersistant = bPersistant;
196}
197
198void Http::setResponseContent( const char *sMime, const char *sContent, int nLen )
199{
200 sResMime = sMime;
201 sResContent.erase();
202 sResContent.append( sContent, nLen );
203}
204
205std::string *Http::convSpaceString( const char *sStr, int nLen )
206{
207 int nNewLen = 0;
208 bool bStart = true;
209 bool bSpace = false;
210
211 for( int j = 0; j < nLen; j++ )
212 {
213 if( sStr[j] == ' ' || sStr[j] == '\t' )
214 {
215 if( bStart )
216 {
217 }
218 else if( bSpace == false )
219 {
220 bSpace = true;
221 nNewLen++;
222 }
223 }
224 else
225 {
226 bStart = false;
227 bSpace = false;
228 nNewLen++;
229 }
230 }
231 if( bSpace )
232 {
233 nNewLen--;
234 }
235
236 std::string *pSStr = new std::string;
237 //char *pStr = pSStr->c_str();
238 nNewLen = 0;
239 bStart = true;
240 bSpace = false;
241
242 for( int j = 0; j < nLen; j++ )
243 {
244 if( sStr[j] == ' ' || sStr[j] == '\t' )
245 {
246 if( bStart )
247 {
248 }
249 else if( bSpace == false )
250 {
251 bSpace = true;
252 *pSStr += ' ';
253 //pStr[nNewLen++] = ' ';
254 }
255 }
256 else
257 {
258 bStart = false;
259 bSpace = false;
260 *pSStr += sStr[j];
261 //pStr[nNewLen++] = sStr[j];
262 }
263 }
264 if( bSpace == true )
265 {
266 nNewLen--;
267// pStr[nNewLen] = '\0';
268 }
269
270 return pSStr;
271}
272
273const char *Http::getRequestURI()
274{
275 return sReqURI.c_str();
276}
277
278short Http::getRequestType( const char *sType )
279{
280 if( !strncmp( sType, "OPTIONS", 7 ) )
281 {
282 return reqOptions;
283 }
284 else if( !strncmp( sType, "GET", 3 ) )
285 {
286 return reqGet;
287 }
288 else if( !strncmp( sType, "HEAD", 4 ) )
289 {
290 return reqHead;
291 }
292 else if( !strncmp( sType, "POST", 4 ) )
293 {
294 return reqPost;
295 }
296 else if( !strncmp( sType, "PUT", 3 ) )
297 {
298 return reqPut;
299 }
300 else if( !strncmp( sType, "DELETE", 6 ) )
301 {
302 return reqDelete;
303 }
304 else if( !strncmp( sType, "TRACE", 5 ) )
305 {
306 return reqTrace;
307 }
308 else if( !strncmp( sType, "CONNECT", 7 ) )
309 {
310 return reqConnect;
311 }
312 else
313 {
314 printf(" Uh oh, extension!\n");
315 return reqExtension;
316 }
317}
318
319const char *Http::getRequestType( short nType )
320{
321 switch( nType )
322 {
323 case reqOptions: return "OPTIONS";
324 case reqGet: return "GET";
325 case reqHead: return "HEAD";
326 case reqPost: return "POST";
327 case reqPut: return "PUT";
328 case reqDelete: return "DELETE";
329 case reqTrace: return "TRACE";
330 case reqConnect: return "CONNECT";
331 case reqExtension: return "EXTENSION";
332 default: return "INVALID VALUE";
333 }
334}
335
336short Http::getRequestType()
337{
338 return nReqType;
339}
340
341const char *Http::getRequestTypeStr()
342{
343 return getRequestType( nReqType );
344}
345
346void Http::setResponseStatus( short nStatus )
347{
348 nResStatus = nStatus;
349}
350
351void Http::setRequestVersion( unsigned char nMajor, unsigned char nMinor )
352{
353 cReqVersion = (nMajor<<4)|nMinor;
354}
355
356unsigned char Http::getRequestMinorVer()
357{
358 return cReqVersion&0x0F;
359}
360
361unsigned char Http::getRequestMajorVer()
362{
363 return cReqVersion>>4;
364}
365
366bool Http::checkRequestVer()
367{
368 if( cReqVersion == HTTP11 )
369 return true;
370 return false;
371}
372
373const char *Http::getHeader( const char *lpStr )
374{
375 return (const char *)hReqHeader[lpStr];
376}
377
diff --git a/src/old/http.h b/src/old/http.h
deleted file mode 100644
index 7e9f9a0..0000000
--- a/src/old/http.h
+++ /dev/null
@@ -1,273 +0,0 @@
1/**\file http.h
2 * Describe a Hyper Text Transfer Protocol processor. This class will allow
3 * any program to act as either an HTTP server, client, or both. It contains
4 * a number of additional helpers and subclasses.
5 *@author Mike Buland
6 */
7
8#ifndef HTTP_H
9#define HTTP_H
10
11#include <iostream>
12#include "connection.h"
13#include "linkedlist.h"
14#include "hashtable.h"
15
16#define CR '\r' /**< The ASCII value of a Carrage Return */
17#define LF '\n' /**< The ASCII value of a Line Feed */
18#define CRLF CR LF /**< Combo of CR+LF for use in http */
19
20/**
21 * Macro to create combined http version codes. This just makes processing a
22 * little bit faster for the most part.
23 *@param maj Major version number, between 0 and 15
24 *@param min Minor version number, between 0 and 15
25 *@returns A one byte combined version number suitable for use in switches.
26 */
27#define HTTPVER( maj, min ) ((maj<<4)|(min))
28
29#define HTTP10 HTTPVER( 1, 0 ) /**< Combined version code for http 1.0 */
30#define HTTP11 HTTPVER( 1, 1 ) /**< Combined version code for http 1.1 */
31
32/**
33 * This is the master HTTP processing class. One instance handles one
34 * transaction, in the future a different mechanism may be thought up, but for
35 * now this means that you must create multiple objects to handle a single
36 * connection that contains multiple requests.
37 * In the constructor the Http class is given a connection object. This object
38 * should already be initialized and connected to whatever socket it wants to
39 * be sending and receiving data to and from. Once that's done you can call
40 * parseRequest if you're acting as a server, or a variety of buildRequest
41 * functions to create and send a request if you're a client.
42 * Please note that this class does not provide any HTTP or extended format
43 * processing systems, but will allow for mime types tables to be registered.
44 *@author Mike Buland
45 */
46class Http
47{
48public:
49 /**
50 * Create an Http object tied to an existing connection object.
51 *@param pConnection The live connection object to deal with.
52 */
53 Http( Connection *pConnection );
54
55 /**
56 * Standard Deconstructor.
57 */
58 virtual ~Http();
59
60 /**
61 * Perform all parsing needed to figure out what an HTTP client wants from
62 * us. This will setup a number of properties in the Http object itself
63 * and has the possibility of setting one or more response states initially.
64 * These states should be checked for immediately after parsing to see if
65 * an appropriate error message should be generated. These errors can
66 * include issues with protocol, data formats, or unknown versions of the
67 * protocol.
68 *@returns True means that all processing is finished, false means that
69 * the parseRequest function should be called again when more data is
70 * ready. A return value of true does not indicate success, only that
71 * processing is finished, the getResponseStatus function should be called
72 * to see what status was set in the parse routine. A 200 indicates that
73 * as far as the parser is concerned, everything when smoothly. Otherwise
74 * it's your responsibility to build the appropriate error response body
75 * (like an html file) and send it as the response.
76 */
77 bool parseRequest();
78
79 /**
80 * Get a request type's internal Http object id based on the string
81 * representation. These can be any HTTP/1.1 standard request type.
82 *@param sType The string that should be checked for type. This is in all
83 * caps, just like if it came from the HTTP client, which is most often
84 * the case.
85 *@returns The numerical ID of the given request type. Please note that
86 * HTTP/1.1 standard specifies that any string is valid here as long as
87 * the non-basic string is a request type understood by the serving
88 * software. This means that anything that is non-standard will return
89 * a type reqExtension and not an error. This is not a mistake.
90 */
91 short getRequestType( const char *sType );
92
93 /**
94 * Get the string representation of an Http object request type integer ID.
95 * This is used mainly for debugging to be sure the system has what we
96 * think it has.
97 *@param nType The integer ID of the request type to process.
98 *@returns The HTTP/1.1 string representation of that Http object ID code.
99 */
100 const char *getRequestType( short nType );
101
102 /**
103 * Returns the Http object request type ID code that is stored in the
104 * object by either the parseRequest function or use of the buildRequest
105 * functions.
106 *@returns The ID of the request type stored in the object.
107 */
108 short getRequestType();
109
110 /**
111 * Same as getRequestType, only returns the string representation.
112 *@returns The string representation of the request type ID stored in the
113 * object.
114 */
115 const char *getRequestTypeStr();
116
117 /**
118 * Sets the version of the request used by the system. This will be used
119 * by parse request, but is also part of the buildRequest tool functions.
120 *@param nMajor The major version number.
121 *@param nMinor The minor version number.
122 */
123 void setRequestVersion( unsigned char nMajor, unsigned char nMinor );
124
125 /**
126 * Gets the major version number of the protocol used/to be used in this
127 * request.
128 *@returns The major version number of the request protocol.
129 */
130 unsigned char getRequestMinorVer();
131
132 /**
133 * Gets the minor version number of the protocol used/to be used in this
134 * request.
135 *@returns The minor version number of the request protocol.
136 */
137 unsigned char getRequestMajorVer();
138
139 /**
140 * Checks the stored request version against an internal table of supported
141 * protocol versions.
142 *@returns True if the protocol version is supported, false otherwise.
143 */
144 bool checkRequestVer();
145
146 /**
147 * Converts an arbitrary string to a new string object with space saving
148 * operations performed ala the HTTP/1.1 specs. All leading and trailing
149 * whitespace is stripped, and all whitespace within the string is reduced
150 * to a single space char.
151 *@param sStr A pointer to the string data to process.
152 *@param nLen The length of the string to process. Since this function is
153 * often called on stream data, there is no null terminator where we need
154 * one. This is here for convinience so the data doesn't need to be hacked
155 * up or moved to an intermediate buffer.
156 *@returns A new string that may well be shorter than the original but that
157 * will have the same value as far as the HTTP/1.1 specs are concerned.
158 */
159 std::string *convSpaceString( const char *sStr, int nLen );
160
161 /**
162 * Gets a string pointer to the URI that was/is being requested. This can
163 * be any RFC standard URI, with or without protocol and domain.
164 *@returns A pointer to the URI that was/is being requested.
165 */
166 const char *getRequestURI();
167
168 /**
169 * Set a new response status. This status can be anything that the HTTP
170 * specs allow. Other values are allowed as well, but beware, not all
171 * servers/clients will accept values that are not in the tables in this
172 * class.
173 *@param nStatus The status to set.
174 */
175 void setResponseStatus( short nStatus );
176
177 bool buildResponse( short nResponseCode=-1, const char *sResponse=NULL );
178 void setResponseContent( const char *sMime, const char *sContent, int nLen );
179 void setResponsePersistant( bool bPersistant );
180 bool sendResponse();
181
182 enum
183 {
184 reqOptions,
185 reqGet,
186 reqHead,
187 reqPost,
188 reqPut,
189 reqDelete,
190 reqTrace,
191 reqConnect,
192 reqExtension
193 };
194
195 enum
196 {
197 statusContinue = 100,
198 statusSwitchProto = 101,
199
200 statusOK = 200,
201 statusCreated = 201,
202 statusAccepted = 202,
203 statusNonAuthInfo = 203,
204 statusNoContent = 204,
205 statusResetContent = 205,
206 statusPartialContent = 206,
207
208 statusMultiChoices = 300,
209 statusMovedPermanently = 301,
210 statusFound = 302,
211 statusSeeOther = 303,
212 statusNotModified = 304,
213 statusUseProxy = 305,
214 statusUnused = 306,
215 statusTempRedirect = 307,
216
217 statusBadRequest = 400,
218 statusUnauthorized = 401,
219 statusPaymentRequired = 402,
220 statusForbidden = 403,
221 statusNotFound = 404,
222 statusMethodNotAllowed = 405,
223 statusNotAcceptable = 406,
224 statusProxyAuthRequired = 407,
225 statusRequestTimeout = 408,
226 statusConflict = 409,
227 statusGone = 410,
228 statusLengthRequired = 411,
229 statusPreconditionFailed = 412,
230 statusRequestEntityTooLarge = 413,
231 statusRequestURITooLong = 414,
232 statusUnsupportedMediaType = 415,
233 statusRequestedRangeNotSatisfiable = 416,
234 statusExpectationFailed = 417,
235
236 statusInternalServerError = 500,
237 statusNotImplemented = 501,
238 statusBadGateway = 502,
239 statusServiceUnavailable = 503,
240 statusGatewayTimeout = 504,
241 statusHTTPVersionNotSupported = 505
242 };
243
244 const char *getHeader( const char *lpStr );
245
246private:
247 Connection *pCon;
248 unsigned char nParseState;
249
250 short nReqType;
251 std::string *pReqStr;
252 std::string sReqURI;
253 unsigned char cReqVersion;
254 HashTable hReqHeader;
255 LinkedList lStrings;
256
257 std::string sServerStr;
258 std::string sResMime;
259 std::string sResContent;
260 std::string sResStatusStr;
261 bool bResPersistant;
262 struct tm tResTime;
263 short nResStatus;
264
265 enum
266 {
267 parseInit,
268 parseHeader,
269 parseFinished
270 };
271};
272
273#endif
diff --git a/src/old/httpget.cpp b/src/old/httpget.cpp
deleted file mode 100644
index ee1f29c..0000000
--- a/src/old/httpget.cpp
+++ /dev/null
@@ -1,263 +0,0 @@
1#include "httpget.h"
2#include "exceptions.h"
3#include "connection.h"
4#include <stdio.h>
5
6char HttpGet::hexcode[]={'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
7
8HttpGet::HttpGet() :
9 nPort( 80 ),
10 sUserAgent("libbu++; HttpGet")
11{
12}
13
14HttpGet::HttpGet( const std::string &url ) :
15 nPort( 80 )
16{
17 setURL( url );
18}
19
20HttpGet::~HttpGet()
21{
22}
23
24void HttpGet::setURL( const std::string &url )
25{
26 int len = url.size();
27 //printf("Full URL: %s\n", url.c_str() );
28 int pos = url.find("://");
29 sProto.assign( url, 0, pos );
30 //printf("Protocol: %s\n", sProto.c_str() );
31
32 int pos2 = url.find("/", pos+3 );
33 if( pos2 >= 0 )
34 {
35 sHost.assign( url, pos+3, pos2-pos-3 );
36 }
37 else
38 {
39 sHost.assign( url, pos+3, std::string::npos );
40 }
41
42 int pos3 = sHost.find(":");
43 if( pos3 >= 0 )
44 {
45 nPort = strtol( sHost.c_str()+pos3+1, NULL, 10 );
46 sHost.erase( pos3 );
47 }
48 //printf("Hostname: %s\n", sHost.c_str() );
49 //printf("Port: %d\n", nPort );
50
51 pos3 = url.find("?", pos2+1 );
52 if( pos3 >= 0 )
53 {
54 sPath.assign( url, pos2, pos3-pos2 );
55 //printf("Path: %s\n", sPath.c_str() );
56 for(;;)
57 {
58 int end = pos3+1;
59 for(; url[end] != '=' && url[end] != '&' && end < len; end++ );
60 std::string sKey, sValue;
61 sKey.assign( url, pos3+1, end-pos3-1 );
62 if( url[end] == '=' )
63 {
64 pos3 = end;
65 for( end++; url[end] != '&' && end < len; end++ );
66 sValue.assign( url, pos3+1, end-pos3-1 );
67 pos3 = end;
68 }
69 else
70 {
71 }
72 lParams.push_back( StringPair( sKey, sValue ) );
73 //printf("Param: %s = %s\n", sKey.c_str(), sValue.c_str() );
74 if( end+1 >= len ) break;
75 }
76 }
77 else
78 {
79 sPath.assign( url, pos2, std::string::npos );
80 //printf("Path: %s\n", sPath.c_str() );
81 }
82
83 //printf("\n");
84}
85
86void HttpGet::addParam( const std::string &key, const std::string &value )
87{
88 lParams.push_back( StringPair( key, value ) );
89}
90
91std::string HttpGet::escape( const std::string &src )
92{
93 std::string escaped("");
94 for( std::string::const_iterator i = src.begin(); i != src.end(); i++ )
95 {
96 unsigned char j = *i;
97 if( (j >= '0' && j <= '9') ||
98 (j >= 'a' && j <= 'z') ||
99 (j >= 'A' && j <= 'Z') ||
100 j == '$' ||
101 j == '-' ||
102 j == '_' ||
103 j == '.' ||
104 j == '+' ||
105 j == '!' ||
106 j == '*' ||
107 j == '\'' ||
108 j == '(' ||
109 j == ')' )
110 {
111 escaped += j;
112 }
113 else
114 {
115 escaped += "%";
116 escaped += hexcode[j>>4];
117 escaped += hexcode[j&0x0F];
118 }
119 }
120
121 return escaped;
122}
123
124SBuffer *HttpGet::get()
125{
126 std::string sData;
127 sData = "GET " + sPath;
128 if( !lParams.empty() )
129 {
130 sData += "?";
131 for( std::list<StringPair>::iterator i = lParams.begin();
132 i != lParams.end(); i++ )
133 {
134 if( i != lParams.begin() )
135 sData += "&";
136
137 if( (*i).second == "" )
138 {
139 sData += escape( (*i).first );
140 }
141 else
142 {
143 sData += escape( (*i).first );
144 sData += "=";
145 sData += escape( (*i).second );
146 }
147 }
148 }
149
150 sData += " HTTP/1.1\r\n"
151 "User-Agent: " + sUserAgent + "\r\n"
152 "Connection: close\r\n"
153 "Host: " + sHost + "\r\n"
154 "Content-type: application/x-www-form-urlencoded\r\n\r\n";
155
156 //printf("Connection content:\n\n%s\n\n", sData.c_str() );
157
158 Connection con;
159 //printf("Opening connection...\n");
160 con.open( sHost.c_str(), nPort );
161 {
162 int nSocket = con.getSocket();
163 fd_set rfds, wfds, efds;
164 int retval;
165
166 FD_ZERO(&rfds);
167 FD_SET(nSocket, &rfds);
168 FD_ZERO(&wfds);
169 FD_SET(nSocket, &wfds);
170 FD_ZERO(&efds);
171 FD_SET(nSocket, &efds);
172
173 struct timeval tv;
174 tv.tv_sec = 4;
175 tv.tv_usec = 0;
176
177 //printf("Selecting on socket, can we read, write, etc?\n");
178 retval = select( nSocket+1, &rfds, &wfds, &efds, &tv );
179 /*printf("About to write: sock=%d, r=%d, w=%d, e=%d, ret=%d\n",
180 nSocket,
181 FD_ISSET( nSocket, &rfds ),
182 FD_ISSET( nSocket, &wfds ),
183 FD_ISSET( nSocket, &efds ),
184 retval
185 );*/
186
187 if( retval == 0 )
188 {
189 //printf("Timeout on connection.\n");
190 con.close();
191 throw ExceptionBase("Connection Timeout on open.\n");
192 }
193
194 }
195 con.appendOutput( sData.c_str(), sData.size() );
196 //printf("Writing to socket...\n");
197 con.writeOutput();
198 //printf("Data written...\n");
199 int nSec = 5;
200 int nUSec = 0;
201 int nLastAmnt = con.getInputAmnt();
202 try
203 {
204 double dTotTime = 0.0;
205 //printf("About to read input...\n");
206 while( con.readInput( nSec, nUSec, &nSec, &nUSec ) )
207 {
208 if( nLastAmnt == con.getInputAmnt() )
209 {
210 if( nSec <= 0 && nUSec <= 0 )
211 {
212 //printf("out of time, closing up.\n");
213 con.close();
214 throw ExceptionBase("Connection Timeout.\n");
215 }
216 if( nSec == 5 && nUSec == 0 )
217 {
218 //printf("No new data, breaking.\n");
219 break;
220 }
221 }
222 else
223 {
224 dTotTime += (5.0-(nSec+nUSec/1000000.0));
225 printf("\rRead %db at %.2fkb/sec",
226 con.getInputAmnt(),
227 ((double)(con.getInputAmnt())/1024.0) / dTotTime
228 );
229 fflush( stdout );
230 nSec = 5;
231 nUSec = 0;
232 nLastAmnt = con.getInputAmnt();
233 }
234 }
235 }
236 catch( ConnectionException &e )
237 {
238 //con.close();
239 if( strcmp( e.what(), "Connection closed" ) )
240 printf("\nConnectionException: %s\n", e.what() );
241 }
242
243 int total = con.getInputAmnt();
244 const char *dat = con.getInput();
245 //printf("\n===> Final size %d\n", total );
246 for( int i = 0; i < total; i++ )
247 {
248 if( !memcmp( dat+i, "\r\n\r\n", 4 ) )
249 {
250 SBuffer *buf = new SBuffer;
251 buf->write( dat+i+4, total-i-4 );
252 buf->setPos( 0 );
253 con.close();
254 return buf;
255 }
256 }
257 con.close();
258
259 //printf("\n\n%s\n\n", dat );
260
261 throw ExceptionBase("Something went wrong, incomplete response? fix this.\n");
262}
263
diff --git a/src/old/httpget.h b/src/old/httpget.h
deleted file mode 100644
index 8272641..0000000
--- a/src/old/httpget.h
+++ /dev/null
@@ -1,44 +0,0 @@
1#ifndef HTTP_GET_H
2#define HTTP_GET_H
3
4#include <stdint.h>
5#include <string>
6#include <list>
7#include <utility>
8
9#include "sbuffer.h"
10
11class HttpGet
12{
13public:
14 HttpGet();
15 HttpGet( const std::string &url );
16 virtual ~HttpGet();
17
18 void setURL( const std::string &url );
19 void addParam( const std::string &key, const std::string &value );
20 void setUserAgent( const std::string &sUserAgent )
21 {
22 this->sUserAgent = sUserAgent;
23 }
24 void setHost( const std::string &sHost )
25 {
26 this->sHost = sHost;
27 }
28
29 std::string escape( const std::string &src );
30 SBuffer *get();
31
32private:
33 std::string sProto;
34 std::string sHost;
35 std::string sPath;
36 int nPort;
37 std::string sUserAgent;
38 typedef std::pair<std::string,std::string> StringPair;
39 std::list<StringPair> lParams;
40 static char hexcode[];
41
42};
43
44#endif
diff --git a/src/old/linkedlist.cpp b/src/old/linkedlist.cpp
deleted file mode 100644
index a9902bc..0000000
--- a/src/old/linkedlist.cpp
+++ /dev/null
@@ -1,210 +0,0 @@
1#include "linkedlist.h"
2
3LinkedList::LinkedList( )
4{
5 pBase = NULL;
6 pTop = NULL;
7 pLast = NULL;
8 nSize = 0;
9 nLast = -1;
10}
11
12LinkedList::~LinkedList( )
13{
14/*
15 Link *pCur = pBase;
16 while( pCur )
17 {
18 Link *pLast = pCur;
19 pCur = pCur->pNext;
20 delete pLast;
21 }
22*/
23 empty();
24}
25
26void *LinkedList::getAt( int index )
27{
28 if( index < 0 || index >= nSize )
29 return NULL;
30
31 return getPtrTo( index )->pData;
32}
33
34void LinkedList::append( void *data )
35{
36 if( pBase == NULL )
37 {
38 pBase = new Link( data );
39 pTop = pBase;
40 nSize++;
41 }
42 else
43 {
44 pTop->pNext = new Link( data );
45 pTop = pTop->pNext;
46 nSize++;
47 }
48}
49
50void LinkedList::insertBefore( void *data, int pos )
51{
52 if( pos < 0 || pos > nSize )
53 return;
54
55 if( pos == 0 )
56 {
57 Link *pTmp = new Link( data, pBase );
58 if( pBase == NULL )
59 {
60 pTop = pTmp;
61 }
62 pBase = pTmp;
63 if( nLast >= 0 ) nLast++;
64 nSize++;
65 }
66 else
67 {
68 Link *pCur;
69 if( (pCur = getPtrTo( pos-1 )) == NULL )
70 {
71 return;
72 }
73 Link *pNew = new Link( data, pCur->pNext );
74 pCur->pNext = pNew;
75 if( pNew->pNext == NULL )
76 {
77 pTop = pNew;
78 }
79 if( nLast >= pos ) nLast++;
80 nSize++;
81 }
82}
83
84int LinkedList::getSize( )
85{
86 return nSize;
87}
88
89bool LinkedList::isEmpty( )
90{
91 if( nSize == 0 )
92 return true;
93 return false;
94}
95
96void LinkedList::deleteAt( int index )
97{
98 if( index >= nSize ||
99 pBase == NULL )
100 return;
101
102 if( index == 0 )
103 {
104 Link *pTmp = pBase->pNext;
105 delete pBase;
106 pBase = pTmp;
107 if( nLast >= 0 ) nLast--;
108 nSize--;
109 if( pBase == NULL )
110 {
111 pTop = NULL;
112 }
113 else if( pBase->pNext == NULL )
114 {
115 pTop = pBase;
116 }
117 }
118 else
119 {
120 Link *pCur = getPtrTo( index-1 );
121 if( pCur->pNext == pTop )
122 {
123 pTop = pCur;
124 }
125 Link *pTmp;
126 if( pCur->pNext == NULL )
127 {
128 pTmp = NULL;
129 }
130 else
131 {
132 pTmp = pCur->pNext->pNext;
133 }
134 delete pCur->pNext;
135 pCur->pNext = pTmp;
136 if( nLast == index ) nLast = -1;
137 else if( index < nLast ) nLast--;
138 nSize--;
139 }
140}
141
142void LinkedList::empty()
143{
144 while( nSize > 0 )
145 {
146 deleteAt( 0 );
147 }
148}
149
150void LinkedList::setSize( int newSize )
151{
152 if( newSize < nSize )
153 {
154 // Delete items off of the end of the list.
155 while( nSize > newSize )
156 {
157 deleteAt( nSize-1 );
158 }
159 }
160 else
161 {
162 // Add null items to the end of the list.
163 while( nSize < newSize )
164 {
165 append( NULL );
166 }
167 }
168}
169
170void LinkedList::setAt( int index, void *data )
171{
172 if( index >= nSize || index < 0 )
173 return;
174
175 getPtrTo( index )->pData = data;
176}
177
178LinkedList::Link *LinkedList::getPtrTo( int index )
179{
180 if( index < 0 || index >= nSize )
181 return NULL;
182 if( index == nLast )
183 {
184 return pLast;
185 }
186 if( index == 0 )
187 {
188 pLast = pBase;
189 nLast = 0;
190 return pBase;
191 }
192 else
193 {
194 Link *pCur = pBase;
195 int nCur = 0;
196 if( nLast < index && nLast >= 0 )
197 {
198 pCur = pLast;
199 nCur = nLast;
200 }
201 while( nCur != index )
202 {
203 pCur = pCur->pNext;
204 nCur++;
205 }
206 nLast = index;
207 pLast = pCur;
208 return pCur;
209 }
210}
diff --git a/src/old/linkedlist.h b/src/old/linkedlist.h
deleted file mode 100644
index e430108..0000000
--- a/src/old/linkedlist.h
+++ /dev/null
@@ -1,87 +0,0 @@
1/**@file
2 * Describes the LinkedList implementation of the List ADT.
3 *@author Mike Buland
4 */
5
6#ifndef LINKEDLIST_H
7#define LINKEDLIST_H
8
9#include <stdio.h>
10#include "list.h"
11
12/** A linked-item implementation of the List ADT. Since the data is linked
13 * sequentially this is a great choice for lists that will grow and shrink
14 * a lot, but don't require as much random access. This implementation
15 * includes optomizations that make iterating through data, and appending
16 * items to the list take O(1) time.
17 *@author Mike Buland
18 */
19class LinkedList : public List
20{
21public:
22 /**
23 * Construct a blank LinkedList.
24 */
25 LinkedList();
26
27 /**
28 * Delete all list data, but do not delete any of the contained elements.
29 */
30 virtual ~LinkedList();
31
32 void *getAt( int nIndex );
33 void append( void *pData );
34 void insertBefore( void *pData, int nPos = 0 );
35 int getSize( );
36 bool isEmpty( );
37 void deleteAt( int nIndex );
38 void empty();
39 void setSize( int nNewSize );
40 void setAt( int nIndex, void *pData );
41
42private:
43 /**
44 * A link in the linked list.
45 */
46 class Link
47 {
48 public:
49 /**
50 * Construct an empty link.
51 */
52 Link()
53 {
54 pData = NULL;
55 pNext = NULL;
56 }
57 /**
58 * Construct a link filled in with useful data.
59 *@param newData The data this link should hold.
60 *@param newNext The next link that this link should point to.
61 */
62 Link( void *newData = NULL, Link * newNext = NULL )
63 {
64 pData = newData;
65 pNext = newNext;
66 }
67 void *pData; /**< A pointer to the contained data. */
68 Link *pNext; /**< A pointer to the next link in the chain */
69 };
70
71 /**
72 * Finds a pointer to the link at index index. This is the core function
73 * called for all seek operations, and has been optimized as heavily as
74 * possible.
75 *@param index The zero-based index of the desired element.
76 *@returns A pointer to the requested Link, or NULL if it isn't found.
77 */
78 Link *getPtrTo( int index );
79 Link *pBase; /**< The first link in the list. */
80 Link *pTop; /**< The Last link in the list. */
81 Link *pLast; /**< The previously requested link. */
82 int nSize; /**< The number of contained links. */
83 int nLast; /**< The index of the previously requested link. */
84};
85
86#endif
87
diff --git a/src/old/linkmessenger.cpp b/src/old/linkmessenger.cpp
deleted file mode 100644
index 3bd401a..0000000
--- a/src/old/linkmessenger.cpp
+++ /dev/null
@@ -1,41 +0,0 @@
1#include "linkmessenger.h"
2
3LinkMessenger::LinkMessenger() :
4 pFirst( NULL ),
5 pLast( NULL )
6{
7}
8
9LinkMessenger::~LinkMessenger()
10{
11}
12
13void LinkMessenger::enqueueMessage( LinkMessage *pMsg )
14{
15 if( pLast == NULL )
16 {
17 pFirst = pLast = new Link;
18 pLast->pMsg = pMsg;
19 pLast->pNext = NULL;
20 }
21 else
22 {
23 pLast->pNext = new Link;
24 pLast = pLast->pNext;
25 pLast->pMsg = pMsg;
26 pLast->pNext = NULL;
27 }
28}
29
30LinkMessage *LinkMessenger::dequeueMessage()
31{
32 if( pFirst == NULL )
33 return NULL;
34
35 Link *pTmp = pFirst;
36 pFirst = pFirst->pNext;
37 LinkMessage *pRet = pTmp->pMsg;
38 delete pTmp;
39 return pRet;
40}
41
diff --git a/src/old/linkmessenger.h b/src/old/linkmessenger.h
deleted file mode 100644
index ed52639..0000000
--- a/src/old/linkmessenger.h
+++ /dev/null
@@ -1,32 +0,0 @@
1#ifndef LINK_MESSENGER_H
2#define LINK_MESSENGER_H
3
4#include <stdlib.h>
5#include <stdint.h>
6#include "linkmessage.h"
7
8class LinkMessenger
9{
10public:
11 LinkMessenger();
12 virtual ~LinkMessenger();
13
14 void enqueueMessage( LinkMessage *pMsg );
15 LinkMessage *dequeueMessage();
16 bool hasMessages()
17 {
18 return (pFirst != NULL);
19 }
20
21private:
22 typedef struct Link
23 {
24 LinkMessage *pMsg;
25 Link *pNext;
26 };
27 Link *pFirst;
28 Link *pLast;
29
30};
31
32#endif
diff --git a/src/old/list.cpp b/src/old/list.cpp
deleted file mode 100644
index 18f1a66..0000000
--- a/src/old/list.cpp
+++ /dev/null
@@ -1,10 +0,0 @@
1#include "list.h"
2
3List::List( )
4{
5}
6
7List::~List( )
8{
9}
10
diff --git a/src/old/list.h b/src/old/list.h
deleted file mode 100644
index c71b328..0000000
--- a/src/old/list.h
+++ /dev/null
@@ -1,101 +0,0 @@
1#ifndef LIST_H
2#define LIST_H
3
4
5/** The basic List class ADT. This, on it's own, does absolutely nothing, but
6 * does define all standard interface functions to access a list.
7 *@author Mike Buland
8 */
9class List
10{
11public:
12 /**
13 * Construct a list.
14 */
15 List();
16
17 /**
18 * Desconstruct a list.
19 */
20 virtual ~List();
21
22 /** Gets the value at a specified index.
23 *@param nIndex The index of the item to return.
24 *@returns The specified item, or NULL if the index was beyond the range
25 * of the list.
26 *@author Mike Buland
27 */
28 virtual void *getAt( int nIndex ) = 0;
29
30 /** Append the given data to the end of the list. This increases the
31 * size of the list by one.
32 *@param pData The data to append to the list.
33 *@author Mike Buland
34 */
35 virtual void append( void *pData ) = 0;
36
37 /** Inserts an item at the specified position in the list. The
38 * new item takes the index that you specify, and all other items
39 * are moved up one position. The size of the list is increased by
40 * one.
41 *@param pData The value to insert into the list.
42 *@param nPos Where to insert the data into the list.
43 *@author Mike Buland
44 */
45 virtual void insertBefore( void *pData, int nPos = 0 ) = 0;
46
47 /** Determines the size of the list, in elements.
48 *@returns The size of the list.
49 *@author Mike Buland
50 */
51 virtual int getSize( ) = 0;
52
53 /** Determines if the list is empty or not.
54 *@returns True if the list is empty, or false if the list has
55 * data in it (if the size is greater than zero).
56 *@author Mike Buland
57 */
58 virtual bool isEmpty( ) = 0;
59
60 /** Deletes an item at the specified index and moves all other
61 * values down one index. The size of the list is decreased by one.
62 *@param nIndex The index of the item to delete.
63 *@author Mike Buland
64 */
65 virtual void deleteAt( int nIndex ) = 0;
66
67 /** Completely empties the list, and sets the effective size to
68 * zero.
69 *@author Mike Buland
70 */
71 virtual void empty() = 0;
72
73 /** Sets the size of the list. This can be larger or smaller
74 * than what it was previously. If larger, new blank items will
75 * be added to the end of the list. If smaller than the old list
76 * items will be deleted from the end.
77 *@param nNewSize The new size of the list.
78 *@author Mike Buland
79 */
80 virtual void setSize( int nNewSize ) = 0;
81
82 /** Sets a member at a specified location to a new value.
83 * If the member being set is outside of the range of the
84 * current list it should be expanded.
85 *@param nIndex The zero-based index of the item to change.
86 *@param pData The new value for that index.
87 *@author Mike Buland
88 */
89 virtual void setAt( int nIndex, void *pData ) = 0;
90
91 /** Makes the List work like an array. Just say listObj[2] to get
92 * the third element.
93 *@param nIndex The index to access in the list.
94 *@returns A pointer to the data at element index.
95 *@author Mike Buland
96 */
97 void *operator[]( int nIndex ) { return getAt( nIndex ); };
98};
99
100#endif
101
diff --git a/src/old/md5.cpp b/src/old/md5.cpp
deleted file mode 100644
index c0cacdd..0000000
--- a/src/old/md5.cpp
+++ /dev/null
@@ -1,190 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include <string.h>
4#include "md5.h"
5
6// This is a fun macro that tells us where the length char goes after the data
7// section in the padded data segment. It's short for OBfuscation LOCaction.
8#define OBLOC(len) ((((len + 64) >> 9) << 4) + 14)
9// This performs a wrapping bitwise shift, kinda' fun!
10
11#define bit_roll( num, cnt ) \
12 (((num) << (cnt)) | (((num) >> (32 - (cnt))) & ~(-1<<(cnt))))
13
14//#define md5_cmn( q, a, b, x, s, t ) (bit_roll((a + q + x + t), s) + b)
15
16// The following are handy wrappers for the cmn function
17#define md5_ff( a, b, c, d, x, s, t ) \
18 (md5_cmn((b & c) | ((~b) & d), a, b, x, s, t))
19
20#define md5_gg( a, b, c, d, x, s, t ) \
21 (md5_cmn((b & d) | (c & (~d)), a, b, x, s, t))
22
23#define md5_hh( a, b, c, d, x, s, t ) \
24 (md5_cmn(b ^ c ^ d, a, b, x, s, t))
25
26#define md5_ii( a, b, c, d, x, s, t ) \
27 (md5_cmn(c ^ (b | (~d)), a, b, x, s, t))
28
29inline long md5_cmn( long q, long a, long b, long x, long s, long t )
30{
31 return bit_roll((a + q + x + t), s) + b;
32}
33
34md5::md5()
35{
36}
37
38md5::~md5()
39{
40}
41
42/*
43 * Calculate the MD5 of an array of little-endian words, and a bit length
44 */
45void md5::core_md5( long *x, long len, md5sum *output )
46{
47 long a = 1732584193, olda;
48 long b = -271733879, oldb;
49 long c = -1732584194, oldc;
50 long d = 271733878, oldd;
51
52 for( long i = 0; i < len; i += 16 )
53 {
54 olda = a;
55 oldb = b;
56 oldc = c;
57 oldd = d;
58
59 a = md5_ff(a, b, c, d, x[i+ 0], 7 , -680876936);
60 d = md5_ff(d, a, b, c, x[i+ 1], 12, -389564586);
61 c = md5_ff(c, d, a, b, x[i+ 2], 17, 606105819);
62 b = md5_ff(b, c, d, a, x[i+ 3], 22, -1044525330);
63 a = md5_ff(a, b, c, d, x[i+ 4], 7 , -176418897);
64 d = md5_ff(d, a, b, c, x[i+ 5], 12, 1200080426);
65 c = md5_ff(c, d, a, b, x[i+ 6], 17, -1473231341);
66 b = md5_ff(b, c, d, a, x[i+ 7], 22, -45705983);
67 a = md5_ff(a, b, c, d, x[i+ 8], 7 , 1770035416);
68 d = md5_ff(d, a, b, c, x[i+ 9], 12, -1958414417);
69 c = md5_ff(c, d, a, b, x[i+10], 17, -42063);
70 b = md5_ff(b, c, d, a, x[i+11], 22, -1990404162);
71 a = md5_ff(a, b, c, d, x[i+12], 7 , 1804603682);
72 d = md5_ff(d, a, b, c, x[i+13], 12, -40341101);
73 c = md5_ff(c, d, a, b, x[i+14], 17, -1502002290);
74 b = md5_ff(b, c, d, a, x[i+15], 22, 1236535329);
75
76 a = md5_gg(a, b, c, d, x[i+ 1], 5 , -165796510);
77 d = md5_gg(d, a, b, c, x[i+ 6], 9 , -1069501632);
78 c = md5_gg(c, d, a, b, x[i+11], 14, 643717713);
79 b = md5_gg(b, c, d, a, x[i+ 0], 20, -373897302);
80 a = md5_gg(a, b, c, d, x[i+ 5], 5 , -701558691);
81 d = md5_gg(d, a, b, c, x[i+10], 9 , 38016083);
82 c = md5_gg(c, d, a, b, x[i+15], 14, -660478335);
83 b = md5_gg(b, c, d, a, x[i+ 4], 20, -405537848);
84 a = md5_gg(a, b, c, d, x[i+ 9], 5 , 568446438);
85 d = md5_gg(d, a, b, c, x[i+14], 9 , -1019803690);
86 c = md5_gg(c, d, a, b, x[i+ 3], 14, -187363961);
87 b = md5_gg(b, c, d, a, x[i+ 8], 20, 1163531501);
88 a = md5_gg(a, b, c, d, x[i+13], 5 , -1444681467);
89 d = md5_gg(d, a, b, c, x[i+ 2], 9 , -51403784);
90 c = md5_gg(c, d, a, b, x[i+ 7], 14, 1735328473);
91 b = md5_gg(b, c, d, a, x[i+12], 20, -1926607734);
92
93 a = md5_hh(a, b, c, d, x[i+ 5], 4 , -378558);
94 d = md5_hh(d, a, b, c, x[i+ 8], 11, -2022574463);
95 c = md5_hh(c, d, a, b, x[i+11], 16, 1839030562);
96 b = md5_hh(b, c, d, a, x[i+14], 23, -35309556);
97 a = md5_hh(a, b, c, d, x[i+ 1], 4 , -1530992060);
98 d = md5_hh(d, a, b, c, x[i+ 4], 11, 1272893353);
99 c = md5_hh(c, d, a, b, x[i+ 7], 16, -155497632);
100 b = md5_hh(b, c, d, a, x[i+10], 23, -1094730640);
101 a = md5_hh(a, b, c, d, x[i+13], 4 , 681279174);
102 d = md5_hh(d, a, b, c, x[i+ 0], 11, -358537222);
103 c = md5_hh(c, d, a, b, x[i+ 3], 16, -722521979);
104 b = md5_hh(b, c, d, a, x[i+ 6], 23, 76029189);
105 a = md5_hh(a, b, c, d, x[i+ 9], 4 , -640364487);
106 d = md5_hh(d, a, b, c, x[i+12], 11, -421815835);
107 c = md5_hh(c, d, a, b, x[i+15], 16, 530742520);
108 b = md5_hh(b, c, d, a, x[i+ 2], 23, -995338651);
109
110 a = md5_ii(a, b, c, d, x[i+ 0], 6 , -198630844);
111 d = md5_ii(d, a, b, c, x[i+ 7], 10, 1126891415);
112 c = md5_ii(c, d, a, b, x[i+14], 15, -1416354905);
113 b = md5_ii(b, c, d, a, x[i+ 5], 21, -57434055);
114 a = md5_ii(a, b, c, d, x[i+12], 6 , 1700485571);
115 d = md5_ii(d, a, b, c, x[i+ 3], 10, -1894986606);
116 c = md5_ii(c, d, a, b, x[i+10], 15, -1051523);
117 b = md5_ii(b, c, d, a, x[i+ 1], 21, -2054922799);
118 a = md5_ii(a, b, c, d, x[i+ 8], 6 , 1873313359);
119 d = md5_ii(d, a, b, c, x[i+15], 10, -30611744);
120 c = md5_ii(c, d, a, b, x[i+ 6], 15, -1560198380);
121 b = md5_ii(b, c, d, a, x[i+13], 21, 1309151649);
122 a = md5_ii(a, b, c, d, x[i+ 4], 6 , -145523070);
123 d = md5_ii(d, a, b, c, x[i+11], 10, -1120210379);
124 c = md5_ii(c, d, a, b, x[i+ 2], 15, 718787259);
125 b = md5_ii(b, c, d, a, x[i+ 9], 21, -343485551);
126
127 a = a + olda;
128 b = b + oldb;
129 c = c + oldc;
130 d = d + oldd;
131 }
132
133 output->data[0] = a;
134 output->data[1] = b;
135 output->data[2] = c;
136 output->data[3] = d;
137 delete[] x;
138}
139
140long *md5::c2l( const char *str, long len, long *nNewLen )
141{
142 long len8 = len*8;
143 long mlen = OBLOC( len8 );
144 long flen = (((mlen/16)+((mlen%16)?(1):(0))))*16;
145 long *aBin = new long[flen];
146 memset( aBin, 0, flen*4 );
147
148 for( long i = 0; i < len8; i+=8 )
149 {
150 aBin[i>>5] |= ((long)str[i/8]) << (i%32);
151 }
152
153 aBin[len8 >> 5] |= 0x80 << ((len8) % 32);
154 aBin[OBLOC( len8 )] = len8;
155
156 (*nNewLen) = flen;
157
158 return aBin;
159}
160
161void md5::l2hexstr( long *binarray, char *str )
162{
163 static const char hex_tab[] = {"0123456789abcdef"};
164 //static char str[33];
165
166 int k = 0;
167 for( int i = 0; i < 16; i++)
168 {
169 str[k++] = hex_tab[(binarray[i>>2] >> ((i%4)*8+4)) & 0xF];
170 str[k++] = hex_tab[(binarray[i>>2] >> ((i%4)*8 )) & 0xF];
171 }
172}
173
174void md5::sumString( md5sum *pSum, const char *sStr )
175{
176 sumData( pSum, sStr, strlen( sStr ) );
177}
178
179void md5::sumData( md5sum *pSum, const char *aData, long nLen )
180{
181 long nNewLen;
182 long *aOb = c2l( aData, nLen, &nNewLen );
183 core_md5( aOb, nNewLen, pSum );
184}
185
186void md5::sumToHex( md5sum *pSum, char *sHex )
187{
188 l2hexstr( pSum->data, sHex );
189}
190
diff --git a/src/old/md5.h b/src/old/md5.h
deleted file mode 100644
index 7f77d83..0000000
--- a/src/old/md5.h
+++ /dev/null
@@ -1,81 +0,0 @@
1#ifndef MD5_H
2#define MD5_H
3
4/**
5 * Used to store an MD5 sum in a handy container.
6 */
7typedef struct
8{
9 /** The actual data-storage for an MD5 sum. */
10 long data[4];
11} md5sum;
12
13/**
14 * Class for easily calculating MD5 sums of just about any data.
15 *@author Mike Buland
16 */
17class md5
18{
19public:
20 /** Build an MD5 sum builder. */
21 md5();
22
23 /** Deconstruct */
24 virtual ~md5();
25
26 /**
27 * Create a sum of a standard c string, null terminated. This is probably
28 * the easiest function to use.
29 *@param pSum The MD5 sum structure to fill up.
30 *@param sStr The null-terminated string to turn into an MD5 sum.
31 */
32 void sumString( md5sum *pSum, const char *sStr );
33
34 /**
35 * Create a sum of an array of arbitrary data. This is the most handy for
36 * dealing with files and so on.
37 *@param pSum The MD5 sum structure to fill up.
38 *@param aData A pointer to the base of the data to sum.
39 *@param nLen The number of bytes to use in the sum.
40 */
41 void sumData( md5sum *pSum, const char *aData, long nLen );
42
43 /**
44 * Convert an md5sum to standard hex representation. Make sure that sHex
45 * contains at least 17 characters of space.
46 *@param pSum The sum structure to convert to hex.
47 *@param sHex The string to store the hex value in.
48 */
49 void sumToHex( md5sum *pSum, char *sHex );
50
51private:
52 /**
53 * Do the bulk of the work of the md5 algorithm.
54 *@param x I'm not sure. I'll need to look it up.
55 *@param len The length of the data.
56 *@param output The sum structure to put the output in.
57 */
58 void core_md5( long *x, long len, md5sum *output );
59
60 /**
61 * Convert an array of charaters to an array of longs in a very crafty way.
62 * This also applies standard MD5 obfuscation to the resulting array, and
63 * makes it fit within MD5 size constraints.
64 *@param str The data to convert.
65 *@param len The length of the data.
66 *@param nNewLen A pointer to a variable that will hold the new length of
67 * the resulting array of longs.
68 *@returns The newly obfuscated and resized long array.
69 */
70 long *c2l( const char *str, long len, long *nNewLen );
71
72 /**
73 * Backend helper to convert an array of longs into a hex string.
74 *@param binarray The binary data to convert.
75 *@param str The string to store the hex string in.
76 */
77 void l2hexstr( long *binarray, char *str );
78
79};
80
81#endif
diff --git a/src/old/multilog.cpp b/src/old/multilog.cpp
deleted file mode 100644
index 143ee89..0000000
--- a/src/old/multilog.cpp
+++ /dev/null
@@ -1,102 +0,0 @@
1#include "multilog.h"
2#include <stdio.h>
3#include <time.h>
4#include <string.h>
5#include <stdlib.h>
6
7#include "multilogchannel.h"
8
9MultiLog::MultiLog()
10{
11 lChannel = new LinkedList();
12 rEntry = new RingList( 150 );
13 nEntriesLost = 0;
14}
15
16MultiLog::~MultiLog()
17{
18 int nMax = lChannel->getSize();
19 for( int j = 0; j < nMax; j++ )
20 {
21 ((MultiLogChannel *)lChannel->getAt(j))->closeLog();
22 delete ((MultiLogChannel *)lChannel->getAt(j));
23 }
24 delete lChannel;
25
26 for( int j = 0; j < rEntry->getSize(); j++ )
27 {
28 delete (LogEntry *)rEntry->getAt( j );
29 }
30 delete rEntry;
31}
32/*
33void MultiLog::Log( int nLevel, const char *lpFormat, ...)
34{
35 switch( nLevel )
36 {
37 default:
38 break;
39 }
40 va_list ap;
41 va_start(ap, lpFormat);
42
43 vprintf( lpFormat, ap );
44
45 va_end(ap);
46}*/
47
48void MultiLog::DetailLog( int nLevel, const char *lpFile, int nLine, const char *lpFunction, const char *lpFormat, ...)
49{
50 LogEntry *e = new LogEntry();
51
52 va_list ap;
53 va_start(ap, lpFormat);
54 char *text;
55 vasprintf( &text, lpFormat, ap );
56 va_end(ap);
57
58 time( &e->xTime );
59 e->nLevel = nLevel;
60 e->nLine = nLine;
61 e->lpFile = new char[strlen(lpFile)+1];
62 strcpy( e->lpFile, lpFile );
63 e->lpText = new char[strlen(text)+1];
64 strcpy( e->lpText, text );
65 free( text );
66
67 append( e );
68}
69
70void MultiLog::append( LogEntry *pEntry )
71{
72 rEntry->append( pEntry );
73 if( rEntry->getPushBuf() )
74 {
75 delete (LogEntry *)rEntry->getPushBuf();
76 nEntriesLost++;
77 }
78
79 for( int j = 0; j < lChannel->getSize(); j++ )
80 {
81 ((MultiLogChannel *)lChannel->getAt( j ))->append( pEntry );
82 }
83}
84
85void MultiLog::addChannel( MultiLogChannel *pChannel )
86{
87 lChannel->append( pChannel );
88
89 pChannel->openLog();
90
91 for( int j = 0; j < rEntry->getSize(); j++ )
92 {
93 pChannel->append( (LogEntry *)rEntry->getAt( j ) );
94 }
95}
96
97MultiLog::LogEntry::~LogEntry()
98{
99 delete[] lpFile;
100 delete[] lpText;
101}
102
diff --git a/src/old/multilog.h b/src/old/multilog.h
deleted file mode 100644
index 692095a..0000000
--- a/src/old/multilog.h
+++ /dev/null
@@ -1,130 +0,0 @@
1#ifndef MULTILOG_H
2#define MULTILOG_H
3
4#include <stdio.h>
5#include <stdarg.h>
6#include <time.h>
7
8#include "ringlist.h"
9#include "linkedlist.h"
10#include "singleton.h"
11
12/**
13 * Calls the DetailLog function but includes pre-processor macros to fill in
14 * most of the fields for you. This makes your life a lot easier, and makes the
15 * log useful for system debugging as well as just letting people know what's
16 * going on.
17 *@param LEVEL The log level, comes from an enum in the MultiLog class.
18 *@param FORMAT The text to store in the log, using printf style formatting.
19 *@param ... Parameters to help format the text in the FROMAT param.
20 */
21#define LineLog( LEVEL, FORMAT, ...) DetailLog( LEVEL, __FILE__, __LINE__, __PRETTY_FUNCTION__, FORMAT, ##__VA_ARGS__ )
22
23#define MultiLineLog( LEVEL, FORMAT, ...) MultiLog::getInstance().DetailLog( LEVEL, __FILE__, __LINE__, __PRETTY_FUNCTION__, FORMAT, ##__VA_ARGS__ )
24
25/** MultiLog keeps track of logfile info in a myriad of varieties, and is
26 * easily configurable between them all. It allows output to the standard
27 * output, error output, files, networks, and streams, which includes memory
28 * buffers.
29 * MultiLog uses the singleton pattern to keep only a single instance of
30 * the log. Instead of instantiating a new copy, call the getLog method.
31 *@author Mike Buland
32 */
33class MultiLog : public Singleton<MultiLog>
34{
35 friend class Singleton<MultiLog>;
36public:
37 /**
38 * Keeps track of a single log entry, in a standard format, that can be
39 * processed by any MultiLogChannel derrived class.
40 *@author Mike Buland
41 */
42 typedef struct LogEntry
43 {
44 /** Safely delete a log entry. */
45 virtual ~LogEntry();
46 time_t xTime; /**< The time the log entry was made. */
47 int nLevel; /**< The log-level of the entry. */
48 char *lpFile; /**< The name of the file this entry came from. */
49 int nLine; /**< The line number that this log came from. */
50 char *lpText; /**< The text content of this log entry. */
51 } LogEntry;
52
53protected:
54 /**
55 * Private constructor, this ensures that this is a singleton.
56 */
57 MultiLog();
58
59 /**
60 * Destroy the multilog.
61 */
62 virtual ~MultiLog();
63
64 /**
65 * Append a new logentry to the log list, possibly pushing an old entry off.
66 *@param pEntry The new entry to append.
67 */
68 void append( LogEntry *pEntry );
69
70 /**
71 * The actual log entry storage mechanism.
72 */
73 RingList *rEntry;
74
75 /**
76 * The number of entries that have rolled off the end of the RingList.
77 */
78 unsigned long nEntriesLost;
79
80 /**
81 * A list of all channels that are registered with the MultiLog.
82 */
83 LinkedList *lChannel;
84
85public:
86
87 /** Sends info to the logfile.
88 *@param nLevel The type of data being logged (error, info, etc.)
89 *@param lpFormat The data to send to the log.
90 *@author Mike Buland
91 */
92 //void Log( int nLevel, const char *lpFormat, ...);
93
94 /** Sends info to the logfile with extra information, including the files
95 * that it was called from and the line in the code. Besides that, it's
96 * exactly the same as Log. Please use the LineLog macro to make DetailLog
97 * really easy to use. It operates exacly like Log, but inserts the
98 * builtin macros as the lpFile and nLine parameters.
99 *@param nLevel The type of data being logged (error, info, etc.)
100 *@param lpFile The name of the file that called the log function.
101 *@param nLine The line in the file that this log function was called from.
102 *@param lpFunction The name of the function that called the log function.
103 *@param lpFormat The data to send to the log.
104 *@author Mike Buland
105 */
106 void DetailLog( int nLevel, const char *lpFile, int nLine, const char *lpFunction, const char *lpFormat, ...);
107
108 /**
109 * Adds a logging channel to the MultiLog channel chain. Every added
110 * channel will automatically receive a complete log of everything that
111 * happened before the channel was added as well as all future messages.
112 *@param pChannel A pointer to the pre-contructed channel object to add.
113 */
114 void addChannel( class MultiLogChannel *pChannel );
115
116 /** The various pre-defined levels available to use when logging.
117 * The person logging can make up their own, just make sure to remember
118 * which value is which (all levels are integers).
119 *@author Mike Buland
120 */
121 enum Levels
122 {
123 LError,
124 LWarning,
125 LInfo,
126 LStatus
127 };
128};
129
130#endif
diff --git a/src/old/multilogchannel.cpp b/src/old/multilogchannel.cpp
deleted file mode 100644
index ee4c9bf..0000000
--- a/src/old/multilogchannel.cpp
+++ /dev/null
@@ -1,13 +0,0 @@
1//
2// C++ Implementation: multilogchannel
3//
4// Description:
5//
6//
7// Author: Mike Buland <eichlan@yf-soft.com>, (C) 2005
8//
9// Copyright: See COPYING file that comes with this distribution
10//
11//
12#include "multilogchannel.h"
13
diff --git a/src/old/multilogchannel.h b/src/old/multilogchannel.h
deleted file mode 100644
index d891a65..0000000
--- a/src/old/multilogchannel.h
+++ /dev/null
@@ -1,46 +0,0 @@
1#ifndef MULTILOGCHANNEL_H
2#define MULTILOGCHANNEL_H
3
4#include "multilog.h"
5
6/**
7 * The baseclass for any MultiLog output channel. Any class that implements
8 * all of these functions can be put in the log chain and will be sent
9 * messages from active MultiLoggers.
10 *@author Mike Buland
11 */
12class MultiLogChannel
13{
14public:
15 /**
16 * Deconstruct a MultiLogChannel.
17 */
18 virtual ~MultiLogChannel() {};
19
20 /**
21 * Should perform any operations that need to take place in order to start
22 * the output of data into this channel. This will be called once by the
23 * MultiLog when the MultiLogChannel is registered.
24 *@returns True means that everything can go as planned. False means that
25 * the MultiLog should remove this channel from the list and delete it.
26 */
27 virtual bool openLog() = 0;
28
29 /**
30 * Should append a log entry to the long, by whatever means are necesarry.
31 *@param pEntry The LogEntry to append.
32 *@returns True means that everything can go as planned. False means that
33 * the MultiLog should remove this channel from the list and delete it.
34 */
35 virtual bool append( MultiLog::LogEntry *pEntry ) = 0;
36
37 /**
38 * Should perform any operations that need to take place in order to safely
39 * close and cleanup the log.
40 *@returns True means that everything can go as planned. False means that
41 * the MultiLog should remove this channel from the list and delete it.
42 */
43 virtual bool closeLog() = 0;
44};
45
46#endif
diff --git a/src/old/multilogtext.cpp b/src/old/multilogtext.cpp
deleted file mode 100644
index 4337cc9..0000000
--- a/src/old/multilogtext.cpp
+++ /dev/null
@@ -1,188 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include <fcntl.h>
4#include <unistd.h>
5#include <time.h>
6#include <string.h>
7#include "multilogtext.h"
8/*
9bool fileexists( const char *sPath )
10{
11 int nFileDesc = open( sPath, O_RDONLY );
12 if( nFileDesc < 0 )
13 {
14 return false;
15 }
16 else
17 {
18 close( nFileDesc );
19 return true;
20 }
21}*/
22
23MultiLogText::MultiLogText( const char *sFileName, const char *lpFormat, bool bRotateLog, int nMaxLogs )
24{
25 this->lpFormat = NULL;
26 /*
27 if( bRotateLog )
28 {
29 if( fileexists( sFileName ) == false )
30 {
31 return;
32 }
33
34 int nLen = strlen( sFileName );
35 char *buf = new char[nLen+6];
36 sprintf( buf, "%s.", sFileName );
37
38 for( int j = 1; j < nMaxLogs; j++ )
39 {
40 sprintf( &buf[nLen+1], "%d", j );
41 if( !fileexists( buf ) )
42 {
43 rename( sFileName, buf );
44 break;
45 }
46 }
47 }*/
48
49 nFD = open( sFileName, O_WRONLY|O_CREAT|O_TRUNC, S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH );
50 setLogFormat( lpFormat );
51}
52
53MultiLogText::MultiLogText( int nFileDesc, const char *lpFormat )
54{
55 this->lpFormat = NULL;
56 nFD = nFileDesc;
57 setLogFormat( lpFormat );
58}
59
60MultiLogText::~MultiLogText()
61{
62 if( nFD != -1 )
63 {
64 close( nFD );
65 }
66
67 delete[] lpFormat;
68}
69
70bool MultiLogText::setLogFormat( const char *lpFormat )
71{
72 char buf[200];
73 int k = 0;
74 static char fmts[10][4]={
75 {'y', 'd', '0', '1'},
76 {'m', 'd', '0', '2'},
77 {'d', 'd', '0', '3'},
78 {'h', 'd', '0', '4'},
79 {'M', 'd', '0', '5'},
80 {'s', 'd', '0', '6'},
81 {'l', 'd', '0', '7'},
82 {'f', 's', '0', '8'},
83 {'L', 'd', '0', '9'},
84 {'t', 's', '1', '0'},
85 };
86
87 for( int j = 0; lpFormat[j] != '\0'; j++ )
88 {
89 if( lpFormat[j] == '%' )
90 {
91 buf[k++] = '%';
92 int nPlace = k++;
93 k++;
94 buf[k++] = '$';
95 bool bDone = false;
96 for( j++; bDone == false; j++ )
97 {
98 int l;
99 for( l = 0; l < 10; l++ )
100 {
101 if( lpFormat[j] == fmts[l][0] )
102 {
103 buf[nPlace] = fmts[l][2];
104 buf[nPlace+1] = fmts[l][3];
105 buf[k++] = fmts[l][1];
106 bDone = true;
107 break;
108 }
109 }
110 if( l == 10 )
111 {
112 buf[k++] = lpFormat[j];
113 }
114 }
115 j--;
116 }
117 else
118 {
119 buf[k++] = lpFormat[j];
120 }
121 }
122 buf[k++] = '\n';
123 buf[k] = '\0';
124
125 if( this->lpFormat != NULL )
126 {
127 delete[] this->lpFormat;
128 }
129 this->lpFormat = new char[k+1];
130 strcpy( this->lpFormat, buf );
131
132 return true;
133}
134
135bool MultiLogText::openLog()
136{
137 if( nFD == -1 )
138 {
139 return false;
140 }
141 return true;
142}
143
144bool MultiLogText::append( MultiLog::LogEntry *pEntry )
145{
146 if( nFD == -1 )
147 {
148 return false;
149 }
150
151 char *line = NULL;
152 struct tm *pTime;
153 pTime = localtime( &pEntry->xTime );
154 asprintf(
155 &line,
156 lpFormat,
157 pTime->tm_year+1900,
158 pTime->tm_mon+1,
159 pTime->tm_mday,
160 pTime->tm_hour,
161 pTime->tm_min,
162 pTime->tm_sec,
163 pEntry->nLevel,
164 pEntry->lpFile,
165 pEntry->nLine,
166 pEntry->lpText
167 );
168 write( nFD, line, strlen(line) );
169 free( line );
170
171 return true;
172}
173
174bool MultiLogText::closeLog()
175{
176 if( nFD == -1 )
177 {
178 return false;
179 }
180 // Don't close it if it's sdtout or errorout
181 if( nFD > 2 )
182 {
183 close( nFD );
184 }
185 nFD = -1;
186 return true;
187}
188
diff --git a/src/old/multilogtext.h b/src/old/multilogtext.h
deleted file mode 100644
index 197aef1..0000000
--- a/src/old/multilogtext.h
+++ /dev/null
@@ -1,70 +0,0 @@
1#ifndef MULTILOGTEXT_H
2#define MULTILOGTEXT_H
3
4#include "multilogchannel.h"
5
6/**
7 * Simple MultiLogChannel that takes the logdata, formats it textually, and
8 * writes it to a text device, either a file or the screen, yay! This takes
9 * the place of the old standard logging facility.
10 * The entries in the format follow the standard printf % style, and are as
11 * follows:
12 * <ul>
13 * <li>%y - current year</li>
14 * <li>%m - current month</li>
15 * <li>%d - current day</li>
16 * <li>%h - current hour (24-hour format)</li>
17 * <li>%M - current minute</li>
18 * <li>%s - current seccond</li>
19 * <li>%l - Loglevel (numerical)</li>
20 * <li>%f - Filename</li>
21 * <li>%L - Line number</li>
22 * <li>%t - Full text of the log entry</li>
23 * </ul>
24 *@author Mike Buland
25 */
26class MultiLogText : public MultiLogChannel
27{
28public:
29 /**
30 * Construct a MultiLogText object around a specific filename and format.
31 * The file named by sFileName will be opened for writting in text+append
32 * mode. No existing data will be destroyed.
33 *@param sFileName The file to output log-data to.
34 *@param lpFormat The format using the above specifications to be used for
35 * every log entry.
36 */
37 MultiLogText( const char *sFileName, const char *lpFormat, bool bRotateLog=false, int nMaxLogs=0 );
38
39 /**
40 * Construct a MultiLogText object around a specific file and format.
41 * The file descriptor passed in should describe an already opened and set-
42 * up file or device. This could easily be a socket or stdout or stderr.
43 *@param nFileDesc The already opened descriptor to send data to.
44 *@param lpFormat The format using the above specifications to be used for
45 * every log entry.
46 */
47 MultiLogText( int nFileDesc, const char *lpFormat );
48
49 /**
50 * Destroy the object.
51 */
52 virtual ~MultiLogText();
53
54 bool openLog();
55 bool append( MultiLog::LogEntry *pEntry );
56 bool closeLog();
57
58 /**
59 * Change the log format on the fly.
60 *@param lpFormat The new format to use for all future log entries.
61 *@returns True if everything was fine, false for catastrophic failure.
62 */
63 bool setLogFormat( const char *lpFormat );
64
65private:
66 int nFD; /**< The file descriptor we're writing to. */
67 char *lpFormat; /**< The format that we're using, converted for printf. */
68};
69
70#endif
diff --git a/src/old/ordhash.cpp b/src/old/ordhash.cpp
deleted file mode 100644
index 77cbd61..0000000
--- a/src/old/ordhash.cpp
+++ /dev/null
@@ -1 +0,0 @@
1#include "ordhash.h"
diff --git a/src/old/ordhash.h b/src/old/ordhash.h
deleted file mode 100644
index e946f95..0000000
--- a/src/old/ordhash.h
+++ /dev/null
@@ -1,104 +0,0 @@
1#ifndef ORD_HASH_H
2#define ORD_HASH_H
3
4#include "hash.h"
5#include "tqsort.h"
6
7template<typename key, typename value, typename cmpfnc, typename sizecalc = __calcNextTSize_fast, typename keyalloc = std::allocator<key>, typename valuealloc = std::allocator<value>, typename challoc = std::allocator<uint32_t> >
8class OrdHash : public Hash<key, value, sizecalc, keyalloc, valuealloc, challoc>
9{
10public:
11 OrdHash() :
12 bSorted( false ),
13 aData( NULL )
14 {
15 }
16
17 virtual ~OrdHash()
18 {
19 }
20
21protected:
22 virtual void invalidate()
23 {
24 bSorted = false;
25 delete[] aData;
26 aData = NULL;
27 }
28
29 virtual void onInsert()
30 {
31 invalidate();
32 }
33
34 virtual void onUpdate()
35 {
36 invalidate();
37 }
38
39 virtual void onDelete()
40 {
41 invalidate();
42 }
43
44 virtual void onReHash()
45 {
46 invalidate();
47 }
48
49 virtual std::pair<key,value> getAtPos( uint32_t nPos )
50 {
51 return Hash<key, value, sizecalc, keyalloc, valuealloc, challoc>::getAtPos( aData[nPos].nIndex );
52 }
53
54 virtual void buildIndex()
55 {
56 aData = new struct ind[this->nFilled];
57 uint32_t k = 0;
58 for( uint32_t j = 0; j < this->nCapacity; j++ )
59 {
60 if( this->isFilled( j ) )
61 {
62 if( !this->isDeleted( j ) )
63 {
64 aData[k].pVal = &(this->aValues[j]);
65 aData[k].nIndex = j;
66 k++;
67 }
68 }
69 }
70
71 tqsort<typename OrdHash<key, value, cmpfnc, sizecalc, keyalloc, valuealloc, challoc>::ind, cmpfnc, value **>( aData, this->nFilled );
72
73 bSorted = true;
74 }
75
76 virtual uint32_t getFirstPos( bool &bFinished )
77 {
78 if( bSorted == false )
79 buildIndex();
80
81 return 0;
82 }
83
84 virtual uint32_t getNextPos( uint32_t nPos, bool &bFinished )
85 {
86 if( nPos+1 >= this->nFilled )
87 {
88 bFinished = true;
89 return 0;
90 }
91 return ++nPos;
92 }
93public:
94 typedef struct ind
95 {
96 value *pVal;
97 uint32_t nIndex;
98 } ind;
99private:
100 bool bSorted;
101 ind *aData;
102};
103
104#endif
diff --git a/src/old/pqueue.cpp b/src/old/pqueue.cpp
deleted file mode 100644
index 1f0b8b5..0000000
--- a/src/old/pqueue.cpp
+++ /dev/null
@@ -1,33 +0,0 @@
1#include "pqueue.h"
2
3PQueue::PQueue( int nNewNumQueues )
4{
5 nNumQueues = nNewNumQueues;
6 aQueue = new Queue[nNumQueues];
7}
8
9PQueue::~PQueue()
10{
11 delete[] aQueue;
12}
13
14void PQueue::enqueue( void *pData, int nQueueLevel )
15{
16 if( nQueueLevel < 0 || nQueueLevel >= nNumQueues )
17 return;
18
19 aQueue[nQueueLevel].enqueue( pData );
20}
21
22void *PQueue::dequeue()
23{
24 for( int j = 0; j < nNumQueues; j++ )
25 {
26 if( aQueue[j].isEmpty() == false )
27 {
28 return aQueue[j].dequeue();
29 }
30 }
31
32 return NULL;
33}
diff --git a/src/old/pqueue.h b/src/old/pqueue.h
deleted file mode 100644
index 8307d56..0000000
--- a/src/old/pqueue.h
+++ /dev/null
@@ -1,48 +0,0 @@
1#ifndef PQUEUE_H
2#define PQUEUE_H
3
4#include "queue.h"
5
6/** Priority queue. This is just like a queue, but something with a higher
7 * priority will always come off the queue before something with a lower
8 * priority, even if it's added after. Otherwise works just like a queue.
9 *@author Mike Buland
10 */
11class PQueue
12{
13public:
14 /** Create a queue with any number of different priorities.
15 *@param nNewNumQueues The number of queues, the default is 3
16 */
17 PQueue( int nNewNumQueues=3 );
18
19 /**
20 * Cleanup all contained queues.
21 */
22 virtual ~PQueue();
23
24 /** Add a new item to the queue at the specified priority. A lower
25 * number means a higher priority!
26 *@param pData A pointer to the data to add to the queue
27 *@param nQueueLevel The priority to set the new data to
28 */
29 void enqueue( void *pData, int nQueueLevel );
30
31 /** Pull the next item off the queue, high priority first.
32 *@returns A pointer to the data that was next in the priority queue
33 */
34 void *dequeue();
35
36private:
37 /**
38 * The queues we use for real data storage.
39 */
40 Queue *aQueue;
41
42 /**
43 * The number of priorities or queus that we need.
44 */
45 int nNumQueues;
46};
47
48#endif
diff --git a/src/old/protocol.cpp b/src/old/protocol.cpp
deleted file mode 100644
index 78b3ee2..0000000
--- a/src/old/protocol.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
1#include "protocol.h"
2
3Protocol::Protocol()
4{
5 pConnection = NULL;
6}
7
8Protocol::~Protocol()
9{
10}
11
12void Protocol::setConnection( Connection *pNewConnection )
13{
14 pConnection = pNewConnection;
15}
16
17Connection *Protocol::getConnection()
18{
19 return pConnection;
20}
diff --git a/src/old/protocol.h b/src/old/protocol.h
deleted file mode 100644
index 09e1c98..0000000
--- a/src/old/protocol.h
+++ /dev/null
@@ -1,62 +0,0 @@
1#ifndef PROTOCOL_H
2#define PROTOCOL_H
3
4#include "connection.h"
5
6/** This is the template for a class that handles specialized input and output
7 * to connections of different types with different protocols.
8 *@author Mike Buland
9 */
10class Protocol
11{
12public:
13 /** Constructor */
14 Protocol();
15 /** Deconstructor */
16 virtual ~Protocol();
17
18 /**
19 * Function is called every time there is new data on the line. This is
20 * called directly from the Connection class to process data. This is not
21 * called whever there is pending data on the input, but every time new data
22 * is added to the input buffer.
23 *@returns True if processing went alright, false if something went wrong,
24 * I suppose. In truth this value is thrown away right now.
25 *@todo Either make a return value of false mean something, or make these
26 * void.
27 */
28 virtual bool onNewData()=0;
29
30 /**
31 * Function is called when there is a new connection. This should only
32 * happen once per Protocol object, but gives each protocol object a
33 * chance to perform connection handshaking and initialization at a point
34 * where they know that they have a handle to an active Connection.
35 *@returns See onNewData
36 */
37 virtual bool onNewConnection()=0;
38
39 virtual void onNewClientConnection(){};
40
41 virtual void poll(){};
42
43 /**
44 * Sets the Protocol's Connection object. This is rather important, and
45 * handled usually by the ConnectionManager.
46 *@param pNewConnection The Connection object that this protocol will use to
47 * deal with the outside world.
48 */
49 void setConnection( class Connection *pNewConnection );
50
51 /**
52 * Get a pointer to this object's Connection object, or NULL if one was
53 * never set. If used with the ConnectionManager that should never happen.
54 *@returns A pointer to the active Connection.
55 */
56 Connection *getConnection();
57
58private:
59 class Connection *pConnection; /**< The pointer to the Connection. */
60};
61
62#endif
diff --git a/src/old/protocoltelnet.cpp b/src/old/protocoltelnet.cpp
deleted file mode 100644
index b169a51..0000000
--- a/src/old/protocoltelnet.cpp
+++ /dev/null
@@ -1,316 +0,0 @@
1#include "protocoltelnet.h"
2#include <string.h>
3
4ProtocolTelnet::ProtocolTelnet()
5{
6 nTermType = termUnInited;
7 bEchoOn = true;
8}
9
10ProtocolTelnet::~ProtocolTelnet()
11{
12}
13
14bool ProtocolTelnet::onNewConnection()
15{
16 Connection *pCon = getConnection();
17
18 pCon->appendOutput( (char)IAC );
19 pCon->appendOutput( (char)WILL );
20 pCon->appendOutput( (char)SUPPRESSGA );
21
22 pCon->appendOutput( (char)IAC );
23 pCon->appendOutput( (char)DO );
24 pCon->appendOutput( (char)SUPPRESSGA );
25
26 pCon->appendOutput( (char)IAC );
27 pCon->appendOutput( (char)DONT );
28 pCon->appendOutput( (char)TERMTYPE );
29
30// pCon->appendOutput( IAC );
31// pCon->appendOutput( SB );
32// pCon->appendOutput( TERMTYPE );
33// pCon->appendOutput( 1 );
34// pCon->appendOutput( IAC );
35// pCon->appendOutput( SE );
36
37 pCon->appendOutput( (char)IAC );
38 pCon->appendOutput( (char)DONT );
39 pCon->appendOutput( (char)ECHO );
40
41 pCon->appendOutput( (char)IAC );
42 pCon->appendOutput( (char)WILL );
43 pCon->appendOutput( (char)ECHO );
44
45// 255(IAC),251(WILL),3
46 return true;
47}
48
49bool ProtocolTelnet::onNewData()
50{
51 Connection *pCon = getConnection();
52 if( !pCon->hasInput() )
53 {
54 return true;
55 }
56
57 int nInSize = pCon->getInputAmnt();
58 char *lpInStr = (char *)pCon->getInput();
59
60 // Here we interpret the basic commands and un-encapsulate them, so to
61 // speak. We'll allow this, even if the terminal is in raw mode, we
62 // just won't send anything in response...
63 for( int j = 0; j < nInSize; j++ )
64 {
65 switch( (unsigned char)lpInStr[j] )
66 {
67 case '\r':
68 fbEdited.appendData('\n');
69 if( bEchoOn ) pCon->appendOutput("\n\r");
70 break;
71
72 case '\n':
73 break;
74
75 case '\177': // backspace
76 if( fbEdited.getLength() > 0 )
77 {
78 fbEdited.usedData( -1 ); // Delete one char from the end
79 if( bEchoOn ) pCon->appendOutput(ESC "[D"); // Move the cursor back one
80 if( bEchoOn ) pCon->appendOutput(ESC "[P"); // Delete one character
81 }
82 break;
83
84 case '\x1B': // escape sequence
85 if( (unsigned char)lpInStr[j+1] == '[' )
86 {
87 switch( (unsigned char)lpInStr[j+2] )
88 {
89 case 'A': // Up
90 break;
91
92 case 'B': // Down
93 break;
94
95 case 'C': // Right
96 break;
97
98 case 'D': // Left
99 break;
100 }
101 j+=2;
102 }
103 break;
104
105 case 0: // NOP: No operation
106 break;
107
108 case IAC: // IAC: Interpret as command
109 switch( lpInStr[j+1] )
110 {
111 case SE: // SE: End of subnegotiation parameters.
112 break;
113
114 case NOP: // NOP: No operation
115 break;
116
117 case DM: // DM: Data mark. Indicates the position of a Synch event within the data stream. This should always be accompanied by a TCP urgent notification.
118 break;
119
120 case BRK: // BRK: Break. Indicates that the "break" or "attention" key was hit.
121 break;
122
123 case IP: // IP: Suspend, interrupt or abort the process to which the NVT is connected.
124 break;
125
126 case AO: // AO: Abort output. Allows the current process to run to completion but do not send its output to the user.
127 break;
128
129 case AYT: // AYT: Are you there. Send back to the NVT some visible evidence that the AYT was received.
130 break;
131
132 case EC: // EC: Erase character. The receiver should delete the last preceding undeleted character from the data stream.
133 break;
134
135 case EL: // EL: Erase line. Delete characters from the data stream back to but not including the previous CRLF.
136 break;
137
138 case GA: // GA: Go ahead. Used, under certain circumstances, to tell the other end that it can transmit.
139 break;
140
141 case SB: // SB: Subnegotiation of the indicated option follows.
142 switch( lpInStr[j+2] )
143 {
144 case TERMTYPE:
145 if( lpInStr[j+3] == 0 )
146 {
147 for( int k = 0; j+4+k < nInSize; k++ )
148 {
149 if( (unsigned char)lpInStr[j+4+k] == IAC &&
150 (unsigned char)lpInStr[j+5+k] == SE )
151 {
152 lpInStr[j+4+k] = 0;
153 //@TODO: Do something with the term type...
154 printf("Term type: %s\n", &lpInStr[j+4] );
155 j += 5+k;
156 }
157 }
158 }
159 else
160 {
161 }
162 break;
163
164 default:
165 //printf("unknown subnegotiation parameters! (%d)\n", lpInStr[j+2] );
166 break;
167 }
168 break;
169
170 case WILL: // WILL: Indicates the desire to begin performing
171 switch( lpInStr[j+2] )
172 {
173 case SUPPRESSGA:
174 j += 2;
175// pCon->usedInput( 3 );
176 break;
177
178 case TERMTYPE:
179 j += 2;
180// pCon->usedInput( 3 );
181 break;
182
183 case ECHO:
184 j += 2;
185// pCon->usedInput( 3 );
186 break;
187
188 case NAWS:
189 default:
190 pCon->appendOutput( (char)ESC[0] );
191 pCon->appendOutput( (char)DONT );
192 pCon->appendOutput( lpInStr[j+2] );
193 //printf("unknown will command used! (%d)\n", lpInStr[j+2] );
194 j += 2;
195 break;
196 }
197 break;
198
199 case WONT: // WONT: Indicates the refusal to perform
200 switch( lpInStr[j+2] )
201 {
202 case ECHO:
203 j += 2;
204// pCon->usedInput( 3 );
205 break;
206
207 default:
208 //printf("unknown wont command used! (%d)\n", lpInStr[j+2] );
209 j += 2;
210 break;
211 }
212 break;
213
214 case DO: // DO: Indicates the request that the other party perform
215 switch( lpInStr[j+2] )
216 {
217 case ECHO:
218 j += 2;
219 break;
220
221 case SUPPRESSGA:
222 j += 2;
223 break;
224
225 default:
226 pCon->appendOutput( (char)ESC[0] );
227 pCon->appendOutput( (char)DONT );
228 pCon->appendOutput( lpInStr[j+2] );
229 //printf("unknown do command used! (%d)\n", lpInStr[j+2] );
230 j += 2;
231 break;
232 }
233// pCon->usedInput( 3 );
234 break;
235
236 case DONT: // DONT: Indicates the demand that the other party stop performing
237 switch( lpInStr[j+2] )
238 {
239 case ECHO:
240 j += 2;
241// pCon->usedInput( 3 );
242 break;
243
244 default:
245 printf("unknown dont command used! (%d)\n", lpInStr[j+2] );
246 j += 2;
247 break;
248 }
249 break;
250 }
251 break;
252
253 default:
254 fbEdited.appendData( lpInStr[j] );
255 if( bEchoOn ) pCon->appendOutput( lpInStr[j] );
256 break;
257 }
258 }
259
260 pCon->usedInput( pCon->getInputAmnt() );
261
262 return true;
263}
264
265char *ProtocolTelnet::getLine( bool bFullOnly )
266{
267 int i = fbEdited.findChar('\n');
268
269 if( i < 0 )
270 {
271 if( bFullOnly == false )
272 {
273 i = fbEdited.getLength();
274 }
275 else
276 {
277 return NULL;
278 }
279 }
280
281 char *lpStr = new char[i+1];
282 strncpy( lpStr, fbEdited.getData(), i );
283 lpStr[i] = '\0';
284
285 fbEdited.usedData( i+1 );
286
287 return lpStr;
288}
289
290char *ProtocolTelnet::peekLine( bool bFullOnly )
291{
292 int i = fbEdited.findChar('\n');
293
294 if( i < 0 )
295 {
296 if( bFullOnly == false )
297 {
298 i = fbEdited.getLength();
299 }
300 else
301 {
302 return NULL;
303 }
304 }
305
306 char *lpStr = new char[i+1];
307 strncpy( lpStr, fbEdited.getData(), i );
308 lpStr[i] = '\0';
309
310 return lpStr;
311}
312
313void ProtocolTelnet::setEcho( bool bEchoOn )
314{
315 this->bEchoOn = bEchoOn;
316}
diff --git a/src/old/protocoltelnet.h b/src/old/protocoltelnet.h
deleted file mode 100644
index a6d2e49..0000000
--- a/src/old/protocoltelnet.h
+++ /dev/null
@@ -1,77 +0,0 @@
1#ifndef PROTOCOLTELNET_H
2#define PROTOCOLTELNET_H
3
4#include "protocol.h"
5#include "flexbuf.h"
6
7#define ESC "\x1B" /**< A telnet escape code. */
8
9/** Handles all specialized protocol actions related to the telnet protocol.
10 * This includes setting modes, non-scrollable regions, and so on.
11 *@author Mike Buland
12 */
13class ProtocolTelnet : public Protocol
14{
15public:
16 ProtocolTelnet();
17 virtual ~ProtocolTelnet();
18
19 bool onNewData();
20 bool onNewConnection();
21
22 char *getLine( bool bFullOnly = true );
23 char *peekLine( bool bFullOnly = true );
24
25 void setEcho( bool bEchoOn = true );
26
27 enum
28 {
29 termUnInited,
30 termRaw,
31 termUnknown,
32 termVT220,
33 termXTerm
34 };
35
36 enum
37 {
38 SE = 240, // SE: End of subnegotiation parameters.
39 NOP = 241, // NOP: No operation
40 DM = 242, // DM: Data mark. Indicates the position of a Synch event within the data stream. This should always be accompanied by a TCP urgent notification.
41 BRK = 243, // BRK: Break. Indicates that the "break" or "attention" key was hit.
42 IP = 244, // IP: Suspend, interrupt or abort the process to which the NVT is connected.
43 AO = 245, // AO: Abort output. Allows the current process to run to completion but do not send its output to the user.
44 AYT = 246, // AYT: Are you there. Send back to the NVT some visible evidence that the AYT was received.
45 EC = 247, // EC: Erase character. The receiver should delete the last preceding undeleted character from the data stream.
46 EL = 248, // EL: Erase line. Delete characters from the data stream back to but not including the previous CRLF.
47 GA = 249, // GA: Go ahead. Used, under certain circumstances, to tell the other end that it can transmit.
48 SB = 250, // SB: Subnegotiation of the indicated option follows.
49 WILL = 251, // WILL: Indicates the desire to begin performing, or confirmation that you are now performing, the indicated option.
50 WONT = 252, // WONT: Indicates the refusal to perform, or continue performing, the indicated option.
51 DO = 253, // DO: Indicates the request that the other party perform, or confirmation that you are expecting the other party to perform, the indicated option.
52 DONT = 254, // DONT: Indicates the demand that the other party stop performing, or confirmation that you are no longer expecting the other party to perform, the indicated option.
53 IAC = 255 // IAC: Interpret as command
54 };
55
56 enum
57 {
58 ECHO = 1, // Explain who'll echo
59 SUPPRESSGA = 3, // Suppress Go Ahead
60 TERMTYPE = 24, // Terminal Type
61 NAWS = 31, // Window size
62 TERMSPEED = 32, // Terminal Speed
63 LINEMODE = 34 // Linemode
64 };
65
66private:
67 int nTermType;
68
69 int nTermWidth;
70 int nTermHeight;
71
72 FlexBuf fbEdited;
73
74 bool bEchoOn;
75};
76
77#endif
diff --git a/src/old/queue.cpp b/src/old/queue.cpp
deleted file mode 100644
index 42999fe..0000000
--- a/src/old/queue.cpp
+++ /dev/null
@@ -1,26 +0,0 @@
1#include "queue.h"
2
3void Queue::enqueue( void *data )
4{
5 lQueueData.append( data );
6}
7
8void *Queue::dequeue()
9{
10 void *dat = lQueueData[0];
11 if( dat != NULL )
12 {
13 lQueueData.deleteAt( 0 );
14 }
15 return dat;
16}
17
18bool Queue::isEmpty()
19{
20 return lQueueData.isEmpty();
21}
22
23void Queue::empty()
24{
25 lQueueData.empty();
26}
diff --git a/src/old/queue.h b/src/old/queue.h
deleted file mode 100644
index 692f5d8..0000000
--- a/src/old/queue.h
+++ /dev/null
@@ -1,45 +0,0 @@
1#ifndef QUEUE_H
2#define QUEUE_H
3#include "linkedlist.h"
4
5/**
6 * An ultra-simple queue implementation. It just uses a linked list as it's
7 * container so we don't have to worry about anything!
8 *@author Mike Buland
9 */
10class Queue
11{
12public:
13 /**
14 * Puts a new item at the end of the queue.
15 *@param data A new value to put at the end of the queue.
16 */
17 void enqueue( void *data );
18
19 /**
20 * Gets the begining item of the queue off and returns it.
21 *@returns The value at the front of the queue.
22 */
23 void *dequeue();
24
25 /**
26 * Checks if the queueu is empty.
27 *@returns True if the queueu is empty, and false if it has things in it.
28 */
29 bool isEmpty();
30
31 /**
32 * Empty the queue.
33 */
34 void empty();
35
36 /**
37 * Get a pointer to the internal list object.
38 *@returns A pointer to the internal list object.
39 */
40 LinkedList *getList() { return &lQueueData; };
41
42private:
43 LinkedList lQueueData; /**< Where all of the real data is stored. */
44};
45#endif
diff --git a/src/old/ringlist.cpp b/src/old/ringlist.cpp
deleted file mode 100644
index 9efbbc4..0000000
--- a/src/old/ringlist.cpp
+++ /dev/null
@@ -1,106 +0,0 @@
1//
2// C++ Implementation: ringlist
3//
4// Description:
5//
6//
7// Author: Mike Buland <eichlan@yf-soft.com>, (C) 2005
8//
9// Copyright: See COPYING file that comes with this distribution
10//
11//
12#include <stdlib.h>
13
14#include "ringlist.h"
15
16RingList::RingList( int nInitSize )
17 : List()
18{
19 nFirstIndex = 0;
20 nRealLength = nInitSize;
21 nDataLength = 0;
22 apData = new void*[nInitSize];
23 pPushBuf = NULL;
24}
25
26RingList::~RingList()
27{
28 delete[] apData;
29}
30
31void *RingList::getAt( int nIndex )
32{
33 if( nIndex < 0 || nIndex >= nDataLength )
34 {
35 return NULL;
36 }
37
38 return apData[(nFirstIndex+nIndex)%nRealLength];
39}
40
41void RingList::append( void *pData )
42{
43 int nIndex = (nFirstIndex+nDataLength)%nRealLength;
44
45 pPushBuf = apData[nIndex];
46 apData[nIndex] = pData;
47
48 if( nDataLength == nRealLength )
49 {
50 nFirstIndex = (nFirstIndex+1)%nRealLength;
51 }
52 else
53 {
54 nDataLength++;
55 // We really didn't need it this time...
56 pPushBuf = NULL;
57 }
58}
59
60void RingList::insertBefore( void *pData, int nPos )
61{
62 // Not implemented right now, don't even try it!
63}
64
65int RingList::getSize()
66{
67 return nDataLength;
68}
69
70bool RingList::isEmpty()
71{
72 return nDataLength==0;
73}
74
75void RingList::deleteAt( int nIndex )
76{
77 // Also not implemented yet
78}
79
80void RingList::empty()
81{
82 nFirstIndex = 0;
83 nDataLength = 0;
84}
85
86void RingList::setSize( int nNewSize )
87{
88 if( apData )
89 {
90 delete[] apData;
91 }
92 nFirstIndex = 0;
93 nRealLength = nNewSize;
94 nDataLength = 0;
95 apData = new void*[nNewSize];
96}
97
98void RingList::setAt( int nIndex, void *pData )
99{
100 apData[(nIndex+nFirstIndex)%nRealLength] = pData;
101}
102
103void *RingList::getPushBuf()
104{
105 return pPushBuf;
106}
diff --git a/src/old/ringlist.h b/src/old/ringlist.h
deleted file mode 100644
index bc069f3..0000000
--- a/src/old/ringlist.h
+++ /dev/null
@@ -1,112 +0,0 @@
1#ifndef RINGLIST_H
2#define RINGLIST_H
3
4#include "list.h"
5
6/**
7 * A RingList or Ring Buffer implementation. This is a list that never grows in
8 * size once it is created, but instead once it is full new items added to the
9 * RingList replace the oldest items and the zero-index is virtually shifted.
10 * Since no data is actually moved when zero-index moves, this is very
11 * efficient.
12 * <br>
13 * The items removed are not actually deleted by the RingList, so instead they
14 * are first moved into a temporary "Push Buffer" that can be accessed so that
15 * elements pushed off the edge of the RingList can be accessed for cleanup.
16 *@author Mike Buland
17 */
18class RingList : public List
19{
20public:
21 /**
22 * Construct a RingList with a fixed initial size. This size never changes
23 * unless setSize is called later during normal operation.
24 *@param nInitSize The number of elements to allocate.
25 */
26 RingList( int nInitSize );
27
28 /**
29 * Clean up the data structures, but not the contained elements.
30 */
31 virtual ~RingList();
32
33 /**
34 * Get an element at the specified index.
35 *@param nIndex The index of the element to retreive.
36 *@returns A pointer to the requested element, or NULL if the element is
37 * not found or not initialized yet.
38 */
39 void *getAt( int nIndex );
40
41 /**
42 * Append an element to the end of the list, overwriting the begining if
43 * necesarry.
44 *@param pData The pointer to append to the RingList.
45 */
46 void append( void *pData );
47
48 /**
49 * Insert an element before another in the RingList, pushing all after it
50 * down the list.
51 *@param pData The data to insert.
52 *@param nPos The position that new the element should occupy in the list.
53 */
54 void insertBefore( void *pData, int nPos = 0 );
55
56 /**
57 * Get the size of the array.
58 */
59 int getSize();
60
61 /**
62 * Is the RingList empty?
63 *@returns True if it is empty, false otherwise.
64 */
65 bool isEmpty();
66
67 /**
68 * Delete an element in the list, moving all later elements down one index.
69 *@param nIndex The index of the element to delete.
70 */
71 void deleteAt( int nIndex );
72
73 /**
74 * Remove all elements from the RingList.
75 */
76 void empty();
77
78 /**
79 * Set a new size for the RingList. Be careful with this one, if shrinking
80 * this may quietly create a memory leak.
81 *@param nNewSize The new size to set the RingList to.
82 *@todo Either fix this memory leak somehow or remove this function.
83 */
84 void setSize( int nNewSize );
85
86 /**
87 * Set a specific element to a new value.
88 *@param nIndex The zero-based index to change the value of.
89 *@param pData The data to put at the location specified by nIndex.
90 */
91 void setAt( int nIndex, void *pData );
92
93 /**
94 * Retrieve the contents of the push buffer. This is the data that is
95 * pushed off the end of the array if you append data and the list is full.
96 * This should be checked after every append operation to be sure there
97 * isn't anything that needs deleting.
98 *@returns The last value pushed off the RingList, or NULL if nothing was
99 * pushed off.
100 */
101 void *getPushBuf();
102
103private:
104 int nFirstIndex; /**< The index to be translated as zero. */
105 int nRealLength; /**< The Amount of storage space available. */
106 int nDataLength; /**< The number of elements filled in. */
107 void **apData; /**< The actual data storage. */
108 void *pPushBuf; /**< The push buffer. */
109
110};
111
112#endif
diff --git a/src/old/sbuffer.cpp b/src/old/sbuffer.cpp
deleted file mode 100644
index f84f8a3..0000000
--- a/src/old/sbuffer.cpp
+++ /dev/null
@@ -1,67 +0,0 @@
1#include <string.h>
2#include "sbuffer.h"
3
4SBuffer::SBuffer() :
5 nPos( 0 ),
6 bOpen( true )
7{
8}
9
10SBuffer::~SBuffer()
11{
12}
13
14void SBuffer::close()
15{
16 bOpen = false;
17 fbData.clearData();
18}
19
20size_t SBuffer::read( char *pBuf, size_t nBytes )
21{
22 size_t nLeft = fbData.getLength() - nPos;
23 if( nBytes > nLeft )
24 nBytes = nLeft;
25
26 if( nLeft == 0 )
27 return 0;
28
29 memcpy( pBuf, fbData.getData()+nPos, nBytes );
30 nPos += nBytes;
31
32 return nBytes;
33}
34
35size_t SBuffer::write( const char *pBuf, size_t nBytes )
36{
37 fbData.appendData( pBuf, nBytes );
38 nPos += nBytes;
39
40 return nBytes;
41}
42
43long SBuffer::tell()
44{
45 return nPos;
46}
47
48void SBuffer::seek( long offset )
49{
50 nPos += offset;
51}
52
53void SBuffer::setPos( long pos )
54{
55 nPos = pos;
56}
57
58void SBuffer::setPosEnd( long pos )
59{
60 nPos = fbData.getLength() - pos;
61}
62
63bool SBuffer::isEOS()
64{
65 return nPos == fbData.getLength();
66}
67
diff --git a/src/old/sbuffer.h b/src/old/sbuffer.h
deleted file mode 100644
index 65feb71..0000000
--- a/src/old/sbuffer.h
+++ /dev/null
@@ -1,40 +0,0 @@
1#ifndef S_BUFFER_H
2#define S_BUFFER_H
3
4#include <stdint.h>
5
6#include "stream.h"
7#include "flexbuf.h"
8
9class SBuffer : public Stream
10{
11public:
12 SBuffer();
13 virtual ~SBuffer();
14
15 virtual void close();
16 virtual size_t read( char *pBuf, size_t nBytes );
17
18 /**
19 *@todo Update this to write at nPos, not just append data.
20 */
21 virtual size_t write( const char *pBuf, size_t nBytes );
22
23 virtual long tell();
24 virtual void seek( long offset );
25 virtual void setPos( long pos );
26 virtual void setPosEnd( long pos );
27 virtual bool isEOS();
28
29 FlexBuf &getBuffer()
30 {
31 return fbData;
32 }
33
34private:
35 long nPos;
36 bool bOpen;
37 FlexBuf fbData;
38};
39
40#endif
diff --git a/src/old/serializerbinary.cpp b/src/old/serializerbinary.cpp
deleted file mode 100644
index ea7ed93..0000000
--- a/src/old/serializerbinary.cpp
+++ /dev/null
@@ -1,63 +0,0 @@
1#include "serializerbinary.h"
2#include "serializable.h"
3#include "exceptions.h"
4
5SerializerBinary::SerializerBinary(FILE *fhFile, bool bLoading):
6 Serializer(bLoading),
7 fhFile(fhFile),
8 bCloseFile(false)
9{
10}
11
12SerializerBinary::SerializerBinary(const char *sFileName, bool bLoading):
13 Serializer(bLoading),
14 bCloseFile(true)
15{
16 if (bLoading)
17 {
18 fhFile = fopen(sFileName, "rb");
19 if( fhFile == NULL )
20 throw FileException("Unable to open file: %s", sFileName );
21 }
22 else
23 {
24 fhFile = fopen(sFileName, "wb");
25 if( fhFile == NULL )
26 throw FileException("Unable to open file: %s", sFileName );
27 }
28}
29
30SerializerBinary::~SerializerBinary()
31{
32 close();
33}
34
35void SerializerBinary::close()
36{
37 if (fhFile != NULL && bCloseFile )
38 {
39 fclose(fhFile);
40 fhFile = NULL;
41 }
42}
43
44void SerializerBinary::write(const void * pData, int32_t nSize)
45{
46 if( nSize == 0 )
47 return;
48
49 fwrite(pData, nSize, 1, fhFile);
50}
51
52void SerializerBinary::read(void * pData, int32_t nSize)
53{
54 if( nSize == 0 )
55 return;
56
57 uint32_t nRead = fread(pData, nSize, 1, fhFile);
58 if( nRead < 1 )
59 {
60 throw FileException( excodeEOF, "End of file read");
61 }
62}
63
diff --git a/src/old/serializerbinary.h b/src/old/serializerbinary.h
deleted file mode 100644
index 8510fcd..0000000
--- a/src/old/serializerbinary.h
+++ /dev/null
@@ -1,24 +0,0 @@
1#ifndef SERIALIZER_BINARY_H
2#define SERIALIZER_BINARY_H
3
4#include "serializer.h"
5#include <stdio.h>
6
7class SerializerBinary : public Serializer
8{
9public:
10 SerializerBinary(FILE *fhFile, bool bLoading);
11 SerializerBinary(const char *sFileName, bool bLoading);
12 virtual ~SerializerBinary();
13
14 virtual void close();
15
16 virtual void write(const void *, int32_t);
17 virtual void read(void *, int32_t);
18
19private:
20 FILE *fhFile;
21 bool bCloseFile;
22};
23
24#endif
diff --git a/src/old/serializerbzip2.cpp b/src/old/serializerbzip2.cpp
deleted file mode 100644
index bafabc8..0000000
--- a/src/old/serializerbzip2.cpp
+++ /dev/null
@@ -1,88 +0,0 @@
1#include "serializerbzip2.h"
2#include "serializable.h"
3
4#include <bzlib.h>
5
6SerializerBZip2::SerializerBZip2(FILE *fhFile, bool bLoading):
7 Serializer(bLoading),
8 fhFile(fhFile),
9 bCloseFile(false)
10{
11 if( bLoading )
12 {
13 bzFile = BZ2_bzReadOpen( &bzerror, fhFile, 0, 0, NULL, 0 );
14 checkBZError();
15 }
16 else
17 {
18 bzFile = BZ2_bzWriteOpen( &bzerror, fhFile, 9, 0, 0 );
19 checkBZError();
20 }
21}
22
23SerializerBZip2::SerializerBZip2(char *sFileName, bool bLoading):
24 Serializer(bLoading),
25 bCloseFile(true)
26{
27 if (bLoading)
28 {
29 fhFile = fopen(sFileName, "rb");
30 bzFile = BZ2_bzReadOpen( &bzerror, fhFile, 0, 0, NULL, 0 );
31 checkBZError();
32 }
33 else
34 {
35 fhFile = fopen(sFileName, "wb");
36 bzFile = BZ2_bzWriteOpen( &bzerror, fhFile, 9, 0, 0 );
37 checkBZError();
38 }
39}
40
41SerializerBZip2::~SerializerBZip2()
42{
43 close();
44}
45
46void SerializerBZip2::checkBZError()
47{
48}
49
50void SerializerBZip2::close()
51{
52 if( bzFile != NULL )
53 {
54 if( isLoading() )
55 {
56 void *unused;
57 int nUnused;
58 BZ2_bzReadGetUnused( &bzerror, bzFile, &unused, &nUnused );
59 BZ2_bzReadClose( &bzerror, bzFile );
60 if( nUnused )
61 fseek( fhFile, -nUnused, SEEK_CUR );
62 }
63 else
64 {
65 BZ2_bzWriteClose( &bzerror, bzFile, 0, 0, 0 );
66 }
67 checkBZError();
68 bzFile = NULL;
69 }
70 if( fhFile != NULL && bCloseFile )
71 {
72 fclose(fhFile);
73 fhFile = NULL;
74 }
75}
76
77void SerializerBZip2::write(const void * pData, int32_t nSize)
78{
79 BZ2_bzWrite( &bzerror, bzFile, (void *)pData, nSize );
80 checkBZError();
81}
82
83void SerializerBZip2::read(void * pData, int32_t nSize)
84{
85 BZ2_bzRead( &bzerror, bzFile, pData, nSize );
86 checkBZError();
87}
88
diff --git a/src/old/serializerbzip2.h b/src/old/serializerbzip2.h
deleted file mode 100644
index 4aeb22e..0000000
--- a/src/old/serializerbzip2.h
+++ /dev/null
@@ -1,27 +0,0 @@
1#ifndef SERIALIZER_BINARY_H
2#define SERIALIZER_BINARY_H
3
4#include "serializer.h"
5#include <stdio.h>
6
7class SerializerBZip2 : public Serializer
8{
9public:
10 SerializerBZip2(FILE *fhFile, bool bLoading);
11 SerializerBZip2(char *sFileName, bool bLoading);
12 virtual ~SerializerBZip2();
13
14 virtual void close();
15
16 virtual void write(const void *, int32_t);
17 virtual void read(void *, int32_t);
18
19private:
20 void checkBZError();
21 FILE *fhFile;
22 void *bzFile;
23 bool bCloseFile;
24 int bzerror;
25};
26
27#endif
diff --git a/src/old/serializerconnection.cpp b/src/old/serializerconnection.cpp
deleted file mode 100644
index 2934c8b..0000000
--- a/src/old/serializerconnection.cpp
+++ /dev/null
@@ -1,15 +0,0 @@
1#include "serializerconnection.h"
2
3SerializerConnection::SerializerConnection(
4 Connection *pCon, bool bIO, int nTimeSec, int nTimeUSec ) :
5 Serializer( bIO ),
6 pCon( pCon ),
7 nTimeSec( nTimeSec ),
8 nTimeUSec( nTimeUSec )
9{
10}
11
12SerializerConnection::~SerializerConnection()
13{
14}
15
diff --git a/src/old/serializerconnection.h b/src/old/serializerconnection.h
deleted file mode 100644
index e8d85c6..0000000
--- a/src/old/serializerconnection.h
+++ /dev/null
@@ -1,24 +0,0 @@
1#ifndef SERIALIZER_CONNECTION_H
2#define SERIALIZER_CONNECTION_H
3
4#include <stdint.h>
5
6#include "serializer.h"
7#include "connection.h"
8
9/**
10 *
11 */
12class SerializerConnection : public Serializer
13{
14public:
15 SerializerConnection( Connection *pCon, bool bIO, int nTimeSec, int nTimeUSec );
16 virtual ~SerializerConnection();
17
18private:
19 Connection *pCon;
20 int nTimeSec;
21 int nTimeUSec;
22};
23
24#endif
diff --git a/src/old/serializertext.cpp b/src/old/serializertext.cpp
deleted file mode 100644
index 9cf4394..0000000
--- a/src/old/serializertext.cpp
+++ /dev/null
@@ -1,170 +0,0 @@
1#include "serializertext.h"
2
3SerializerText::SerializerText(FILE *fhFile, bool bLoading):
4 Serializer(bLoading),
5 fhFile(fhFile),
6 bCloseFile(false)
7{
8}
9
10SerializerText::SerializerText(const char *sFileName, bool bLoading):
11 Serializer(bLoading),
12 bCloseFile(true)
13{
14 if (bLoading)
15 {
16 fhFile = fopen(sFileName, "rt");
17 }
18 else
19 {
20 fhFile = fopen(sFileName, "wt");
21 }
22}
23
24SerializerText::~SerializerText()
25{
26 close();
27}
28
29void SerializerText::close()
30{
31 if (fhFile != NULL)
32 {
33 fclose(fhFile);
34 fhFile = NULL;
35 }
36}
37
38void SerializerText::write(const void * pData, int32_t nSize)
39{
40 fwrite(pData, nSize, 1, fhFile);
41 fprintf(fhFile, "\n");
42}
43
44void SerializerText::read(void * pData, int32_t nSize)
45{
46 fread(pData, nSize, 1, fhFile);
47 fgetc(fhFile);
48}
49
50Serializer &SerializerText::operator<<(bool p)
51{
52 fprintf(fhFile, "%hhd\n", p);
53 return *this;
54}
55Serializer &SerializerText::operator<<(int8_t p)
56{
57 fprintf(fhFile, "%hhd\n", p);
58 return *this;
59}
60Serializer &SerializerText::operator<<(int16_t p)
61{
62 fprintf(fhFile, "%hd\n", p);
63 return *this;
64}
65Serializer &SerializerText::operator<<(int32_t p)
66{
67 fprintf(fhFile, "%d\n", p);
68 return *this;
69}
70Serializer &SerializerText::operator<<(int64_t p)
71{
72 fprintf(fhFile, "%lld\n", p);
73 return *this;
74}
75Serializer &SerializerText::operator<<(uint8_t p)
76{
77 fprintf(fhFile, "%hhu\n", p);
78 return *this;
79}
80Serializer &SerializerText::operator<<(uint16_t p)
81{
82 fprintf(fhFile, "%hu\n", p);
83 return *this;
84}
85Serializer &SerializerText::operator<<(uint32_t p)
86{
87 fprintf(fhFile, "%u\n", p);
88 return *this;
89}
90Serializer &SerializerText::operator<<(uint64_t p)
91{
92 fprintf(fhFile, "%llu\n", p);
93 return *this;
94}
95Serializer &SerializerText::operator<<(float p)
96{
97 fprintf(fhFile, "%f\n", p);
98 return *this;
99}
100Serializer &SerializerText::operator<<(double p)
101{
102 fprintf(fhFile, "%f\n", p);
103 return *this;
104}
105Serializer &SerializerText::operator<<(long double p)
106{
107 fprintf(fhFile, "%Lf\n", p);
108 return *this;
109}
110
111Serializer &SerializerText::operator>>(bool &p)
112{
113 fscanf(fhFile, "%hhd\n", ((signed char *)&p));
114 return *this;
115}
116Serializer &SerializerText::operator>>(int8_t &p)
117{
118 fscanf(fhFile, "%hhd\n", &p);
119 return *this;
120}
121Serializer &SerializerText::operator>>(int16_t &p)
122{
123 fscanf(fhFile, "%hd\n", &p);
124 return *this;
125}
126Serializer &SerializerText::operator>>(int32_t &p)
127{
128 fscanf(fhFile, "%d\n", &p);
129 return *this;
130}
131Serializer &SerializerText::operator>>(int64_t &p)
132{
133 fscanf(fhFile, "%lld\n", &p);
134 return *this;
135}
136Serializer &SerializerText::operator>>(uint8_t &p)
137{
138 fscanf(fhFile, "%hhu\n", &p);
139 return *this;
140}
141Serializer &SerializerText::operator>>(uint16_t &p)
142{
143 fscanf(fhFile, "%hu\n", &p);
144 return *this;
145}
146Serializer &SerializerText::operator>>(uint32_t &p)
147{
148 fscanf(fhFile, "%u\n", &p);
149 return *this;
150}
151Serializer &SerializerText::operator>>(uint64_t &p)
152{
153 fscanf(fhFile, "%llu\n", &p);
154 return *this;
155}
156Serializer &SerializerText::operator>>(float &p)
157{
158 fscanf(fhFile, "%f\n", &p);
159 return *this;
160}
161Serializer &SerializerText::operator>>(double &p)
162{
163 fscanf(fhFile, "%lf\n", &p);
164 return *this;
165}
166Serializer &SerializerText::operator>>(long double &p)
167{
168 fscanf(fhFile, "%Lf\n", &p);
169 return *this;
170}
diff --git a/src/old/serializertext.h b/src/old/serializertext.h
deleted file mode 100644
index 01b7f7b..0000000
--- a/src/old/serializertext.h
+++ /dev/null
@@ -1,49 +0,0 @@
1#ifndef SERIALIZER_TEXT_H
2#define SERIALIZER_TEXT_H
3
4#include "serializer.h"
5#include <stdio.h>
6
7class SerializerText : public Serializer
8{
9public:
10 SerializerText(FILE *fhFile, bool bLoading);
11 SerializerText(const char *sFileName, bool bLoading);
12 virtual ~SerializerText();
13
14 virtual void close();
15
16 virtual void write(const void *, int32_t);
17 virtual void read(void *, int32_t);
18
19 virtual Serializer &operator<<(bool);
20 virtual Serializer &operator<<(int8_t);
21 virtual Serializer &operator<<(int16_t);
22 virtual Serializer &operator<<(int32_t);
23 virtual Serializer &operator<<(int64_t);
24 virtual Serializer &operator<<(uint8_t);
25 virtual Serializer &operator<<(uint16_t);
26 virtual Serializer &operator<<(uint32_t);
27 virtual Serializer &operator<<(uint64_t);
28 virtual Serializer &operator<<(float);
29 virtual Serializer &operator<<(double);
30 virtual Serializer &operator<<(long double);
31
32 virtual Serializer &operator>>(bool &);
33 virtual Serializer &operator>>(int8_t &);
34 virtual Serializer &operator>>(int16_t &);
35 virtual Serializer &operator>>(int32_t &);
36 virtual Serializer &operator>>(int64_t &);
37 virtual Serializer &operator>>(uint8_t &);
38 virtual Serializer &operator>>(uint16_t &);
39 virtual Serializer &operator>>(uint32_t &);
40 virtual Serializer &operator>>(uint64_t &);
41 virtual Serializer &operator>>(float &);
42 virtual Serializer &operator>>(double &);
43 virtual Serializer &operator>>(long double &);
44private:
45 FILE *fhFile;
46 bool bCloseFile;
47};
48
49#endif
diff --git a/src/old/sha1.cpp b/src/old/sha1.cpp
deleted file mode 100644
index 8270c3b..0000000
--- a/src/old/sha1.cpp
+++ /dev/null
@@ -1,161 +0,0 @@
1#include <stdio.h>
2#include <string.h>
3#include <stdlib.h>
4
5#include "sha1.h"
6
7Sha1::Sha1() :
8 H0( 0x67452301 ),
9 H1( 0xefcdab89 ),
10 H2( 0x98badcfe ),
11 H3( 0x10325476 ),
12 H4( 0xc3d2e1f0 ),
13 unprocessedBytes( 0 ),
14 size( 0 )
15{
16}
17
18Sha1::~Sha1()
19{
20}
21
22void Sha1::process()
23{
24 int t;
25 uint32_t a, b, c, d, e, K, f, W[80];
26
27 // starting values
28 a = H0;
29 b = H1;
30 c = H2;
31 d = H3;
32 e = H4;
33
34 // copy and expand the message block
35 for( t = 0; t < 16; t++ ) W[t] = (bytes[t*4] << 24)
36 +(bytes[t*4 + 1] << 16)
37 +(bytes[t*4 + 2] << 8)
38 + bytes[t*4 + 3];
39 for(; t< 80; t++ ) W[t] = lrot( W[t-3]^W[t-8]^W[t-14]^W[t-16], 1 );
40
41 /* main loop */
42 uint32_t temp;
43 for( t = 0; t < 80; t++ )
44 {
45 if( t < 20 ) {
46 K = 0x5a827999;
47 f = (b & c) | ((~b) & d);
48 } else if( t < 40 ) {
49 K = 0x6ed9eba1;
50 f = b ^ c ^ d;
51 } else if( t < 60 ) {
52 K = 0x8f1bbcdc;
53 f = (b & c) | (b & d) | (c & d);
54 } else {
55 K = 0xca62c1d6;
56 f = b ^ c ^ d;
57 }
58 temp = lrot(a,5) + f + e + W[t] + K;
59 e = d;
60 d = c;
61 c = lrot(b,30);
62 b = a;
63 a = temp;
64 //printf( "t=%d %08x %08x %08x %08x %08x\n",t,a,b,c,d,e );
65 }
66
67 /* add variables */
68 H0 += a;
69 H1 += b;
70 H2 += c;
71 H3 += d;
72 H4 += e;
73
74 //printf( "Current: %08x %08x %08x %08x %08x\n",H0,H1,H2,H3,H4 );
75 /* all bytes have been processed */
76 unprocessedBytes = 0;
77}
78
79void Sha1::update( const char* data, int num )
80{
81 // add these bytes to the running total
82 size += num;
83
84 // repeat until all data is processed
85 while( num > 0 )
86 {
87 // number of bytes required to complete block
88 int needed = 64 - unprocessedBytes;
89
90 // number of bytes to copy (use smaller of two)
91 int toCopy = (num < needed) ? num : needed;
92
93 // Copy the bytes
94 memcpy( bytes + unprocessedBytes, data, toCopy );
95
96 // Bytes have been copied
97 num -= toCopy;
98 data += toCopy;
99 unprocessedBytes += toCopy;
100
101 // there is a full block
102 if( unprocessedBytes == 64 ) process();
103 }
104}
105
106unsigned char* Sha1::getDigest()
107{
108 // save the message size
109 uint32_t totalBitsL = size << 3;
110 uint32_t totalBitsH = size >> 29;
111
112 // add 0x80 to the message
113 update( "\x80", 1 );
114
115 unsigned char footer[64] = {
116 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
117 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
118 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
119 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
120
121 // block has no room for 8-byte filesize, so finish it
122 if( unprocessedBytes > 56 )
123 update( (char*)footer, 64 - unprocessedBytes);
124
125 // how many zeros do we need
126 int neededZeros = 56 - unprocessedBytes;
127
128 // store file size (in bits) in big-endian format
129 toBigEndian( totalBitsH, footer + neededZeros );
130 toBigEndian( totalBitsL, footer + neededZeros + 4 );
131
132 // finish the final block
133 update( (char*)footer, neededZeros + 8 );
134
135 // allocate memory for the digest bytes
136 unsigned char* digest = new unsigned char[20];
137
138 // copy the digest bytes
139 toBigEndian( H0, digest );
140 toBigEndian( H1, digest + 4 );
141 toBigEndian( H2, digest + 8 );
142 toBigEndian( H3, digest + 12 );
143 toBigEndian( H4, digest + 16 );
144
145 // return the digest
146 return digest;
147}
148
149uint32_t Sha1::lrot( uint32_t x, int bits )
150{
151 return (x<<bits) | (x>>(32 - bits));
152};
153
154void Sha1::toBigEndian( uint32_t num, unsigned char* byte )
155{
156 byte[0] = (unsigned char)(num>>24);
157 byte[1] = (unsigned char)(num>>16);
158 byte[2] = (unsigned char)(num>>8);
159 byte[3] = (unsigned char)num;
160}
161
diff --git a/src/old/sha1.h b/src/old/sha1.h
deleted file mode 100644
index ab6081d..0000000
--- a/src/old/sha1.h
+++ /dev/null
@@ -1,42 +0,0 @@
1/* sha1.h
2
3Copyright (c) 2005 Michael D. Leonhard
4
5http://tamale.net/
6
7This file is licensed under the terms described in the
8accompanying LICENSE file.
9*/
10
11#ifndef SHA1_H
12#define SHA1_H
13
14#include <stdint.h>
15
16/**
17 * Calculates SHA-1 sums. This is based strongly on code from Michael D.
18 * Leonhard who released his code under the terms of the MIT license, thank you!
19 */
20class Sha1
21{
22public:
23 Sha1();
24 ~Sha1();
25
26 void update( const char* data, int num );
27 unsigned char* getDigest();
28
29 // utility methods
30 static uint32_t lrot( uint32_t x, int bits );
31 static void toBigEndian( uint32_t in, unsigned char* out );
32
33private:
34 // fields
35 uint32_t H0, H1, H2, H3, H4;
36 unsigned char bytes[64];
37 int unprocessedBytes;
38 uint32_t size;
39 void process();
40};
41
42#endif
diff --git a/src/old/stack.cpp b/src/old/stack.cpp
deleted file mode 100644
index 8d9565c..0000000
--- a/src/old/stack.cpp
+++ /dev/null
@@ -1,33 +0,0 @@
1#include "stack.h"
2
3void Stack::push( void *data )
4{
5 lStackData.append( data );
6}
7
8void *Stack::top()
9{
10 return lStackData.getAt( lStackData.getSize()-1 );
11}
12
13void Stack::pop()
14{
15 lStackData.deleteAt( lStackData.getSize()-1 );
16}
17
18void *Stack::poptop()
19{
20 void *dat = top();
21 pop();
22 return dat;
23}
24
25bool Stack::isEmpty()
26{
27 return lStackData.isEmpty();
28}
29
30void Stack::empty()
31{
32 lStackData.empty();
33}
diff --git a/src/old/stack.h b/src/old/stack.h
deleted file mode 100644
index 30e2a19..0000000
--- a/src/old/stack.h
+++ /dev/null
@@ -1,50 +0,0 @@
1#ifndef STACK_H
2#define STACK_H
3#include "linkedlist.h"
4
5/** An ultra-simple stack implementation that just uses a linked list.
6 *@author Mike Buland
7 */
8class Stack
9{
10public:
11 /** Pushes a new value onto the top of the stack.
12 *@param data A new value for the stack.
13 *@author Mike Buland
14 */
15 void push( void *data );
16
17 /** Returns the top value off of the stack, but doesn't remove it from the
18 * stack.
19 *@returns The value at the top of the stack.
20 *@author Mike Buland
21 */
22 void *top();
23
24 /** Pops the top item off of the stack.
25 *@author Mike Buland
26 */
27 void pop();
28
29 /** Gets the top item off of the stack, pops it off the stack, and returns
30 * it.
31 *@returns The value at the top of the stack.
32 *@author Mike Buland
33 */
34 void *poptop();
35
36 /** Checks if the stack is empty.
37 *@returns True if the stack is empty, and false if it has things in it.
38 *@author Mike Buland
39 */
40 bool isEmpty();
41
42 /** Empty the stack.
43 *@author Mike Buland
44 */
45 void empty();
46
47private:
48 LinkedList lStackData; /**< The actual stack data. */
49};
50#endif
diff --git a/src/old/staticstring.cpp b/src/old/staticstring.cpp
deleted file mode 100644
index 60f130f..0000000
--- a/src/old/staticstring.cpp
+++ /dev/null
@@ -1,282 +0,0 @@
1#include "staticstring.h"
2#include "serializer.h"
3
4#include <stdlib.h>
5#include <stdio.h>
6#include <string.h>
7
8StaticString::StaticString()
9{
10 lpStr = NULL;
11 nLen = 0;
12}
13
14StaticString::StaticString( int nLength )
15{
16 lpStr = new char[nLength+1];
17 nLen = nLength;
18 memset( lpStr, 0, nLength+1 );
19}
20
21StaticString::StaticString( const char *lpNewStr, int nNewLen )
22{
23 lpStr = NULL;
24 nLen = 0;
25 setString( lpNewStr, nNewLen );
26}
27
28StaticString::StaticString( const char *lpNewStr )
29{
30 lpStr = NULL;
31 nLen = 0;
32 setString( lpNewStr, -1 );
33}
34
35StaticString::StaticString( StaticString &xSrcStr, int nNewLen )
36{
37 lpStr = NULL;
38 nLen = 0;
39 setString( xSrcStr, nNewLen );
40}
41
42StaticString::StaticString( StaticString &xSrcStr )
43{
44 lpStr = NULL;
45 nLen = 0;
46 setString( xSrcStr, -1 );
47}
48
49StaticString::StaticString( const StaticString &xSrcStr )
50{
51 nLen = xSrcStr.getLength();
52 lpStr = new char[nLen];
53 memcpy( lpStr, xSrcStr.getString(), nLen );
54}
55
56StaticString::~StaticString()
57{
58 if( lpStr != NULL ) delete[] lpStr;
59}
60
61char *StaticString::getString()
62{
63 return lpStr;
64}
65
66const char *StaticString::getString() const
67{
68 return lpStr;
69}
70
71int StaticString::getLength() const
72{
73 return nLen;
74}
75
76void StaticString::setLength( int nNewLength )
77{
78 char *lpNewStr = new char[nNewLength+1];
79 if( lpStr != NULL )
80 {
81 strncpy( lpNewStr, lpStr, nNewLength );
82 }
83 lpNewStr[nNewLength] = '\0';
84 if( lpStr )
85 {
86 delete[] lpStr;
87 }
88 lpStr = lpNewStr;
89 nLen = nNewLength;
90}
91
92void StaticString::setString( const char *lpNewStr, int nNewLen )
93{
94 if( lpStr )
95 {
96 delete[] lpStr;
97 lpStr = NULL;
98 nLen = 0;
99 }
100 if( nNewLen < 0 )
101 {
102 if( lpNewStr == NULL ) return;
103 nLen = strlen( lpNewStr );
104 lpStr = new char[nLen+1];
105 strcpy( lpStr, lpNewStr );
106 }
107 else
108 {
109 nLen = nNewLen;
110 lpStr = new char[nLen+1];
111 memset( lpStr, 0, nLen+1 );
112 if( lpNewStr )
113 strncpy( lpStr, lpNewStr, nNewLen );
114 }
115}
116
117void StaticString::setString( StaticString &sNewStr, int nNewLen )
118{
119 if( lpStr )
120 {
121 delete[] lpStr;
122 lpStr = NULL;
123 nLen = 0;
124 }
125 if( nNewLen < 0 )
126 {
127 if( sNewStr.lpStr == NULL ) return;
128 nLen = sNewStr.nLen;
129 lpStr = new char[nLen+1];
130 strcpy( lpStr, sNewStr.lpStr );
131 }
132 else
133 {
134 nLen = nNewLen;
135 lpStr = new char[nLen+1];
136 memset( lpStr, 0, nLen+1 );
137 if( sNewStr.lpStr )
138 strncpy( lpStr, sNewStr.lpStr, nNewLen );
139 }
140}
141
142StaticString &StaticString::operator=( StaticString &lpOtherStr )
143{
144 setString( lpOtherStr );
145
146 return *this;
147}
148
149StaticString &StaticString::operator=( std::string &lpOtherStr )
150{
151 setString( lpOtherStr.c_str() );
152
153 return *this;
154}
155
156StaticString &StaticString::operator=( const char *lpNewStr )
157{
158 setString( lpNewStr );
159
160 return *this;
161}
162
163StaticString::operator const char *()
164{
165 return lpStr;
166}
167
168char StaticString::getAt( unsigned int nIndex )
169{
170 if( nIndex < 0 || nIndex >= nLen )
171 return '\0';
172
173 return lpStr[nIndex];
174}
175
176void StaticString::setAt( unsigned int nIndex, char cVal )
177{
178 if( nIndex < 0 || nIndex >= nLen )
179 return;
180
181 lpStr[nIndex] = cVal;
182}
183
184char &StaticString::operator[]( unsigned int nIndex )
185{
186 if( nIndex < 0 || nIndex >= nLen )
187 return lpStr[0];
188
189 return lpStr[nIndex];
190}
191
192StaticString::operator int()
193{
194 return nLen;
195}
196
197char *StaticString::operator+( int nAmnt )
198{
199 return lpStr + nAmnt;
200}
201
202char *StaticString::operator-( int nAmnt )
203{
204 return lpStr - nAmnt;
205}
206
207void StaticString::clear()
208{
209 memset( lpStr, 0, nLen+1 );
210}
211
212void StaticString::serialize( Serializer &ar )
213{
214 if( ar.isLoading() )
215 {
216 ar >> nLen;
217 setLength( nLen );
218 ar.read( lpStr, nLen );
219 }
220 else
221 {
222 ar << nLen;
223 ar.write( lpStr, nLen );
224 }
225}
226
227bool StaticString::operator==( const char *str )
228{
229 const char *a = str, *b = lpStr;
230 for(; *a == *b; a++, b++ ) if( *a == '\0' && *b == '\0' ) return true;
231 return false;
232}
233
234bool StaticString::operator==( StaticString &str )
235{
236 const char *a = str.lpStr, *b = lpStr;
237 for(; *a == *b; a++, b++ ) if( *a == '\0' && *b == '\0' ) return true;
238 return false;
239}
240
241bool StaticString::operator!=( const char *str )
242{
243 const char *a = str, *b = lpStr;
244 for(; *a == *b; a++, b++ ) if( *a == '\0' && *b == '\0' ) return false;
245 return true;
246}
247
248bool StaticString::operator!=( StaticString &str )
249{
250 const char *a = str.lpStr, *b = lpStr;
251 for(; *a == *b; a++, b++ ) if( *a == '\0' && *b == '\0' ) return false;
252 return true;
253}
254/*
255unsigned long int StaticString::getHashCode()
256{
257 unsigned long int nPos = nLen;
258 unsigned long int j = 0;
259 for( const char *s = (const char *)lpStr; j< nLen; s++, j++ )
260 {
261 nPos = *s + (nPos << 6) + (nPos << 16) - nPos;
262 }
263 return nPos;
264}
265
266bool StaticString::compareForHash( Hashable &other )
267{
268 if( ((StaticString &)other).nLen != nLen )
269 return false;
270
271 const char *a = ((StaticString &)other).lpStr;
272 const char *b = lpStr;
273 if( a == b )
274 return true;
275
276 for( unsigned long j = 0; j < nLen; j++, a++, b++ )
277 if( *a != *b )
278 return false;
279
280 return true;
281}
282*/
diff --git a/src/old/staticstring.h b/src/old/staticstring.h
deleted file mode 100644
index 4c3f7b8..0000000
--- a/src/old/staticstring.h
+++ /dev/null
@@ -1,63 +0,0 @@
1#ifndef STATIC_STRING_H
2#define STATIC_STRING_H
3
4#include <string>
5#include "serializable.h"
6//#include "hashable.h"
7
8/**
9 * Simple string managing class. Allows for dynamically allocated string data
10 * along with some minor caching to speed things up when accessing your
11 * string data. Really designed for making copies of strings easy and safe,
12 * and making accessing meta-info like length fast and reliable as well.
13 *@author Mike Buland
14 */
15class StaticString : public Serializable/*, public Hashable*/
16{
17public:
18 StaticString();
19 StaticString( const char *lpNewStr, int nNewLen );
20 StaticString( const char *lpNewStr );
21 StaticString( StaticString &xSrcStr, int nNewLen );
22 StaticString( StaticString &xSrcStr );
23 StaticString( const StaticString &xSrcStr );
24 StaticString( int nLength );
25 virtual ~StaticString();
26
27 char *getString();
28 const char *getString() const;
29 int getLength() const;
30 void setLength( int nNewLength );
31
32 void setString( const char *lpNewStr, int nNewLen=-1 );
33 void setString( StaticString &sNewStr, int nNewLen=-1 );
34
35 char getAt( unsigned int nIndex );
36 void setAt( unsigned int nIndex, char cVal );
37
38 class StaticString &operator=( class StaticString &lpOtherStr );
39 class StaticString &operator=( std::string &lpOtherStr );
40 class StaticString &operator=( const char *lpNewStr );
41 operator const char *();
42 char &operator[]( unsigned int nIndex );
43 operator int();
44 char *operator+( int nAmnt );
45 char *operator-( int nAmnt );
46 bool operator==( const char *str );
47 bool operator==( StaticString &str );
48 bool operator!=( const char *str );
49 bool operator!=( StaticString &str );
50
51 void clear();
52
53 virtual void serialize( class Serializer &ar );
54
55 //virtual unsigned long int getHashCode();
56 //virtual bool compareForHash( Hashable &other );
57
58private:
59 char *lpStr;
60 uint32_t nLen;
61};
62
63#endif
diff --git a/src/old/stringrep.cpp b/src/old/stringrep.cpp
deleted file mode 100644
index a505f8a..0000000
--- a/src/old/stringrep.cpp
+++ /dev/null
@@ -1,19 +0,0 @@
1#include "stringrep.h"
2
3int32_t stringlen( const char *s )
4{
5 for( int32_t i = 0;; i++ )
6 if( !s[i] )
7 return i;
8}
9
10char *stringdup( const char *s )
11{
12 int len = stringlen( s );
13 char *r = new char[len+1];
14 for( int j = 0; j <= len; j++ )
15 r[j] = s[j];
16
17 return r;
18}
19
diff --git a/src/old/stringrep.h b/src/old/stringrep.h
deleted file mode 100644
index eaa4a12..0000000
--- a/src/old/stringrep.h
+++ /dev/null
@@ -1,17 +0,0 @@
1#ifndef STRING_REP_H
2#define STRING_REP_H
3
4#include <stdint.h>
5
6/**
7 * Calculates the length of a string.
8 */
9int32_t stringlen( const char *s );
10
11/**
12 * Identicle to strdup, which isn't available everywhere, but uses c++ memory
13 * facilities. Remember to use delete[] when freeing the returned string.
14 */
15char *stringdup( const char *s );
16
17#endif
diff --git a/src/old/tests/clistress.cpp b/src/old/tests/clistress.cpp
deleted file mode 100644
index 6b0ac66..0000000
--- a/src/old/tests/clistress.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
1#include "connection.h"
2
3int main()
4{
5 Connection c;
6
7 c.open("localhost", 4001 );
8
9 c.appendOutput("w");
10 c.writeOutput();
11
12 c.waitForInput( 6, 5, 0 );
13
14 printf("read: %s\n", c.getInput() );
15
16 c.close();
17
18 return 0;
19}
20
diff --git a/src/old/tests/confpair.cpp b/src/old/tests/confpair.cpp
deleted file mode 100644
index fb1b0d3..0000000
--- a/src/old/tests/confpair.cpp
+++ /dev/null
@@ -1,19 +0,0 @@
1#include "confpair.h"
2#include <iostream>
3
4using namespace std;
5
6int main()
7{
8 ConfPair<float> p1("DebugMode");
9 p1.value() = 12;
10 cout << p1.value() << "\n";
11 p1.value() = 55;
12 cout << p1.value() << "\n";
13
14 ConfPairBase &p = p1;
15
16 p = "33.12";
17 cout << p.getAsString();
18}
19
diff --git a/src/old/tests/connect.cpp b/src/old/tests/connect.cpp
deleted file mode 100644
index a9fca64..0000000
--- a/src/old/tests/connect.cpp
+++ /dev/null
@@ -1,38 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include <unistd.h>
4#include <fcntl.h>
5#include "connection.h"
6
7int main()
8{
9 Connection c;
10 c.open("127.0.0.1", 12457 );
11
12 {
13 int newSocket = c.getSocket();
14 int flags;
15
16 flags = fcntl(newSocket, F_GETFL, 0);
17 flags |= O_NONBLOCK;
18 if (fcntl(newSocket, F_SETFL, flags) < 0)
19 {
20 return false;
21 }
22 }
23
24 for( int i = 0; i < 50; i++ )
25 {
26 usleep( 100000 );
27 int nbytes = c.readInput();
28 if( nbytes == 0 )
29 printf("0 bytes, EOF?\n");
30 else
31 printf("Got %d bytes, whacky...\n", nbytes );
32 }
33
34 c.close();
35
36 return 0;
37}
38
diff --git a/src/old/tests/exception.cpp b/src/old/tests/exception.cpp
deleted file mode 100644
index 6417692..0000000
--- a/src/old/tests/exception.cpp
+++ /dev/null
@@ -1,16 +0,0 @@
1#include <iostream>
2#include "exceptions.h"
3
4int main()
5{
6 try
7 {
8 throw ExceptionBase( 42, "There was an error on line: %d", __LINE__ );
9 }
10 catch( ExceptionBase &e )
11 {
12 std::cout << "Error "<< e.getErrorCode() << ": " << e.what() << "\n";
13 }
14
15 throw ExceptionBase( 112, "This exception wasn't caught!");
16}
diff --git a/src/old/tests/formula.cpp b/src/old/tests/formula.cpp
deleted file mode 100644
index 976b039..0000000
--- a/src/old/tests/formula.cpp
+++ /dev/null
@@ -1,13 +0,0 @@
1#include "formula.h"
2
3int main( int argc, char *argv[] )
4{
5 if( argc < 2 ) return 0;
6
7 Formula f;
8 double dOut = f.run( argv[1] );
9 printf("%s = %f\n", argv[1], dOut );
10
11 return 0;
12}
13
diff --git a/src/old/tests/hash.cpp b/src/old/tests/hash.cpp
deleted file mode 100644
index 2fc6968..0000000
--- a/src/old/tests/hash.cpp
+++ /dev/null
@@ -1,116 +0,0 @@
1#include "hash.h"
2#include "staticstring.h"
3
4int main()
5{
6 const char *names[]={
7 "Homer the Great",
8 "And Maggie Makes Three",
9 "Bart's Comet",
10 "Homie The Clown",
11 "Bart Vs Australia",
12 "Homer vs Patty and Selma",
13 "A star is burns",
14 "Lisa's Wedding",
15 "Two Dozen and One Greyhounds",
16 "The PTA Disbands",
17 "Round Springfield",
18 "The Springfield connection",
19 "Lemon of Troy",
20 "Who Shot Mr. Burns (Pt. 1)",
21 "Who Shot Mr. Burns (pt. 2)",
22 "Radioactive Man",
23 "Home Sweet Homediddly-dum-doodly",
24 "Bart Sells His Soul",
25 "Lisa the Vegetarian",
26 "Treehouse of horror VI",
27 "King Size Homer",
28 "Mother Simpson",
29 "Sideshow Bob's Last Gleaming",
30 "The Simpson's 138th Show Spectacular",
31 "Marge Be Not Proud",
32 "Team Homer",
33 "Two Bad Neighbors",
34 "Scenes From the Class Struggle in Springfield",
35 "Bart the Fink",
36 "Lisa the Iconoclast",
37 "Homer the Smithers",
38 "The Day the Violence Died",
39 "A Fish Called Selma",
40 "Bart on the road",
41 "22 Short Films about Springfield",
42 "The Curse of the Flying Hellfish",
43 "Much Apu about Nothing",
44 "Homerpalooza",
45 "The Summer of 4 Ft 2",
46 "Treehouse of Horror VII",
47 "You Only Move Twice",
48 "The Homer They Fall",
49 "Burns Baby Burns",
50 "Bart After Dark",
51 "A Millhouse Divided",
52 "Lisas Date With Destiny",
53 "Hurricane Neddy",
54 "The Mysterious Voyage of Our Homer",
55 "The Springfield Files",
56 "The Twisted World of Marge Simpson",
57 "Mountain of Madness",
58 NULL
59 };
60
61 Hash<const char *, int> sTest;
62
63 printf("Inserting\n-------------------\n\n");
64 for( int j = 0; j < 33; j++ )
65 {
66 sTest[names[j]] = j;
67 }
68
69 printf("Test1: %d, Test2: %d\n", sTest.has("Lemon of Troy"), sTest.has(std::string("Lemon of Troy").c_str() ) );
70
71 sTest.has(std::string("Lemon of Troy").c_str() );
72
73 printf("Getting\n-------------------\n\n");
74
75 sTest.erase("Homer the Great");
76 sTest["Bart's Comet"].erase();
77
78 for( Hash<const char *, int>::iterator i = sTest.begin();
79 i != sTest.end(); i++ )
80 {
81 Hash<const char *, int>::iterator j = i;
82 printf("%d: %s\n", (*j).second, (*j).first );
83 }
84
85 printf("Testing\n-------------------\n\n");
86 for( int j = 0; j < 33; j++ )
87 {
88 if( sTest.has(names[j]) )
89 {
90 if( sTest[names[j]] != j )
91 {
92 printf("'%s' should be %d, is %d\n",
93 names[j], j,
94 sTest[names[j]].value()
95 );
96 }
97 }
98 else
99 {
100 printf("Missing element %d, '%s'\n", j, names[j] );
101 }
102 }
103
104 printf("Clearing\n-------------------\n\n");
105
106 sTest.clear();
107
108 for( Hash<const char *, int>::iterator i = sTest.begin();
109 i != sTest.end(); i++ )
110 {
111 Hash<const char *, int>::iterator j = i;
112 printf("%d: %s\n", (*j).second, (*j).first );
113 }
114
115}
116
diff --git a/src/old/tests/hashtest.cpp b/src/old/tests/hashtest.cpp
deleted file mode 100644
index eaa84a0..0000000
--- a/src/old/tests/hashtest.cpp
+++ /dev/null
@@ -1,107 +0,0 @@
1#include <stdio.h>
2#include <iostream>
3#include "hashtable.h"
4#include "hashfunctioncasestring.h"
5
6int main()
7{
8 const char *names[]={
9 "Homer the Great",
10 "And Maggie Makes Three",
11 "Bart's Comet",
12 "Homie The Clown",
13 "Bart Vs Australia",
14 "Homer vs Patty and Selma",
15 "A star is burns",
16 "Lisa's Wedding",
17 "Two Dozen and One Greyhounds",
18 "The PTA Disbands",
19 "Round Springfield",
20 "The Springfield connection",
21 "Lemon of Troy",
22 "Who Shot Mr. Burns (Pt. 1)",
23 "Who Shot Mr. Burns (pt. 2)",
24 "Radioactive Man",
25 "Home Sweet Homediddly-dum-doodly",
26 "Bart Sells His Soul",
27 "Lisa the Vegetarian",
28 "Treehouse of horror VI",
29 "King Size Homer",
30 "Mother Simpson",
31 "Sideshow Bob's Last Gleaming",
32 "The Simpson's 138th Show Spectacular",
33 "Marge Be Not Proud",
34 "Team Homer",
35 "Two Bad Neighbors",
36 "Scenes From the Class Struggle in Springfield",
37 "Bart the Fink",
38 "Lisa the Iconoclast",
39 "Homer the Smithers",
40 "The Day the Violence Died",
41 "A Fish Called Selma",
42 "Bart on the road",
43 "22 Short Films about Springfield",
44 "The Curse of the Flying Hellfish",
45 "Much Apu about Nothing",
46 "Homerpalooza",
47 "The Summer of 4 Ft 2",
48 "Treehouse of Horror VII",
49 "You Only Move Twice",
50 "The Homer They Fall",
51 "Burns Baby Burns",
52 "Bart After Dark",
53 "A Millhouse Divided",
54 "Lisas Date With Destiny",
55 "Hurricane Neddy",
56 "The Mysterious Voyage of Our Homer",
57 "The Springfield Files",
58 "The Twisted World of Marge Simpson",
59 "Mountain of Madness",
60 NULL
61 };
62
63 HashTable h( new HashFunctionCaseString(), 5, false );
64
65 int j;
66 printf("Inserting...\n");
67 for( j = 0; j < 10; j++ )
68 {
69 h.insert( names[j], (void *)(j+1) );
70 h.insert( names[j], (void *)(j+1) );
71 printf("Capacity: %lu, Size: %lu, Load: %f\n",
72 h.getCapacity(),
73 h.getSize(),
74 h.getLoad()
75 );
76 }
77
78 for( j = 0; j < 10; j++ )
79 {
80 printf("\"%s\" = %d\n", names[j], (int)h[names[j]] );
81 }
82
83 printf("\nDeleting some...\n");
84
85 for( int k = 0; k < 7; k++ )
86 {
87 h.del( names[k] );
88 //h.insert( names[j], (void *)(j+1) );
89 printf("Capacity: %lu, Size: %lu, Load: %f\n",
90 h.getCapacity(),
91 h.getSize(),
92 h.getLoad()
93 );
94 }
95
96 printf("\nInserting more...\n");
97
98 for( ; names[j] != NULL; j++ )
99 {
100 h.insert( names[j], (void *)(j+1) );
101 printf("Capacity: %lu, Size: %lu, Load: %f\n",
102 h.getCapacity(),
103 h.getSize(),
104 h.getLoad()
105 );
106 }
107}
diff --git a/src/old/tests/hashtest2.cpp b/src/old/tests/hashtest2.cpp
deleted file mode 100644
index 74700fd..0000000
--- a/src/old/tests/hashtest2.cpp
+++ /dev/null
@@ -1,15 +0,0 @@
1#include "hash.h"
2#include <string.h>
3
4int main()
5{
6 char *a, *b;
7 a = new char[10];
8 b = new char[10];
9 strcpy( a, "Hey there");
10 strcpy( b, "Hey there");
11 printf("Same: %s\n", __cmpHashKeys( a, b )?"yes":"no");
12
13 return 0;
14}
15
diff --git a/src/old/tests/httpsrv/httpconnectionmonitor.cpp b/src/old/tests/httpsrv/httpconnectionmonitor.cpp
deleted file mode 100644
index 51d82f3..0000000
--- a/src/old/tests/httpsrv/httpconnectionmonitor.cpp
+++ /dev/null
@@ -1,88 +0,0 @@
1#include "httpconnectionmonitor.h"
2#include "http.h"
3#include "exceptions.h"
4#include <sys/stat.h>
5
6HttpConnectionMonitor::HttpConnectionMonitor()
7{
8}
9
10HttpConnectionMonitor::~HttpConnectionMonitor()
11{
12}
13
14bool HttpConnectionMonitor::onNewConnection( Connection *pCon, int nPort )
15{
16 printf("Got connection on port %d\n", nPort );
17
18 try
19 {
20 pCon->readInput( 60, 0 );
21 printf("#######################\n%s\n#######################\n", pCon->getInput() );
22
23 Http hp( pCon );
24 while( hp.parseRequest() == false );
25 printf("Done parsing.\n\n");
26
27 if( hp.getRequestType() == Http::reqGet )
28 {
29 printf("\"\"\"%s\"\"\"\n", hp.getRequestURI() );
30 if( !strcmp( hp.getRequestURI(), "/" ) )
31 {
32 std::string content("<html><head><title>Server Test</test></head><body>This is a test of a new system where all the pages will be more or less dynamic...<br>If you want to try to login, you can do that here:<br><form method=\"post\" action=\"showvars\" enctype=\"multipart/form-data\">Name: <input type=\"text\" name=\"name\"><br>Password: <input type=\"password\" name=\"pass\"><br><input type=\"submit\" name=\"action\" value=\"login\"></form></body></html>");
33 hp.buildResponse();
34 hp.setResponseContent(
35 "text/html",
36 content.c_str(),
37 content.size()
38 );
39 hp.sendResponse();
40 }
41 else
42 {
43 std::string content("<html><head><title>URL Not Found</test></head><body>There is no content mapped to the URL you requested. Please try another one.</body></html>");
44 hp.buildResponse( 404, "File not found.");
45 hp.setResponseContent(
46 "text/html",
47 content.c_str(),
48 content.size()
49 );
50 hp.sendResponse();
51 }
52 }
53 else
54 {
55 printf("Non get: %s\n", hp.getRequestTypeStr() );
56 pCon->appendOutput("HTTP/1.1 100 Continue\r\n\r\n");
57 }
58 pCon->writeOutput();
59 //for( int j = 0; j < 50; j++ )
60 {
61 pCon->readInput( 1, 0 );
62 //printf("Size so far: %d\n", pCon->getInputAmnt() );
63 }
64
65 if( pCon->hasInput() )
66 {
67 std::string s( pCon->getInput(), pCon->getInputAmnt() );
68
69 pCon->printInputDebug();
70 //printf("Reamining data\n==============\n%s\n==============\n",
71 // s.c_str() );
72 }
73
74 pCon->disconnect();
75 }
76 catch( ConnectionException &e )
77 {
78 printf("Connection: %s\n", e.what() );
79 }
80
81 return true;
82}
83
84bool HttpConnectionMonitor::onClosedConnection( Connection *pCon )
85{
86 return true;
87}
88
diff --git a/src/old/tests/httpsrv/httpconnectionmonitor.h b/src/old/tests/httpsrv/httpconnectionmonitor.h
deleted file mode 100644
index 30c0afd..0000000
--- a/src/old/tests/httpsrv/httpconnectionmonitor.h
+++ /dev/null
@@ -1,16 +0,0 @@
1#ifndef HTTPCONNECTIONMONITOR_H
2#define HTTPCONNECTIONMONITOR_H
3
4#include "connectionmonitor.h"
5
6class HttpConnectionMonitor : public ConnectionMonitor
7{
8public:
9 HttpConnectionMonitor();
10 ~HttpConnectionMonitor();
11
12 bool onNewConnection( Connection *pCon, int nPort );
13 bool onClosedConnection( Connection *pCon );
14};
15
16#endif
diff --git a/src/old/tests/httpsrv/main.cpp b/src/old/tests/httpsrv/main.cpp
deleted file mode 100644
index 2f1563c..0000000
--- a/src/old/tests/httpsrv/main.cpp
+++ /dev/null
@@ -1,22 +0,0 @@
1#include "connectionmanager.h"
2#include "httpconnectionmonitor.h"
3
4int main()
5{
6 printf("Starting server...\n");
7
8 ConnectionManager srv;
9 HttpConnectionMonitor http;
10
11 srv.setConnectionMonitor( &http );
12
13 printf("Listening on port 7331\n");
14 srv.startServer( 7331 );
15
16 for(;;)
17 {
18 srv.scanConnections( 5000, false );
19 }
20
21 return 0;
22}
diff --git a/src/old/tests/log.cpp b/src/old/tests/log.cpp
deleted file mode 100644
index d7cfa0b..0000000
--- a/src/old/tests/log.cpp
+++ /dev/null
@@ -1,29 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include <iostream>
4#include "multilog.h"
5#include "multilogtext.h"
6
7class Test
8{
9public:
10 Test()
11 {
12 MultiLineLog( 4, "Test init'd\n");
13 }
14};
15
16int main()
17{
18 MultiLog &xLog = MultiLog::getInstance();
19
20 xLog.LineLog( 2, "Hello again");
21
22 MultiLog::getInstance().addChannel(
23 new MultiLogText( STDOUT_FILENO, "%02y-%02m-%02d %02h:%02M:%02s: %t" )
24 );
25
26 MultiLineLog( MultiLog::LError, "Hi there!");
27 Test t;
28}
29
diff --git a/src/old/tests/md5test.cpp b/src/old/tests/md5test.cpp
deleted file mode 100644
index 6f832df..0000000
--- a/src/old/tests/md5test.cpp
+++ /dev/null
@@ -1,19 +0,0 @@
1#include <stdio.h>
2#include <string.h>
3#include "md5.h"
4
5int main()
6{
7 md5 mproc;
8 md5sum sum;
9 char hexstr[33];
10
11 memset( hexstr, 0, 33 );
12
13 mproc.sumString( &sum, "qwertyuiopasdfgh" );
14 mproc.sumToHex( &sum, hexstr );
15 printf("sum: %s\n", hexstr );
16 printf("chk: 1ebfc043d8880b758b13ddc8aa1638ef\n");
17
18 return 0;
19}
diff --git a/src/old/tests/ordhash.cpp b/src/old/tests/ordhash.cpp
deleted file mode 100644
index f1d96ec..0000000
--- a/src/old/tests/ordhash.cpp
+++ /dev/null
@@ -1,48 +0,0 @@
1#include "ordhash.h"
2#include <string>
3
4typedef struct eldef
5{
6 eldef( int a, int b, const std::string &c ) :
7 id( a ), nSequence( b ), sName( c ) {}
8 int id;
9 int nSequence;
10 std::string sName;
11} eldef;
12
13struct seqcmp
14{
15 bool operator()( eldef **a, eldef **b )
16 {
17 return (*a)->nSequence < (*b)->nSequence;
18 }
19};
20
21struct namcmp
22{
23 bool operator()( eldef **a, eldef **b )
24 {
25 return (*a)->sName < (*b)->sName;
26 }
27};
28
29typedef OrdHash<int, eldef, seqcmp> AHash;
30//typedef OrdHash<int, eldef, namcmp> AHash;
31
32int main()
33{
34 AHash hsh;
35 hsh[1] = eldef( 0, 43, "Bob");
36 hsh[4] = eldef( 1, 443, "Abby");
37 hsh[2] = eldef( 2, 1, "Name");
38 hsh[5] = eldef( 3, 0, "Catagory");
39 hsh[32] = eldef( 4, 12, "Epilogue");
40
41 for( AHash::iterator i = hsh.begin(); i != hsh.end(); i++ )
42 {
43 eldef e = (*i).second;
44 printf("%d, %d, %s\n", e.id, e.nSequence, e.sName.c_str() );
45 }
46
47}
48
diff --git a/src/old/tests/param.cpp b/src/old/tests/param.cpp
deleted file mode 100644
index a4d2824..0000000
--- a/src/old/tests/param.cpp
+++ /dev/null
@@ -1,46 +0,0 @@
1#include "param.h"
2#include <stdio.h>
3
4Param::Param()
5{
6 addHelpBanner("param - A test of the libbu++ parameter systems\n"
7 "Enjoy with care and caution\n\nTest stuff:\n");
8 addParam( "name", 's', mkproc( Param::printStuff ), &str, "Test a param param" );
9 //addParam( "name", &str );
10 addParam( "job", 'U', mkproc( Param::printStuff ), "Test a paramless param" );
11
12 addHelpBanner("\nInformational:\n");
13 addParam( "help", mkproc( ParamProc::help ), "Help!" );
14
15 addHelpBanner("\nThanks for trying my test!\n\n");
16}
17
18Param::~Param()
19{
20}
21
22int Param::printStuff( int argc, char *argv[] )
23{
24 printf("------------%02d-------------\n", argc );
25 for( int j = 0; j < argc; j++ )
26 {
27 printf("%d: %s\n", j, argv[j] );
28 }
29 printf("---------------------------\n" );
30 printf("SETVAR===\"%s\"\n", str.c_str() );
31
32 return 1;
33}
34
35int main( int argc, char *argv[] )
36{
37 if( argc == 1 )
38 {
39 printf("You have to enter some parameter, try '--help'\n\n");
40 return 0;
41 }
42
43 Param p;
44 p.process( argc, argv );
45}
46
diff --git a/src/old/tests/param.h b/src/old/tests/param.h
deleted file mode 100644
index 2756b69..0000000
--- a/src/old/tests/param.h
+++ /dev/null
@@ -1,21 +0,0 @@
1#ifndef PARAM_H
2#define PARAM_H
3
4#include <stdint.h>
5
6#include "paramproc.h"
7
8class Param : public ParamProc
9{
10public:
11 Param();
12 virtual ~Param();
13
14private:
15 int printStuff( int argc, char *argv[] );
16
17 std::string str;
18 uint32_t uint32;
19};
20
21#endif
diff --git a/src/old/tests/plugin/main.cpp b/src/old/tests/plugin/main.cpp
deleted file mode 100644
index 51c8390..0000000
--- a/src/old/tests/plugin/main.cpp
+++ /dev/null
@@ -1,14 +0,0 @@
1#include "plugger.h"
2#include "plugin.h"
3
4int main()
5{
6 Plugger<Plugin> p;
7
8 p.registerExternalPlugin( "./guy.so", "Guy" );
9
10 Plugin *t = p.instantiate( "Guy" );
11
12 p.destroy( t );
13}
14
diff --git a/src/old/tests/plugin/plugin.cpp b/src/old/tests/plugin/plugin.cpp
deleted file mode 100644
index ea558fd..0000000
--- a/src/old/tests/plugin/plugin.cpp
+++ /dev/null
@@ -1,10 +0,0 @@
1#include "plugin.h"
2
3Plugin::Plugin()
4{
5}
6
7Plugin::~Plugin()
8{
9}
10
diff --git a/src/old/tests/plugin/plugin.h b/src/old/tests/plugin/plugin.h
deleted file mode 100644
index f726867..0000000
--- a/src/old/tests/plugin/plugin.h
+++ /dev/null
@@ -1,14 +0,0 @@
1#ifndef PLUGIN_H
2#define PLUGIN_H
3
4class Plugin
5{
6public:
7 Plugin();
8 virtual ~Plugin();
9
10private:
11
12};
13
14#endif
diff --git a/src/old/tests/qsort.cpp b/src/old/tests/qsort.cpp
deleted file mode 100644
index 28c6f03..0000000
--- a/src/old/tests/qsort.cpp
+++ /dev/null
@@ -1,228 +0,0 @@
1#define _QSORT_SWAP(a, b, t) ((void)((t = *a), (*a = *b), (*b = t)))
2
3/* Discontinue quicksort algorithm when partition gets below this size.
4 This particular magic number was chosen to work best on a Sun 4/260. */
5#define _QSORT_MAX_THRESH 4
6
7/* Stack node declarations used to store unfulfilled partition obligations
8 * (inlined in QSORT).
9typedef struct {
10 QSORT_TYPE *_lo, *_hi;
11} qsort_stack_node;
12 */
13
14/* The next 4 #defines implement a very fast in-line stack abstraction. */
15/* The stack needs log (total_elements) entries (we could even subtract
16 log(MAX_THRESH)). Since total_elements has type unsigned, we get as
17 upper bound for log (total_elements):
18 bits per byte (CHAR_BIT) * sizeof(unsigned). */
19#define _QSORT_STACK_SIZE (8 * sizeof(unsigned))
20#define _QSORT_PUSH(top, low, high) \
21 (((top->_lo = (low)), (top->_hi = (high)), ++top))
22#define _QSORT_POP(low, high, top) \
23 ((--top, (low = top->_lo), (high = top->_hi)))
24#define _QSORT_STACK_NOT_EMPTY (_stack < _top)
25
26
27/* Order size using quicksort. This implementation incorporates
28 four optimizations discussed in Sedgewick:
29
30 1. Non-recursive, using an explicit stack of pointer that store the
31 next array partition to sort. To save time, this maximum amount
32 of space required to store an array of SIZE_MAX is allocated on the
33 stack. Assuming a 32-bit (64 bit) integer for size_t, this needs
34 only 32 * sizeof(stack_node) == 256 bytes (for 64 bit: 1024 bytes).
35 Pretty cheap, actually.
36
37 2. Chose the pivot element using a median-of-three decision tree.
38 This reduces the probability of selecting a bad pivot value and
39 eliminates certain extraneous comparisons.
40
41 3. Only quicksorts TOTAL_ELEMS / MAX_THRESH partitions, leaving
42 insertion sort to order the MAX_THRESH items within each partition.
43 This is a big win, since insertion sort is faster for small, mostly
44 sorted array segments.
45
46 4. The larger of the two sub-partitions is always pushed onto the
47 stack first, with the algorithm then concentrating on the
48 smaller partition. This *guarantees* no more than log (total_elems)
49 stack size is needed (actually O(1) in this case)! */
50
51/* The main code starts here... */
52
53template<typename QSORT_TYPE, typename QSORT_LTT>
54void qsrt( QSORT_TYPE *QSORT_BASE, int QSORT_NELT )
55{
56 QSORT_LTT QSORT_LT;
57 QSORT_TYPE *const _base = (QSORT_BASE);
58 const unsigned _elems = (QSORT_NELT);
59 QSORT_TYPE _hold;
60
61 /* Don't declare two variables of type QSORT_TYPE in a single
62 * statement: eg `TYPE a, b;', in case if TYPE is a pointer,
63 * expands to `type* a, b;' wich isn't what we want.
64 */
65
66 if (_elems > _QSORT_MAX_THRESH) {
67 QSORT_TYPE *_lo = _base;
68 QSORT_TYPE *_hi = _lo + _elems - 1;
69 struct {
70 QSORT_TYPE *_hi; QSORT_TYPE *_lo;
71 } _stack[_QSORT_STACK_SIZE], *_top = _stack + 1;
72
73 while (_QSORT_STACK_NOT_EMPTY) {
74 QSORT_TYPE *_left_ptr; QSORT_TYPE *_right_ptr;
75
76 /* Select median value from among LO, MID, and HI. Rearrange
77 LO and HI so the three values are sorted. This lowers the
78 probability of picking a pathological pivot value and
79 skips a comparison for both the LEFT_PTR and RIGHT_PTR in
80 the while loops. */
81
82 QSORT_TYPE *_mid = _lo + ((_hi - _lo) >> 1);
83
84 if (QSORT_LT (_mid, _lo))
85 _QSORT_SWAP (_mid, _lo, _hold);
86 if (QSORT_LT (_hi, _mid))
87 _QSORT_SWAP (_mid, _hi, _hold);
88 else
89 goto _jump_over;
90 if (QSORT_LT (_mid, _lo))
91 _QSORT_SWAP (_mid, _lo, _hold);
92 _jump_over:;
93
94 _left_ptr = _lo + 1;
95 _right_ptr = _hi - 1;
96
97 /* Here's the famous ``collapse the walls'' section of quicksort.
98 Gotta like those tight inner loops! They are the main reason
99 that this algorithm runs much faster than others. */
100 do {
101 while (QSORT_LT (_left_ptr, _mid))
102 ++_left_ptr;
103
104 while (QSORT_LT (_mid, _right_ptr))
105 --_right_ptr;
106
107 if (_left_ptr < _right_ptr) {
108 _QSORT_SWAP (_left_ptr, _right_ptr, _hold);
109 if (_mid == _left_ptr)
110 _mid = _right_ptr;
111 else if (_mid == _right_ptr)
112 _mid = _left_ptr;
113 ++_left_ptr;
114 --_right_ptr;
115 }
116 else if (_left_ptr == _right_ptr) {
117 ++_left_ptr;
118 --_right_ptr;
119 break;
120 }
121 } while (_left_ptr <= _right_ptr);
122
123 /* Set up pointers for next iteration. First determine whether
124 left and right partitions are below the threshold size. If so,
125 ignore one or both. Otherwise, push the larger partition's
126 bounds on the stack and continue sorting the smaller one. */
127
128 if (_right_ptr - _lo <= _QSORT_MAX_THRESH) {
129 if (_hi - _left_ptr <= _QSORT_MAX_THRESH)
130 /* Ignore both small partitions. */
131 _QSORT_POP (_lo, _hi, _top);
132 else
133 /* Ignore small left partition. */
134 _lo = _left_ptr;
135 }
136 else if (_hi - _left_ptr <= _QSORT_MAX_THRESH)
137 /* Ignore small right partition. */
138 _hi = _right_ptr;
139 else if (_right_ptr - _lo > _hi - _left_ptr) {
140 /* Push larger left partition indices. */
141 _QSORT_PUSH (_top, _lo, _right_ptr);
142 _lo = _left_ptr;
143 }
144 else {
145 /* Push larger right partition indices. */
146 _QSORT_PUSH (_top, _left_ptr, _hi);
147 _hi = _right_ptr;
148 }
149 }
150 }
151
152 /* Once the BASE array is partially sorted by quicksort the rest
153 is completely sorted using insertion sort, since this is efficient
154 for partitions below MAX_THRESH size. BASE points to the
155 beginning of the array to sort, and END_PTR points at the very
156 last element in the array (*not* one beyond it!). */
157
158 {
159 QSORT_TYPE *const _end_ptr = _base + _elems - 1;
160 QSORT_TYPE *_tmp_ptr = _base;
161 register QSORT_TYPE *_run_ptr;
162 QSORT_TYPE *_thresh;
163
164 _thresh = _base + _QSORT_MAX_THRESH;
165 if (_thresh > _end_ptr)
166 _thresh = _end_ptr;
167
168 /* Find smallest element in first threshold and place it at the
169 array's beginning. This is the smallest array element,
170 and the operation speeds up insertion sort's inner loop. */
171
172 for (_run_ptr = _tmp_ptr + 1; _run_ptr <= _thresh; ++_run_ptr)
173 if (QSORT_LT (_run_ptr, _tmp_ptr))
174 _tmp_ptr = _run_ptr;
175
176 if (_tmp_ptr != _base)
177 _QSORT_SWAP (_tmp_ptr, _base, _hold);
178
179 /* Insertion sort, running from left-hand-side
180 * up to right-hand-side. */
181
182 _run_ptr = _base + 1;
183 while (++_run_ptr <= _end_ptr) {
184 _tmp_ptr = _run_ptr - 1;
185 while (QSORT_LT (_run_ptr, _tmp_ptr))
186 --_tmp_ptr;
187
188 ++_tmp_ptr;
189 if (_tmp_ptr != _run_ptr) {
190 QSORT_TYPE *_trav = _run_ptr + 1;
191 while (--_trav >= _run_ptr) {
192 QSORT_TYPE *_hi; QSORT_TYPE *_lo;
193 _hold = *_trav;
194
195 for (_hi = _lo = _trav; --_lo >= _tmp_ptr; _hi = _lo)
196 *_hi = *_lo;
197 *_hi = _hold;
198 }
199 }
200 }
201 }
202
203}
204
205
206struct cc
207{
208 bool operator()( int *a, int *b )
209 {
210 return *a < *b;
211 }
212};
213
214#include <stdio.h>
215
216int main()
217{
218 int lst[] = { 43, 1, 342, 12, 491, 32, 12321, 32, 3, -3 };
219
220 for( int j = 0; j < 10; j++ )
221 printf("%s%d", (j>0)?", ":"", lst[j] );
222 printf("\n");
223 qsrt<int, cc>( lst, 10 );
224 for( int j = 0; j < 10; j++ )
225 printf("%s%d", (j>0)?", ":"", lst[j] );
226 printf("\n");
227}
228
diff --git a/src/old/tests/sbuffer.cpp b/src/old/tests/sbuffer.cpp
deleted file mode 100644
index 02798cb..0000000
--- a/src/old/tests/sbuffer.cpp
+++ /dev/null
@@ -1,27 +0,0 @@
1#include "sbuffer.h"
2
3int main()
4{
5 SBuffer buf;
6
7 buf.write("abcdefg", 7 );
8
9 printf("tell: %ld\n", buf.tell() );
10
11 char abuf[6];
12 int nRead;
13 nRead = buf.read( abuf, 5 );
14 abuf[nRead] = '\0';
15 printf("Read %d bytes \"%s\"\n", nRead, abuf );
16
17 buf.setPos( 0 );
18 nRead = buf.read( abuf, 5 );
19 abuf[nRead] = '\0';
20 printf("Read %d bytes \"%s\"\n", nRead, abuf );
21
22 nRead = buf.read( abuf, 5 );
23 abuf[nRead] = '\0';
24 printf("Read %d bytes \"%s\"\n", nRead, abuf );
25
26}
27
diff --git a/src/old/tests/serialize.cpp b/src/old/tests/serialize.cpp
deleted file mode 100644
index e233704..0000000
--- a/src/old/tests/serialize.cpp
+++ /dev/null
@@ -1,30 +0,0 @@
1#include "serializerbinary.h"
2#include "staticstring.h"
3#include <stdio.h>
4#include <string>
5
6int main()
7{
8 int32_t one;
9 double two;
10 bool three;
11 StaticString s("Test string!");
12 std::string ss("Another test string");
13 SerializerBinary ar("hello.dat", false);
14 ar << (int)85;
15 ar << (double)2.63434;
16 ar << false;
17 ar << ss;
18 ar.close();
19
20 one = 0; two = 0; three = true; s = "die";
21
22 SerializerBinary ar2("hello.dat", true);
23 ar2 >> one;
24 ar2 >> two;
25 ar2 >> three;
26 ar2 >> s;
27
28 printf("we got %d - %f - %s - \"%s\"\n", one, two, (three ? "true":"false"), s.getString() );
29 return 0;
30}
diff --git a/src/old/tests/serializetext.cpp b/src/old/tests/serializetext.cpp
deleted file mode 100644
index f6be7d3..0000000
--- a/src/old/tests/serializetext.cpp
+++ /dev/null
@@ -1,28 +0,0 @@
1#include "serializertext.h"
2#include "staticstring.h"
3#include <iostream>
4
5int main()
6{
7 StaticString s("You're a dog!!");
8 SerializerText ar("hello.dat", false);
9
10 ar << 4 << 3.993 << true << s;
11
12 ar.close();
13
14 int one=0;float two=0.0;bool three=false; s = "";
15
16 SerializerText ar2("hello.dat", true);
17
18 ar2 >> one;
19 ar2 >> two;
20 ar2 >> three;
21 ar2 >> s;
22
23 //printf("out: %d, %f, %s, \"%s\"\n", one, two, (three ? "true" : "false"), s.getString());
24 std::cout << one << ", " << two << ", " << three << ", " << s.getString() << "\n";
25
26 return 0;
27}
28
diff --git a/src/old/tests/sha1.cpp b/src/old/tests/sha1.cpp
deleted file mode 100644
index df3113c..0000000
--- a/src/old/tests/sha1.cpp
+++ /dev/null
@@ -1,44 +0,0 @@
1#include "sha1.h"
2#include "sfile.h"
3
4#define BS 1024
5
6int main( int argc, char *argv[] )
7{
8 argc--; argv++;
9
10 if( argc == 0 )
11 {
12 printf("Provide a filename.\n");
13 return 0;
14 }
15
16 char buf[BS];
17
18 Sha1 s;
19 SFile fin( *argv, "rb" );
20 for(;;)
21 {
22 int nRead = fin.read( buf, BS );
23 if( nRead == 0 )
24 break;
25
26 s.update( buf, nRead );
27 if( nRead < BS )
28 break;
29 }
30
31 unsigned char *dig = s.getDigest();
32
33 char val[]={"0123456789ABCDEF"};
34
35 for( int j = 0; j < 20; j++ )
36 {
37 putchar( val[dig[j]>>4] );
38 putchar( val[dig[j]&0x0F] );
39 }
40 putchar('\n');
41
42 delete[] dig;
43}
44
diff --git a/src/old/tests/sptr.cpp b/src/old/tests/sptr.cpp
deleted file mode 100644
index 38d3675..0000000
--- a/src/old/tests/sptr.cpp
+++ /dev/null
@@ -1,55 +0,0 @@
1#include <stdio.h>
2#include "sptr.h"
3
4class Annoy
5{
6public:
7 Annoy() : nCnt( 0 )
8 {
9 printf("Created.\n");
10 }
11
12 ~Annoy()
13 {
14 printf("Destroyed.\n");
15 }
16
17 void go()
18 {
19 printf("%d: I'm annoying.\n", ++nCnt);
20 }
21
22 int nCnt;
23};
24
25void beAnnoying( SPtr<Annoy> bob )
26{
27 printf("bob-Count: %d\n", bob.count() );
28 bob->go();
29}
30
31int main()
32{
33 SPtr<Annoy> pt( new Annoy );
34 printf("Count: %d\n", pt.count() );
35 pt->go();
36
37 {
38 SPtr<Annoy> pt2 = pt;
39 printf("Count: %d\n", pt2.count() );
40
41 pt2->go();
42
43 {
44 SPtr<Annoy> pt3( pt2 );
45 printf("Count: %d\n", pt3.count() );
46
47 pt3->go();
48
49 beAnnoying( pt3 );
50 }
51 printf("Count: %d\n", pt.count() );
52 }
53 printf("Count: %d\n", pt.count() );
54}
55
diff --git a/src/old/tests/srvstress.cpp b/src/old/tests/srvstress.cpp
deleted file mode 100644
index d9a9a1c..0000000
--- a/src/old/tests/srvstress.cpp
+++ /dev/null
@@ -1,91 +0,0 @@
1#include "connectionmanager.h"
2#include "programlink.h"
3#include "linkedlist.h"
4#include "protocol.h"
5
6class StressProtocol : public Protocol
7{
8public:
9 bool onNewData()
10 {
11 switch( getConnection()->getInput()[0] )
12 {
13 case 'd':
14 throw "Hello";
15 break;
16
17 case 'w':
18 getConnection()->appendOutput("Hello");
19 break;
20 };
21
22 return true;
23 }
24
25 bool onNewConnection()
26 {
27 return true;
28 }
29};
30
31class StressMonitor : public ConnectionMonitor, public ProgramLink
32{
33public:
34 bool init()
35 {
36 return true;
37 }
38
39 bool deInit()
40 {
41 return true;
42 }
43
44 bool timeSlice()
45 {
46 return true;
47 }
48
49 bool onNewConnection( Connection *pCon, int nPort )
50 {
51 StressProtocol *sp = new StressProtocol();
52 pCon->setProtocol( sp );
53
54 printf(" sys: New connection: socket(%d), port(%d)\n",
55 pCon->getSocket(), nPort );
56
57 return true;
58 }
59
60 bool onClosedConnection( Connection *pCon )
61 {
62 printf(" sys: Closed connection: socket(%d)\n",
63 pCon->getSocket() );
64
65 return true;
66 }
67
68 LinkMessage *processIRM( LinkMessage *pMsg )
69 {
70 return NULL;
71 }
72};
73
74int main()
75{
76 printf("Starting server...\n");
77
78 ConnectionManager srv;
79 StressMonitor telnet;
80
81 srv.setConnectionMonitor( &telnet );
82
83 srv.startServer( 4001 );
84
85 for(;;)
86 {
87 srv.scanConnections( 5000, false );
88 }
89
90 return 0;
91}
diff --git a/src/old/tests/strhash.cpp b/src/old/tests/strhash.cpp
deleted file mode 100644
index f6528ca..0000000
--- a/src/old/tests/strhash.cpp
+++ /dev/null
@@ -1,12 +0,0 @@
1#include <stdio.h>
2#include "hashfunctionstring.h"
3
4int main( int argc, char *argv[] )
5{
6 HashFunctionString h;
7
8 printf("\"%s\": %lu\n", argv[1], h.hash( argv[1] ) );
9
10 return 0;
11}
12
diff --git a/src/old/tests/teltest/main.cpp b/src/old/tests/teltest/main.cpp
deleted file mode 100644
index 5d3ec26..0000000
--- a/src/old/tests/teltest/main.cpp
+++ /dev/null
@@ -1,21 +0,0 @@
1#include "connectionmanager.h"
2#include "telnetmonitor.h"
3
4int main()
5{
6 printf("Starting server...\n");
7
8 ConnectionManager srv;
9 TelnetMonitor telnet;
10
11 srv.setConnectionMonitor( &telnet );
12
13 srv.startServer( 4001 );
14
15 for(;;)
16 {
17 srv.scanConnections( 5000, false );
18 }
19
20 return 0;
21}
diff --git a/src/old/tests/teltest/telnetmonitor.cpp b/src/old/tests/teltest/telnetmonitor.cpp
deleted file mode 100644
index 65954eb..0000000
--- a/src/old/tests/teltest/telnetmonitor.cpp
+++ /dev/null
@@ -1,54 +0,0 @@
1#include "telnetmonitor.h"
2#include "protocoltelnet.h"
3#include <sys/stat.h>
4
5TelnetMonitor::TelnetMonitor()
6{
7}
8
9TelnetMonitor::~TelnetMonitor()
10{
11}
12
13bool TelnetMonitor::init()
14{
15 return true;
16}
17
18bool TelnetMonitor::deInit()
19{
20 return true;
21}
22
23bool TelnetMonitor::timeSlice()
24{
25 for( int j = 0; j < lCon.getSize(); j++ )
26 {
27 if( ((Connection *)lCon[j])->hasInput() )
28 {
29 printf("%s\n", ((Connection *)lCon[j])->getInput() );
30 }
31 }
32 return true;
33}
34
35LinkMessage* TelnetMonitor::processIRM( LinkMessage *pMsg )
36{
37 return NULL;
38}
39
40bool TelnetMonitor::onNewConnection( Connection *pCon, int nPort )
41{
42 ProtocolTelnet *pt = new ProtocolTelnet();
43 pCon->setProtocol( pt );
44
45 lCon.append( pt );
46
47 return true;
48}
49
50bool TelnetMonitor::onClosedConnection( Connection *pCon )
51{
52 return true;
53}
54
diff --git a/src/old/tests/teltest/telnetmonitor.h b/src/old/tests/teltest/telnetmonitor.h
deleted file mode 100644
index ba5761e..0000000
--- a/src/old/tests/teltest/telnetmonitor.h
+++ /dev/null
@@ -1,26 +0,0 @@
1#ifndef HTTPCONNECTIONMONITOR_H
2#define HTTPCONNECTIONMONITOR_H
3
4#include "connectionmonitor.h"
5#include "programlink.h"
6#include "linkedlist.h"
7
8class TelnetMonitor : public ConnectionMonitor, public ProgramLink
9{
10public:
11 TelnetMonitor();
12 ~TelnetMonitor();
13
14 bool init();
15 bool deInit();
16 bool timeSlice();
17 LinkMessage* processIRM( LinkMessage *pMsgIn );
18
19 bool onNewConnection( Connection *pCon, int nPort );
20 bool onClosedConnection( Connection *pCon );
21
22private:
23 LinkedList lCon;
24};
25
26#endif
diff --git a/src/old/tests/xmlreadtest.cpp b/src/old/tests/xmlreadtest.cpp
deleted file mode 100644
index d061810..0000000
--- a/src/old/tests/xmlreadtest.cpp
+++ /dev/null
@@ -1,29 +0,0 @@
1#include "xmlfilereader.h"
2#include "xmlstringreader.h"
3#include "xmlfilewriter.h"
4
5int main( int argc, char *argv[] )
6{
7 if( argc < 4 )
8 {
9 printf("Usage: %s f <file in> <file out>\n", argv[0] );
10 printf(" %s s <xml string> <file out>\n\n", argv[0] );
11 return 0;
12 }
13
14 if( argv[1][0] == 'f' )
15 {
16 XmlFileReader r( argv[2], true );
17// XmlFileWriter w( argv[3], "\t", r.detatchRoot() );
18// w.write();
19 }
20 else if( argv[1][0] == 's' )
21 {
22 XmlStringReader r( argv[2], true );
23 XmlFileWriter w(stdout, "\t", r.detatchRoot() );
24 w.write();
25 }
26
27 return 0;
28}
29
diff --git a/src/old/tests/xmlrepltest.cpp b/src/old/tests/xmlrepltest.cpp
deleted file mode 100644
index 9667705..0000000
--- a/src/old/tests/xmlrepltest.cpp
+++ /dev/null
@@ -1,31 +0,0 @@
1#include "xmlwriter.h"
2
3int main()
4{
5 printf("Testing Xml Replacement...\n");
6 XmlDocument w;
7
8 w.addNode("text");
9 w.setContent("this text is before the node. ");
10 w.addNode("keepme", "This one we keep...", true );
11 w.setContent("this text is after.");
12 w.addNode("deleteme", "This one we don't...", true );
13 w.setContent("this is last..." );
14 w.closeNode();
15
16 //XmlWriter::writeNode( stdout, w.getRoot(), 0, NULL );
17
18 printf("\n\n");
19
20 //XmlNode *xNode = w.getRoot()->detatchNode( 1 );
21
22 //XmlWriter::writeNode( stdout, w.getRoot(), 0, NULL );
23
24 printf("\n\n");
25
26 //XmlWriter::writeNode( stdout, xNode, 0, NULL );
27
28 printf("\n\n");
29
30 return 0;
31}
diff --git a/src/old/tests/xmlwritetest.cpp b/src/old/tests/xmlwritetest.cpp
deleted file mode 100644
index a22d19d..0000000
--- a/src/old/tests/xmlwritetest.cpp
+++ /dev/null
@@ -1,48 +0,0 @@
1#include "xmlfilewriter.h"
2#include "xmlstringwriter.h"
3#include "xmlstringreader.h"
4
5void fillItIn( XmlWriter &w )
6{
7 w.addNode("thinglist");
8
9 w.addNode("thing");
10 w.addProperty("type", " ±î´<M-F6><M-F6>³¸®°êòì¯");
11
12 w.addNode("id", "Klophin²³±¹¸·µ´äêíëã Staff", true );
13 w.addNode("name", "Klophin Staff", true );
14 w.addNode("durability", "0.01", true );
15 w.addNode("size", "0.1", true );
16
17 w.addNode("config");
18 w.addNode("damage", "3d6+4", true );
19 w.addNode("class", "melee", true );
20 w.addNode("type", "bludgeon", true );
21 w.addNode("damagedesc", "club/clubs", true );
22 w.closeNode();
23
24 w.closeNode();
25
26 w.closeNode();
27}
28
29int main()
30{
31 printf("Testing XmlWriter...\n");
32
33 //XmlStringReader *xsr = new XmlStringReader("<stuff/>");
34
35 //printf("%08X\n%08X\n%08X\n", xsr, (XmlReader *)xsr, (XmlDocument *)xsr );
36
37 //delete (XmlDocument *)xsr;
38 XmlFileWriter wf("test.xml", "\t");
39
40 fillItIn( wf );
41
42 XmlStringWriter ws("\t");
43 fillItIn( ws );
44
45 printf("Now the string version:\n\n%s\n", ws.getString().c_str() );
46
47 return 0;
48}
diff --git a/src/old/tokenstring.cpp b/src/old/tokenstring.cpp
deleted file mode 100644
index e57ba69..0000000
--- a/src/old/tokenstring.cpp
+++ /dev/null
@@ -1,163 +0,0 @@
1#include "tokenstring.h"
2#include <string.h>
3
4TokenString::TokenString( const char *lpNewTokenString )
5{
6 lpTokenString = NULL;
7 if( lpNewTokenString )
8 {
9 parseLine( lpNewTokenString );
10 }
11}
12
13TokenString::~TokenString()
14{
15 delete[] lpTokenString;
16 for( int j = 0; j < lToken.getSize(); j++ )
17 {
18 delete[] (((Token *)lToken[j])->lpToken);
19 delete ((Token *)lToken[j]);
20 }
21}
22
23void TokenString::parseLine( const char *lpNewTokenString )
24{
25 if( lpTokenString != NULL )
26 {
27 delete[] lpTokenString;
28 lpTokenString = NULL;
29 for( int j = 0; j < lToken.getSize(); j++ )
30 {
31 delete[] (((Token *)lToken[j])->lpToken);
32 delete ((Token *)lToken[j]);
33 }
34 lToken.empty();
35 }
36 if( lpNewTokenString == NULL )
37 {
38 lpTokenString = new char[1];
39 lpTokenString[0] = '\0';
40 lToken.setSize(0);
41 return;
42 }
43 // First order of business, make an internal copy so someone can get it
44 // if they want to.
45 int nLen = strlen(lpNewTokenString);
46 lpTokenString = new char[nLen+1];
47 strcpy( lpTokenString, lpNewTokenString );
48
49 // Now we do a preliminary parse. This could be effected by later
50 // editing and aliasing, but we'll see...
51 int nTkStart, nTkEnd;
52 int mode=0; // 0 = startSearch, 1=endSearch
53 for( int j = 0; j <= nLen; j++ )
54 {
55 if( mode == 0 )
56 {
57 if( lpTokenString[j] != ' ' &&
58 lpTokenString[j] != '\t' )
59 {
60 nTkStart = j;
61 mode = 1;
62 }
63 }
64 else
65 {
66 if( lpTokenString[j] == ' ' ||
67 lpTokenString[j] == '\t' ||
68 lpTokenString[j] == '\0' )
69 {
70 nTkEnd = j-1;
71 mode = 0;
72
73 appendToken( nTkStart, nTkEnd );
74 }
75 }
76 }
77}
78
79void TokenString::appendToken( int nStart, int nEnd )
80{
81 Token *pToken = new Token;
82 pToken->lpOrig = &lpTokenString[nStart];
83
84 // nStart and nEnd are inclusive, we must add two for the end, and the null
85 pToken->lpToken = new char[nEnd-nStart+2];
86 memcpy( pToken->lpToken, &lpTokenString[nStart], nEnd-nStart+1 );
87 pToken->lpToken[nEnd-nStart+1] = '\0';
88
89// printf("%s\n", pToken->lpToken );
90 lToken.append( pToken );
91}
92
93void TokenString::insertToken( int nStart, int nEnd, char *lpOldOrig, const char *lpNewToken, int nIndex )
94{
95 Token *pToken = new Token;
96 pToken->lpOrig = lpOldOrig;
97
98 // nStart and nEnd are inclusive, we must add two for the end, and the null
99 pToken->lpToken = new char[nEnd-nStart+2];
100 memcpy( pToken->lpToken, &lpNewToken[nStart], nEnd-nStart+1 );
101 pToken->lpToken[nEnd-nStart+1] = '\0';
102
103 lToken.insertBefore( pToken, nIndex );
104}
105
106int TokenString::getNumTokens()
107{
108 return lToken.getSize();
109}
110
111char *TokenString::getToken( int nIndex )
112{
113 if( nIndex >= lToken.getSize() ) return NULL;
114 return (char *)(((Token *)lToken[nIndex])->lpToken);
115}
116
117char *TokenString::getTokenString( int nIndex )
118{
119 if( nIndex >= lToken.getSize() ) return NULL;
120 return (char *)(((Token *)lToken[nIndex])->lpOrig);
121}
122
123void TokenString::expandTokenTo( int nIndex, char *lpNewToken )
124{
125 // First, we delete the token at nIndex, then we keep inserting
126 // at that position...
127 // We also have to remember the index to the original string,
128 // since most of what we're expanding to won't be in the origingal
129 // we need to keep these indexes updated in order to make other parts
130 // of the system happy.
131 char *lpOldOrig = ((Token *)lToken[nIndex])->lpOrig;
132 delete[] ((Token *)lToken[nIndex])->lpToken;
133 delete ((Token *)lToken[nIndex]);
134 lToken.deleteAt( nIndex );
135
136 // We'll do this just like we did above, but instead we'll
137 // do tricky things when we find tokens...
138 int nLen = strlen(lpNewToken);
139 int nTkStart, nTkEnd, nNewIndex=nIndex;
140 int mode=0; // 0 = startSearch, 1=endSearch
141 for( int j = 0; j <= nLen; j++ )
142 {
143 if( mode == 0 )
144 {
145 if( lpNewToken[j] != ' ' && lpNewToken[j] != '\t' )
146 {
147 nTkStart = j;
148 mode = 1;
149 }
150 }
151 else
152 {
153 if( lpNewToken[j] == ' ' || lpNewToken[j] == '\t' || lpNewToken[j] == '\0' )
154 {
155 nTkEnd = j-1;
156 mode = 0;
157
158 insertToken( nTkStart, nTkEnd, lpOldOrig, lpNewToken, nNewIndex );
159 nNewIndex++;
160 }
161 }
162 }
163}
diff --git a/src/old/tokenstring.h b/src/old/tokenstring.h
deleted file mode 100644
index 42f7309..0000000
--- a/src/old/tokenstring.h
+++ /dev/null
@@ -1,114 +0,0 @@
1#ifndef TOKENSTRING_H
2#define TOKENSTRING_H
3
4#include "linkedlist.h"
5
6/** A single tokenized command line. Contains all information necesarry to
7 * nicely access a stand-alone command line and to perform alias expansion
8 * inside of that command line.
9 * When expanding a token, the original command line is left intact, so any
10 * command usng a command line verbatum (getTokenString not getToken) will get
11 * the original, and not the expanded version.
12 * Since indexing into the original command line is also done by token, it
13 * means that using getTokenString( 0 ) will not always get you the first
14 * character of the command line, it will get you the first non-whitespace
15 * character.
16 * Furthermore, when expanding the expantion string is tokenized as well,
17 * but since the original string is unchanged, all tokens that expand any
18 * given index will all retain the same index into the original command line.
19 *@todo Update this to allow it to break on different types of token
20 * delimiters.
21 *@author Mike Buland
22 */
23class TokenString{
24public:
25 /** Automatically call parseLine when created.
26 *@param lpNewTokenString The command line to tokenize
27 *@author Mike Buland
28 */
29 TokenString( const char *lpNewTokenString=NULL );
30 virtual ~TokenString();
31
32 /** Performs a tokenizing parse on the given command line, setting it as
33 * the internal command line for all future tokenizing (excluding
34 * expansion)
35 *@param lpNewTokenString The new command line to set to this object.
36 *@author Mike Buland
37 */
38 void parseLine( const char *lpNewTokenString );
39
40 /** Appends a token to the list of available tokens. This references the
41 * internal pointer to the command line, so no token string must be
42 * specified.
43 *@param nStart The first character of the token to insert.
44 *@param nEnd The last character of the token to insert.
45 *@author Mike Buland
46 */
47 void appendToken( int nStart, int nEnd );
48
49 /** Gets the number of tokens. This is particularly useful post-aliasing
50 * since the number of tokens may not match what is percieved from the
51 * original command line.
52 *@returns The number of available tokens.
53 *@author Mike Buland
54 */
55 int getNumTokens();
56
57 /** Gets a processed token specified by index.
58 *@param nIndex The index of the token to retrieve.
59 *@returns A pointer to the requested token. Please note that these tokens
60 * may not match the original command line.
61 *@author Mike Buland
62 */
63 char *getToken( int nIndex );
64
65 /** Gets the original command line based on tokens. Use this if you want
66 * to perform your own processing on parts of the command line, without
67 * resorting to tokens.
68 * The first character in the returned string will always be
69 * non-whitespace.
70 *@param nIndex The index of the token to start at, zero gets you the whole
71 * command line.
72 *@returns A pointer to the internal original command line string, starting
73 * at the position of the first non-whitespace character of the token
74 * specified.
75 *@author Mike Buland
76 */
77 char *getTokenString( int nIndex=0 );
78
79 /** Expands a token, replacing it with the string lpNewToken, but
80 * processing the new string for tokens before performing the replacement
81 *@param nIndex Which token should be replaced.
82 *@param lpNewToken The string to replace the token with.
83 *@author Mike Buland
84 */
85 void expandTokenTo( int nIndex, char *lpNewToken );
86
87 /** Inserts a token at any position in the command line. This does not
88 * effect the original command line.
89 *@param nStart The start of the token in the string lpNewToken. (inclusive)
90 *@param nEnd The end of the token in the string lpToken. (inclusive)
91 *@param lpOldOrig The pointer to the position in the orginal command
92 * line where this new token should point.
93 *@param lpNewToken The string containing the new token. May contain more
94 * than just one token.
95 *@param nIndex The position to insert the token to.
96 *@author Mike Buland
97 */
98 void insertToken( int nStart, int nEnd, char *lpOldOrig, const char *lpNewToken, int nIndex );
99
100private:
101 char *lpTokenString; /**< The original text that this string came from */
102 LinkedList lToken; /**< The list of tokens. */
103
104 /**
105 * A single token within the token string.
106 */
107 typedef struct Token
108 {
109 char *lpOrig; /**< This is just a pointer back to lpTokenString */
110 char *lpToken; /**< This is really a whole token */
111 } Token;
112};
113
114#endif
diff --git a/src/old/tqsort.h b/src/old/tqsort.h
deleted file mode 100644
index c836b4f..0000000
--- a/src/old/tqsort.h
+++ /dev/null
@@ -1,207 +0,0 @@
1#ifndef T_QSORT_H
2#define T_QSORT_H
3
4#define _QSORT_SWAP(a, b, t) ((void)((t = *a), (*a = *b), (*b = t)))
5
6/* Discontinue quicksort algorithm when partition gets below this size.
7 This particular magic number was chosen to work best on a Sun 4/260. */
8#define _QSORT_MAX_THRESH 4
9
10/* Stack node declarations used to store unfulfilled partition obligations
11 * (inlined in QSORT).
12typedef struct {
13 QSORT_TYPE *_lo, *_hi;
14} qsort_stack_node;
15 */
16
17/* The next 4 #defines implement a very fast in-line stack abstraction. */
18/* The stack needs log (total_elements) entries (we could even subtract
19 log(MAX_THRESH)). Since total_elements has type unsigned, we get as
20 upper bound for log (total_elements):
21 bits per byte (CHAR_BIT) * sizeof(unsigned). */
22#define _QSORT_STACK_SIZE (8 * sizeof(unsigned))
23#define _QSORT_PUSH(top, low, high) \
24 (((top->_lo = (low)), (top->_hi = (high)), ++top))
25#define _QSORT_POP(low, high, top) \
26 ((--top, (low = top->_lo), (high = top->_hi)))
27#define _QSORT_STACK_NOT_EMPTY (_stack < _top)
28
29
30/* Order size using quicksort. This implementation incorporates
31 four optimizations discussed in Sedgewick:
32
33 1. Non-recursive, using an explicit stack of pointer that store the
34 next array partition to sort. To save time, this maximum amount
35 of space required to store an array of SIZE_MAX is allocated on the
36 stack. Assuming a 32-bit (64 bit) integer for size_t, this needs
37 only 32 * sizeof(stack_node) == 256 bytes (for 64 bit: 1024 bytes).
38 Pretty cheap, actually.
39
40 2. Chose the pivot element using a median-of-three decision tree.
41 This reduces the probability of selecting a bad pivot value and
42 eliminates certain extraneous comparisons.
43
44 3. Only quicksorts TOTAL_ELEMS / MAX_THRESH partitions, leaving
45 insertion sort to order the MAX_THRESH items within each partition.
46 This is a big win, since insertion sort is faster for small, mostly
47 sorted array segments.
48
49 4. The larger of the two sub-partitions is always pushed onto the
50 stack first, with the algorithm then concentrating on the
51 smaller partition. This *guarantees* no more than log (total_elems)
52 stack size is needed (actually O(1) in this case)! */
53
54/* The main code starts here... */
55
56template<typename QSORT_TYPE, typename QSORT_LTT, typename CST>
57void tqsort( QSORT_TYPE *QSORT_BASE, int QSORT_NELT )
58{
59 QSORT_LTT QSORT_LT;
60 QSORT_TYPE *const _base = (QSORT_BASE);
61 const unsigned _elems = (QSORT_NELT);
62 QSORT_TYPE _hold;
63
64 /* Don't declare two variables of type QSORT_TYPE in a single
65 * statement: eg `TYPE a, b;', in case if TYPE is a pointer,
66 * expands to `type* a, b;' wich isn't what we want.
67 */
68
69 if (_elems > _QSORT_MAX_THRESH) {
70 QSORT_TYPE *_lo = _base;
71 QSORT_TYPE *_hi = _lo + _elems - 1;
72 struct {
73 QSORT_TYPE *_hi; QSORT_TYPE *_lo;
74 } _stack[_QSORT_STACK_SIZE], *_top = _stack + 1;
75
76 while (_QSORT_STACK_NOT_EMPTY) {
77 QSORT_TYPE *_left_ptr; QSORT_TYPE *_right_ptr;
78
79 /* Select median value from among LO, MID, and HI. Rearrange
80 LO and HI so the three values are sorted. This lowers the
81 probability of picking a pathological pivot value and
82 skips a comparison for both the LEFT_PTR and RIGHT_PTR in
83 the while loops. */
84
85 QSORT_TYPE *_mid = _lo + ((_hi - _lo) >> 1);
86
87 if (QSORT_LT ((CST)(_mid), (CST)(_lo)))
88 _QSORT_SWAP (_mid, _lo, _hold);
89 if (QSORT_LT ((CST)(_hi), (CST)(_mid)))
90 _QSORT_SWAP (_mid, _hi, _hold);
91 else
92 goto _jump_over;
93 if (QSORT_LT ((CST)(_mid), (CST)(_lo)))
94 _QSORT_SWAP (_mid, _lo, _hold);
95 _jump_over:;
96
97 _left_ptr = _lo + 1;
98 _right_ptr = _hi - 1;
99
100 /* Here's the famous ``collapse the walls'' section of quicksort.
101 Gotta like those tight inner loops! They are the main reason
102 that this algorithm runs much faster than others. */
103 do {
104 while (QSORT_LT ((CST)(_left_ptr), (CST)(_mid)))
105 ++_left_ptr;
106
107 while (QSORT_LT ((CST)(_mid), (CST)(_right_ptr)))
108 --_right_ptr;
109
110 if (_left_ptr < _right_ptr) {
111 _QSORT_SWAP (_left_ptr, _right_ptr, _hold);
112 if (_mid == _left_ptr)
113 _mid = _right_ptr;
114 else if (_mid == _right_ptr)
115 _mid = _left_ptr;
116 ++_left_ptr;
117 --_right_ptr;
118 }
119 else if (_left_ptr == _right_ptr) {
120 ++_left_ptr;
121 --_right_ptr;
122 break;
123 }
124 } while (_left_ptr <= _right_ptr);
125
126 /* Set up pointers for next iteration. First determine whether
127 left and right partitions are below the threshold size. If so,
128 ignore one or both. Otherwise, push the larger partition's
129 bounds on the stack and continue sorting the smaller one. */
130
131 if (_right_ptr - _lo <= _QSORT_MAX_THRESH) {
132 if (_hi - _left_ptr <= _QSORT_MAX_THRESH)
133 /* Ignore both small partitions. */
134 _QSORT_POP (_lo, _hi, _top);
135 else
136 /* Ignore small left partition. */
137 _lo = _left_ptr;
138 }
139 else if (_hi - _left_ptr <= _QSORT_MAX_THRESH)
140 /* Ignore small right partition. */
141 _hi = _right_ptr;
142 else if (_right_ptr - _lo > _hi - _left_ptr) {
143 /* Push larger left partition indices. */
144 _QSORT_PUSH (_top, _lo, _right_ptr);
145 _lo = _left_ptr;
146 }
147 else {
148 /* Push larger right partition indices. */
149 _QSORT_PUSH (_top, _left_ptr, _hi);
150 _hi = _right_ptr;
151 }
152 }
153 }
154
155 /* Once the BASE array is partially sorted by quicksort the rest
156 is completely sorted using insertion sort, since this is efficient
157 for partitions below MAX_THRESH size. BASE points to the
158 beginning of the array to sort, and END_PTR points at the very
159 last element in the array (*not* one beyond it!). */
160
161 {
162 QSORT_TYPE *const _end_ptr = _base + _elems - 1;
163 QSORT_TYPE *_tmp_ptr = _base;
164 register QSORT_TYPE *_run_ptr;
165 QSORT_TYPE *_thresh;
166
167 _thresh = _base + _QSORT_MAX_THRESH;
168 if (_thresh > _end_ptr)
169 _thresh = _end_ptr;
170
171 /* Find smallest element in first threshold and place it at the
172 array's beginning. This is the smallest array element,
173 and the operation speeds up insertion sort's inner loop. */
174
175 for (_run_ptr = _tmp_ptr + 1; _run_ptr <= _thresh; ++_run_ptr)
176 if (QSORT_LT ((CST)(_run_ptr), (CST)(_tmp_ptr)))
177 _tmp_ptr = _run_ptr;
178
179 if (_tmp_ptr != _base)
180 _QSORT_SWAP (_tmp_ptr, _base, _hold);
181
182 /* Insertion sort, running from left-hand-side
183 * up to right-hand-side. */
184
185 _run_ptr = _base + 1;
186 while (++_run_ptr <= _end_ptr) {
187 _tmp_ptr = _run_ptr - 1;
188 while (QSORT_LT ((CST)(_run_ptr), (CST)(_tmp_ptr)))
189 --_tmp_ptr;
190
191 ++_tmp_ptr;
192 if (_tmp_ptr != _run_ptr) {
193 QSORT_TYPE *_trav = _run_ptr + 1;
194 while (--_trav >= _run_ptr) {
195 QSORT_TYPE *_hi; QSORT_TYPE *_lo;
196 _hold = *_trav;
197
198 for (_hi = _lo = _trav; --_lo >= _tmp_ptr; _hi = _lo)
199 *_hi = *_lo;
200 *_hi = _hold;
201 }
202 }
203 }
204 }
205}
206
207#endif
diff --git a/src/old/unit/hashtable/hashtable.cpp b/src/old/unit/hashtable/hashtable.cpp
deleted file mode 100644
index b2e1cf5..0000000
--- a/src/old/unit/hashtable/hashtable.cpp
+++ /dev/null
@@ -1,107 +0,0 @@
1#include <cstdlib>
2#include <cstring>
3#include <iostream>
4#include <cpptest.h>
5#include <string.h>
6#include <set>
7#include <map>
8
9#include "hashfunctionstring.h"
10#include "hashfunctioncasestring.h"
11#include "hashfunctionint.h"
12
13class HashFunctionSuite : public Test::Suite
14{
15public:
16 HashFunctionSuite()
17 {
18 TEST_ADD( HashFunctionSuite::functionString )
19 TEST_ADD( HashFunctionSuite::functionCaseString )
20 TEST_ADD( HashFunctionSuite::functionInt )
21 }
22
23private:
24 void functionStringWorker( HashFunction &hf, std::set<unsigned long> &sCodes, char *str, int nLevel, int nMax )
25 {
26 for( char let = 'A'; let <= 'z'; let += 3 )
27 {
28 str[nLevel+1] = '\0';
29 str[nLevel] = let;
30 unsigned long x = hf.hash( str );
31 TEST_ASSERT( sCodes.find( x ) == sCodes.end() );
32 TEST_ASSERT( hf.cmpIDs( str, str ) );
33 sCodes.insert( x );
34
35 if( nLevel < nMax )
36 functionStringWorker( hf, sCodes, str, nLevel+1, nMax );
37 }
38 }
39
40 void functionString()
41 {
42 HashFunctionString hf;
43 char str[10];
44
45 std::set<unsigned long> sCodes;
46
47 functionStringWorker( hf, sCodes, str, 0, 3 );
48 }
49
50 void functionCaseStringWorker( HashFunction &hf, std::map<unsigned long, char *> &sCodes, char *str, int nLevel, int nMax )
51 {
52 for( char let = 'A'; let <= 'z'; let += 3 )
53 {
54 str[nLevel+1] = '\0';
55 str[nLevel] = let;
56 unsigned long x = hf.hash( str );
57 std::map<unsigned long, char *>::iterator i = sCodes.find( x );
58 if( i == sCodes.end() )
59 {
60 sCodes[x] = strdup( str );
61 }
62 else
63 {
64 TEST_ASSERT( strcasecmp( (*i).second, str ) == 0 );
65 TEST_ASSERT( hf.cmpIDs( (*i).second, str ) == true );
66 }
67
68 if( nLevel < nMax )
69 functionCaseStringWorker( hf, sCodes, str, nLevel+1, nMax );
70 }
71 }
72
73 void functionCaseString()
74 {
75 HashFunctionCaseString hf;
76 char str[10];
77
78 std::map<unsigned long, char *> sCodes;
79
80 functionCaseStringWorker( hf, sCodes, str, 0, 3 );
81
82 std::map<unsigned long, char *>::iterator i;
83 for( i = sCodes.begin(); i != sCodes.end(); i++ )
84 {
85 free( (*i).second );
86 }
87 }
88
89 void functionInt()
90 {
91 HashFunctionInt hf;
92
93 for( long i = -100000; i <= 100000; i += 100 )
94 {
95 TEST_ASSERT( ((long)hf.hash( (void *)i )) == i );
96 TEST_ASSERT( ((long)hf.cmpIDs( (void *)i, (void *)i )) );
97 }
98 }
99};
100
101int main( int argc, char *argv[] )
102{
103 Test::TextOutput output( Test::TextOutput::Verbose );
104 HashFunctionSuite ts;
105 return ts.run( output ) ? EXIT_SUCCESS : EXIT_FAILURE;
106}
107
diff --git a/src/old/unit/xml/xml.cpp b/src/old/unit/xml/xml.cpp
deleted file mode 100644
index e4d779c..0000000
--- a/src/old/unit/xml/xml.cpp
+++ /dev/null
@@ -1,59 +0,0 @@
1#include <cstdlib>
2#include <cstring>
3#include <iostream>
4#include <cpptest.h>
5#include <string.h>
6
7#include "xmlstringreader.h"
8#include "xmlexception.h"
9
10class XmlCoreTestSuite : public Test::Suite
11{
12public:
13 XmlCoreTestSuite()
14 {
15 TEST_ADD( XmlCoreTestSuite::badXml01 )
16 TEST_ADD( XmlCoreTestSuite::badXml02 )
17 TEST_ADD( XmlCoreTestSuite::badXml03 )
18
19 TEST_ADD( XmlCoreTestSuite::entityBuiltin01 )
20
21 TEST_ADD( XmlCoreTestSuite::entityDoc01 )
22 }
23
24private:
25 void badXml01()
26 {
27 TEST_THROWS( XmlStringReader r("<hello></bye>"), XmlException & );
28 }
29
30 void badXml02()
31 {
32 TEST_THROWS( XmlStringReader r("<hello>"), XmlException & );
33 }
34
35 void badXml03()
36 {
37 TEST_THROWS( XmlStringReader r("<hello param=\"stuff?"), XmlException & );
38 }
39
40 void entityBuiltin01()
41 {
42 XmlStringReader r("<hello>&gt;&lt;&amp;&apos;&quot;</hello>");
43 TEST_ASSERT( strcmp( r.getRoot()->getContent(), "><&\'\"" ) == 0 );
44 }
45
46 void entityDoc01()
47 {
48 XmlStringReader r("<!ENTITY name \"bob the man\"><hello>&quot;&name;&quot;</hello>");
49 TEST_ASSERT( strcmp( r.getRoot()->getContent(), "\"bob the man\"" ) == 0 );
50 }
51};
52
53int main( int argc, char *argv[] )
54{
55 Test::TextOutput output( Test::TextOutput::Verbose );
56 XmlCoreTestSuite ts;
57 return ts.run( output ) ? EXIT_SUCCESS : EXIT_FAILURE;
58}
59
diff --git a/src/old/xmldocument.cpp b/src/old/xmldocument.cpp
deleted file mode 100644
index 95b9788..0000000
--- a/src/old/xmldocument.cpp
+++ /dev/null
@@ -1,145 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include "xmldocument.h"
4
5XmlDocument::XmlDocument( XmlNode *pRoot )
6{
7 this->pRoot = pRoot;
8 pCurrent = NULL;
9 bCompleted = (pRoot!=NULL);
10}
11
12XmlDocument::~XmlDocument()
13{
14 if( pRoot )
15 {
16 delete pRoot;
17 }
18}
19
20void XmlDocument::addNode( const Bu::FString &sName )
21{
22 if( pRoot == NULL )
23 {
24 // This is the first node, so ignore position and just insert it.
25 pCurrent = pRoot = new XmlNode( sName );
26 }
27 else
28 {
29 pCurrent = pCurrent->addChild( sName );
30 }
31}
32/*
33void XmlDocument::setName( const char *sName )
34{
35 pCurrent->setName( sName );
36}*/
37
38bool XmlDocument::isCompleted()
39{
40 return bCompleted;
41}
42
43XmlNode *XmlDocument::getRoot()
44{
45 return pRoot;
46}
47
48XmlNode *XmlDocument::detatchRoot()
49{
50 XmlNode *pTemp = pRoot;
51 pRoot = NULL;
52 return pTemp;
53}
54
55XmlNode *XmlDocument::getCurrent()
56{
57 return pCurrent;
58}
59
60void XmlDocument::closeNode()
61{
62 if( pCurrent != NULL )
63 {
64 pCurrent = pCurrent->getParent();
65
66 if( pCurrent == NULL )
67 {
68 bCompleted = true;
69 }
70 }
71}
72
73void XmlDocument::addProperty( const char *sName, const char *sValue )
74{
75 if( pCurrent )
76 {
77 pCurrent->addProperty( sName, sValue );
78 }
79}
80
81void XmlDocument::addProperty( const char *sName, const unsigned char nValue )
82{
83 char buf[12];
84 sprintf( buf, "%hhi", nValue );
85 addProperty( sName, buf );
86}
87
88void XmlDocument::addProperty( const char *sName, const char nValue )
89{
90 char buf[12];
91 sprintf( buf, "%hhi", nValue );
92 addProperty( sName, buf );
93}
94
95void XmlDocument::addProperty( const char *sName, const unsigned short nValue )
96{
97 char buf[12];
98 sprintf( buf, "%hi", nValue );
99 addProperty( sName, buf );
100}
101
102void XmlDocument::addProperty( const char *sName, const short nValue )
103{
104 char buf[12];
105 sprintf( buf, "%hi", nValue );
106 addProperty( sName, buf );
107}
108
109void XmlDocument::addProperty( const char *sName, const int nValue )
110{
111 char buf[12];
112 sprintf( buf, "%d", nValue );
113 addProperty( sName, buf );
114}
115
116void XmlDocument::addProperty( const char *sName, const unsigned long nValue )
117{
118 char buf[12];
119 sprintf( buf, "%li", nValue );
120 addProperty( sName, buf );
121}
122
123void XmlDocument::addProperty( const char *sName, const long nValue )
124{
125 char buf[12];
126 sprintf( buf, "%li", nValue );
127 addProperty( sName, buf );
128}
129
130void XmlDocument::addProperty( const char *sName, const double dValue )
131{
132 char buf[40];
133 sprintf( buf, "%f", dValue );
134 addProperty( sName, buf );
135}
136
137void XmlDocument::setContent( const char *sContent )
138{
139 if( pCurrent )
140 {
141 printf("XmlDocument::setContent: not yet implemented.\n");
142 //pCurrent->setContent( sContent );
143 }
144}
145
diff --git a/src/old/xmldocument.h b/src/old/xmldocument.h
deleted file mode 100644
index e0c36eb..0000000
--- a/src/old/xmldocument.h
+++ /dev/null
@@ -1,165 +0,0 @@
1#ifndef XMLDOCUMENT
2#define XMLDOCUMENT
3
4#include "xmlnode.h"
5
6/**
7 * Keeps track of an easily managed set of XmlNode information. Allows simple
8 * operations for logical writing to and reading from XML structures. Using
9 * already formed structures is simply done through the XmlNode structures,
10 * and the getRoot function here. Creation is performed through a simple set
11 * of operations that creates the data in a stream type format.
12 *@author Mike Buland
13 */
14class XmlDocument
15{
16public:
17 /**
18 * Construct either a blank XmlDocuemnt or construct a document around an
19 * existing XmlNode. Be careful, once an XmlNode is passed into a document
20 * the document takes over ownership and will delete it when the XmlDocument
21 * is deleted.
22 *@param pRoot The XmlNode to use as the root of this document, or NULL if
23 * you want to start a new document.
24 */
25 XmlDocument( XmlNode *pRoot=NULL );
26
27 /**
28 * Destroy all contained nodes.
29 */
30 virtual ~XmlDocument();
31
32 /**
33 * Add a new node to the document. The new node is appended to the end of
34 * the current context, i.e. XmlNode, and the new node, provided it isn't
35 * close as part of this operation, will become the current context.
36 *@param sName The name of the new node to add.
37 *@param sContent A content string to be placed inside of the new node.
38 *@param bClose Set this to true to close the node immediately after adding
39 * the node and setting the content and name. If this is set to true the
40 * node is appended, but the context node doesn't change.
41 */
42 void addNode( const Bu::FString &sName );
43
44 /**
45 * Close the current node context. This will move the current context to
46 * the parent node of the former current node. If the current node was the
47 * root then the "completed" flag is set and no more operations are allowed.
48 */
49 void closeNode();
50
51 /**
52 * Change the content of the current node at the current position between
53 * nodes.
54 *@param sContent The new content of the current node.
55 */
56 void setContent( const char *sContent );
57
58 /**
59 * Add a named property to the current context node.
60 *@param sName The name of the property to add.
61 *@param sValue The string value of the property.
62 */
63 void addProperty( const char *sName, const char *sValue );
64
65 /**
66 * Add a named property to the current context node, converting the
67 * numerical parameter to text using standrd printf style conversion.
68 *@param sName The name of the property to add.
69 *@param nValue The numerical value to add.
70 */
71 void addProperty( const char *sName, const unsigned char nValue );
72
73 /**
74 * Add a named property to the current context node, converting the
75 * numerical parameter to text using standrd printf style conversion.
76 *@param sName The name of the property to add.
77 *@param nValue The numerical value to add.
78 */
79 void addProperty( const char *sName, const char nValue );
80
81 /**
82 * Add a named property to the current context node, converting the
83 * numerical parameter to text using standrd printf style conversion.
84 *@param sName The name of the property to add.
85 *@param nValue The numerical value to add.
86 */
87 void addProperty( const char *sName, const unsigned short nValue );
88
89 /**
90 * Add a named property to the current context node, converting the
91 * numerical parameter to text using standrd printf style conversion.
92 *@param sName The name of the property to add.
93 *@param nValue The numerical value to add.
94 */
95 void addProperty( const char *sName, const short nValue );
96
97 /**
98 * Add a named property to the current context node, converting the
99 * numerical parameter to text using standrd printf style conversion.
100 *@param sName The name of the property to add.
101 *@param nValue The numerical value to add.
102 */
103 void addProperty( const char *sName, const unsigned long nValue );
104
105 /**
106 * Add a named property to the current context node, converting the
107 * numerical parameter to text using standrd printf style conversion.
108 *@param sName The name of the property to add.
109 *@param nValue The numerical value to add.
110 */
111 void addProperty( const char *sName, const long nValue );
112
113 /**
114 * Add a named property to the current context node, converting the
115 * numerical parameter to text using standrd printf style conversion.
116 *@param sName The name of the property to add.
117 *@param nValue The numerical value to add.
118 */
119 void addProperty( const char *sName, const int nValue );
120
121 /**
122 * Add a named property to the current context node, converting the
123 * numerical parameter to text using standrd printf style conversion.
124 *@param sName The name of the property to add.
125 *@param dValue The numerical value to add.
126 */
127 void addProperty( const char *sName, const double dValue );
128
129 /**
130 * The XmlDocuemnt is considered completed if the root node has been closed.
131 * Once an XmlDocument has been completed, you can no longer perform
132 * operations on it.
133 *@return True if completed, false if still in progress.
134 */
135 bool isCompleted();
136
137 /**
138 * Get a pointer to the root object of this XmlDocument.
139 *@returns A pointer to an internally owned XmlNode. Do not delete this
140 * XmlNode.
141 */
142 XmlNode *getRoot();
143
144 /**
145 * Get a pointer to the root object of this XmlDocument, and remove the
146 * ownership from this object.
147 *@returns A pointer to an internally owned XmlNode. Do not delete this
148 * XmlNode.
149 */
150 XmlNode *detatchRoot();
151
152 /**
153 * Get the current context node, which could be the same as the root node.
154 *@returns A pointer to an internally owned XmlNode. Do not delete this
155 * XmlNode.
156 */
157 XmlNode *getCurrent();
158
159private:
160 XmlNode *pRoot; /**< The root node. */
161 XmlNode *pCurrent; /**< The current node. */
162 bool bCompleted; /**< Is it completed? */
163};
164
165#endif
diff --git a/src/old/xmlfilereader.cpp b/src/old/xmlfilereader.cpp
deleted file mode 100644
index ed674a8..0000000
--- a/src/old/xmlfilereader.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
1#include "xmlfilereader.h"
2#include "exceptions.h"
3#include <string.h>
4
5XmlFileReader::XmlFileReader( const char *sFile, bool bStrip )
6 : XmlReader( bStrip )
7{
8 fh = fopen( sFile, "rt" );
9
10 if( fh == NULL )
11 {
12 throw XmlException("Couldn't open file: %s", sFile );
13 //nError = 1;
14 }
15 else
16 {
17 buildDoc();
18 }
19}
20
21XmlFileReader::~XmlFileReader()
22{
23}
24
25char XmlFileReader::getChar( int nIndex )
26{
27 // Make sure we always have a little data left in the buffer
28 if( fbDataIn.getLength() <= nIndex+1 && fh )
29 {
30 int nBytes = fbDataIn.getCapacity()-1;
31 char *buf = new char[nBytes];
32 int nRead = fread( buf, 1, nBytes, fh );
33 fbDataIn.appendData( buf, nRead );
34 delete[] buf;
35
36 if( nRead < nBytes )
37 {
38 fclose( fh );
39 fh = NULL;
40 }
41 }
42 if( fbDataIn.getLength() >= nIndex+1 )
43 {
44 return fbDataIn.getData()[nIndex];
45 }
46 else
47 {
48 throw XmlException("End of XML stream read.");
49 }
50}
51
52void XmlFileReader::usedChar( int nAmnt )
53{
54 if( fbDataIn.getLength()-nAmnt >= 0 )
55 {
56 fbDataIn.usedData( nAmnt );
57 }
58}
diff --git a/src/old/xmlfilereader.h b/src/old/xmlfilereader.h
deleted file mode 100644
index e3e02c2..0000000
--- a/src/old/xmlfilereader.h
+++ /dev/null
@@ -1,47 +0,0 @@
1#ifndef XMLFILEREADER
2#define XMLFILEREADER
3
4#include <stdio.h>
5#include "xmlreader.h"
6#include "flexbuf.h"
7
8/**
9 * Takes care of reading in xml formatted data from a file. This could/should
10 * be made more arbitrary in the future so that we can read the data from any
11 * source. This is actually made quite simple already since all data read in
12 * is handled by one single helper function and then palced into a FlexBuf for
13 * easy access by the other functions. The FlexBuf also allows for block
14 * reading from disk, which improves speed by a noticable amount.
15 * <br>
16 * There are also some extra features implemented that allow you to break the
17 * standard XML reader specs and eliminate leading and trailing whitespace in
18 * all read content. This is useful in situations where you allow additional
19 * whitespace in the files to make them easily human readable. The resturned
20 * content will be NULL in sitautions where all content between nodes was
21 * stripped.
22 *@author Mike Buland
23 */
24class XmlFileReader : public XmlReader
25{
26public:
27 /**
28 * Construct an XmlReader around an xml file on your file system.
29 *@param sFile The file to read.
30 *@param bStrip Set to true to strip out leading and trailing whitespace in
31 * node contents.
32 */
33 XmlFileReader( const char *sFile, bool bStrip=false );
34
35 /**
36 * Destroy the reader and cleanup.
37 */
38 virtual ~XmlFileReader();
39
40private:
41 char getChar( int nIndex = 0 );
42 void usedChar( int nAmnt = 1 );
43 FILE *fh; /**< The file handle. */
44 FlexBuf fbDataIn; /**< The input buffer. */
45};
46
47#endif
diff --git a/src/old/xmlfilewriter.cpp b/src/old/xmlfilewriter.cpp
deleted file mode 100644
index 3c6fb41..0000000
--- a/src/old/xmlfilewriter.cpp
+++ /dev/null
@@ -1,28 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include "xmlfilewriter.h"
4
5XmlFileWriter::XmlFileWriter( const char *sFileName, const char *sIndent, XmlNode *pRoot ) :
6 XmlWriter( sIndent, pRoot )
7{
8 this->sFileName = sFileName;
9 fh = fopen( sFileName, "wt");
10 fprintf( fh, "<?xml version=\"1.0\"?>\n");
11}
12
13XmlFileWriter::XmlFileWriter( FILE *fh, const char *sIndent, XmlNode *pRoot ) :
14 XmlWriter( sIndent, pRoot ),
15 fh( fh )
16{
17}
18
19XmlFileWriter::~XmlFileWriter()
20{
21 fclose( fh );
22}
23
24void XmlFileWriter::writeString( const char *sString )
25{
26 fputs( sString, fh );
27}
28
diff --git a/src/old/xmlfilewriter.h b/src/old/xmlfilewriter.h
deleted file mode 100644
index e328f96..0000000
--- a/src/old/xmlfilewriter.h
+++ /dev/null
@@ -1,45 +0,0 @@
1#ifndef XML_FILE_WRITER
2#define XML_FILE_WRITER
3
4#include "xmlnode.h"
5#include "xmlwriter.h"
6
7/**
8 * Implements xml writing in the XML standard format. Also allows you to
9 * break that format and auto-indent your exported xml data for ease of
10 * reading. The auto-indenting will only be applied to sections that
11 * have no content of their own already. This means that except for
12 * whitespace all of your data will be preserved perfectly.
13 * You can create an XmlWriter object around a file, or access the static
14 * write function directly and just hand it a filename and a root XmlNode.
15 * When using an XmlWriter object the interface is identicle to that of
16 * the XmlDocument class, so reference that class for API info. However
17 * when the initial (or root) node is closed, and the document is finished
18 * the file will be created and written to automatically. The user can
19 * check to see if this is actually true by calling the isFinished
20 * function in the XmlDocument class.
21 *@author Mike Buland
22 */
23class XmlFileWriter : public XmlWriter
24{
25public:
26 /**
27 * Construct a file writer around a given file.
28 *@param sFileName The file to create or overwrite and write XML into.
29 *@param sIndent The indent text to use, if any.
30 */
31 XmlFileWriter( const char *sFileName, const char *sIndent=NULL, XmlNode *pRoot=NULL );
32 XmlFileWriter( FILE *fh, const char *sIndent=NULL, XmlNode *pRoot=NULL );
33
34 /**
35 * Destroy the writer.
36 */
37 virtual ~XmlFileWriter();
38
39private:
40 void writeString( const char *sString );
41 std::string sFileName; /**< The filename to write to. */
42 FILE *fh; /**< The file handle to the open file. */
43};
44
45#endif
diff --git a/src/old/xmlnode.cpp b/src/old/xmlnode.cpp
deleted file mode 100644
index 96d5850..0000000
--- a/src/old/xmlnode.cpp
+++ /dev/null
@@ -1,403 +0,0 @@
1#include "xmlnode.h"
2
3XmlNode::XmlNode( const Bu::FString &sName, XmlNode *pParent ) :
4 sName( sName ),
5 pParent( pParent )
6{
7}
8
9XmlNode::~XmlNode()
10{
11}
12/*
13void XmlNode::setName( const char *sName )
14{
15 if( pParent )
16 {
17 if( this->sName.size() == 0 )
18 {
19 // We're not in the hash yet, so add us
20 this->sName = sName;
21 pParent->hChildren.insert( this->sName.c_str(), this );
22 }
23 else
24 {
25 // Slightly more tricky, delete us, then add us...
26 pParent->hChildren.del( this->sName.c_str() );
27 this->sName = sName;
28 pParent->hChildren.insert( this->sName.c_str(), this );
29 }
30 }
31 else
32 {
33 // If we have no parent, then just set the name string, we don't need
34 // to worry about hashing.
35 this->sName = sName;
36 }
37}
38
39void XmlNode::setContent( const char *sContent, int nIndex )
40{
41 if( nIndex == -1 )
42 {
43 nIndex = nCurContent;
44 }
45 if( nIndex == 0 )
46 {
47 if( this->sPreContent )
48 {
49 delete this->sPreContent;
50 }
51
52 this->sPreContent = new std::string( sContent );
53 }
54 else
55 {
56 nIndex--;
57 if( lPostContent[nIndex] )
58 {
59 delete (std::string *)lPostContent[nIndex];
60 }
61
62 lPostContent.setAt( nIndex, new std::string( sContent ) );
63 }
64}
65
66const char *XmlNode::getContent( int nIndex )
67{
68 if( nIndex == 0 )
69 {
70 if( sPreContent )
71 {
72 return sPreContent->c_str();
73 }
74 }
75 else
76 {
77 nIndex--;
78 if( lPostContent[nIndex] )
79 {
80 return ((std::string *)lPostContent[nIndex])->c_str();
81 }
82 }
83
84 return NULL;
85}*/
86
87XmlNode *XmlNode::addChild( const Bu::FString &sName )
88{
89 return addChild( new XmlNode( sName, this ) );
90}
91
92XmlNode *XmlNode::addChild( XmlNode *pNode )
93{
94 Child c = { typeNode };
95 c.pNode = pNode;
96 lChildren.append( c );
97 pNode->pParent = this;
98
99 return pNode;
100}
101
102XmlNode *XmlNode::getParent()
103{
104 return pParent;
105}
106
107void XmlNode::addProperty( const Bu::FString &sName, const Bu::FString &sValue )
108{
109 hProperties.insert( sName, sValue );
110}
111
112int XmlNode::getNumProperties()
113{
114 return hProperties.size();
115}
116/*
117const char *XmlNode::getPropertyName( int nIndex )
118{
119 std::string *tmp = ((std::string *)lPropNames[nIndex]);
120 if( tmp == NULL )
121 return NULL;
122 return tmp->c_str();
123}
124
125const char *XmlNode::getProperty( int nIndex )
126{
127 std::string *tmp = ((std::string *)lPropValues[nIndex]);
128 if( tmp == NULL )
129 return NULL;
130 return tmp->c_str();
131}
132*/
133Bu::FString XmlNode::getProperty( const Bu::FString &sName )
134{
135 return hProperties[sName];
136}
137/*
138void XmlNode::deleteProperty( int nIndex )
139{
140 hProperties.del( ((std::string *)lPropNames[nIndex])->c_str() );
141
142 delete (std::string *)lPropNames[nIndex];
143 delete (std::string *)lPropValues[nIndex];
144
145 lPropNames.deleteAt( nIndex );
146 lPropValues.deleteAt( nIndex );
147}
148
149bool XmlNode::hasChildren()
150{
151 return hChildren.getSize()>0;
152}*/
153
154int XmlNode::getNumChildren()
155{
156 return lChildren.getSize();
157}
158/*
159XmlNode *XmlNode::getChild( int nIndex )
160{
161 return (XmlNode *)lChildren[nIndex];
162}
163*/
164XmlNode *XmlNode::getChild( const Bu::FString &sName, int nSkip )
165{
166 if( !hChildren.has( sName ) )
167 return NULL;
168
169 Bu::List<XmlNode *>::iterator i = hChildren[sName]->begin();
170 return *i;
171}
172
173Bu::FString XmlNode::getName()
174{
175 return sName;
176}
177/*
178void XmlNode::deleteNode( int nIndex, const char *sReplacementText )
179{
180 XmlNode *xRet = detatchNode( nIndex, sReplacementText );
181
182 if( xRet != NULL )
183 {
184 delete xRet;
185 }
186}
187
188XmlNode *XmlNode::detatchNode( int nIndex, const char *sReplacementText )
189{
190 if( nIndex < 0 || nIndex >= lChildren.getSize() )
191 return NULL;
192
193 // The real trick when deleteing a node isn't actually deleting it, it's
194 // reforming the content around the node that's now missing...hmmm...
195
196 if( nIndex == 0 )
197 {
198 // If the index is zero we have to deal with the pre-content
199 if( sReplacementText )
200 {
201 if( sPreContent == NULL )
202 {
203 sPreContent = new std::string( sReplacementText );
204 }
205 else
206 {
207 *sPreContent += sReplacementText;
208 }
209 }
210 if( lPostContent.getSize() > 0 )
211 {
212 if( lPostContent[0] != NULL )
213 {
214 if( sPreContent == NULL )
215 {
216 sPreContent = new std::string(
217 ((std::string *)lPostContent[0])->c_str()
218 );
219 }
220 else
221 {
222 *sPreContent +=
223 ((std::string *)lPostContent[0])->c_str();
224 }
225 }
226 delete (std::string *)lPostContent[0];
227 lPostContent.deleteAt( 0 );
228 }
229 }
230 else
231 {
232 int nCont = nIndex-1;
233 // If it's above zero we deal with the post-content only
234 if( sReplacementText )
235 {
236 if( lPostContent[nCont] == NULL )
237 {
238 lPostContent.setAt( nCont, new std::string( sReplacementText ) );
239 }
240 else
241 {
242 *((std::string *)lPostContent[nCont]) += sReplacementText;
243 }
244 }
245 if( lPostContent.getSize() > nIndex )
246 {
247 if( lPostContent[nIndex] != NULL )
248 {
249 if( lPostContent[nCont] == NULL )
250 {
251 lPostContent.setAt( nCont, new std::string(
252 ((std::string *)lPostContent[nIndex])->c_str()
253 ) );
254 }
255 else
256 {
257 *((std::string *)lPostContent[nCont]) +=
258 ((std::string *)lPostContent[nIndex])->c_str();
259 }
260 }
261 delete (std::string *)lPostContent[nIndex];
262 lPostContent.deleteAt( nIndex );
263 }
264 }
265
266 XmlNode *xRet = (XmlNode *)lChildren[nIndex];
267 hChildren.del( ((XmlNode *)lChildren[nIndex])->getName() );
268 lChildren.deleteAt( nIndex );
269
270 return xRet;
271}
272
273void XmlNode::replaceNode( int nIndex, XmlNode *pNewNode )
274{
275 if( nIndex < 0 || nIndex >= lChildren.getSize() )
276 return; //TODO: throw an exception
277
278 delete (XmlNode *)lChildren[nIndex];
279 lChildren.setAt( nIndex, pNewNode );
280 pNewNode->pParent = this;
281}
282
283XmlNode *XmlNode::getCopy()
284{
285 XmlNode *pNew = new XmlNode();
286
287 pNew->sName = sName;
288 if( sPreContent )
289 {
290 pNew->sPreContent = new std::string( sPreContent->c_str() );
291 }
292 else
293 {
294 pNew->sPreContent = NULL;
295 }
296 pNew->nCurContent = 0;
297
298 int nSize = lPostContent.getSize();
299 pNew->lPostContent.setSize( nSize );
300 for( int j = 0; j < nSize; j++ )
301 {
302 if( lPostContent[j] )
303 {
304 pNew->lPostContent.setAt(
305 j, new std::string(
306 ((std::string *)lPostContent[j])->c_str()
307 )
308 );
309 }
310 else
311 {
312 pNew->lPostContent.setAt( j, NULL );
313 }
314 }
315
316 nSize = lChildren.getSize();
317 pNew->lChildren.setSize( nSize );
318 for( int j = 0; j < nSize; j++ )
319 {
320 XmlNode *pChild = ((XmlNode *)lChildren[j])->getCopy();
321 pNew->lChildren.setAt( j, pChild );
322 pChild->pParent = pNew;
323 pNew->hChildren.insert( pChild->getName(), pChild );
324 }
325
326 nSize = lPropNames.getSize();
327 pNew->lPropNames.setSize( nSize );
328 pNew->lPropValues.setSize( nSize );
329 for( int j = 0; j < nSize; j++ )
330 {
331 std::string *pProp = new std::string( ((std::string *)lPropNames[j])->c_str() );
332 std::string *pVal = new std::string( ((std::string *)lPropValues[j])->c_str() );
333 pNew->lPropNames.setAt( j, pProp );
334 pNew->lPropValues.setAt( j, pVal );
335 pNew->hProperties.insert( pProp->c_str(), pVal->c_str() );
336 pNew->nCurContent++;
337 }
338
339 return pNew;
340}
341
342void XmlNode::deleteNodeKeepChildren( int nIndex )
343{
344 // This is a tricky one...we need to do some patching to keep things all
345 // even...
346 XmlNode *xRet = (XmlNode *)lChildren[nIndex];
347
348 if( xRet == NULL )
349 {
350 return;
351 }
352 else
353 {
354 if( getContent( nIndex ) )
355 {
356 std::string sBuf( getContent( nIndex ) );
357 sBuf += xRet->getContent( 0 );
358 setContent( sBuf.c_str(), nIndex );
359 }
360 else
361 {
362 setContent( xRet->getContent( 0 ), nIndex );
363 }
364
365 int nSize = xRet->lChildren.getSize();
366 for( int j = 0; j < nSize; j++ )
367 {
368 XmlNode *pCopy = ((XmlNode *)xRet->lChildren[j])->getCopy();
369 pCopy->pParent = this;
370 lChildren.insertBefore( pCopy, nIndex+j );
371
372 if( xRet->lPostContent[j] )
373 {
374 lPostContent.insertBefore(
375 new std::string( ((std::string *)xRet->lPostContent[j])->c_str() ),
376 nIndex+j
377 );
378 }
379 else
380 {
381 lPostContent.insertBefore( NULL, nIndex+j );
382 }
383 }
384
385 if( getContent( nIndex+nSize ) )
386 {
387 //SString sBuf( getContent( nIndex+nSize ) );
388 //sBuf.catfrom( xRet->getContent( nSize ) );
389 //setContent( sBuf, nIndex+nSize );
390 }
391 else
392 {
393 setContent( xRet->getContent( nSize ), nIndex+nSize );
394 }
395
396 deleteNode( nIndex+nSize );
397 }
398}
399
400void XmlNode::replaceNodeWithChildren( int nIndex, XmlNode *pNewNode )
401{
402}
403*/
diff --git a/src/old/xmlnode.h b/src/old/xmlnode.h
deleted file mode 100644
index c895cd8..0000000
--- a/src/old/xmlnode.h
+++ /dev/null
@@ -1,207 +0,0 @@
1#ifndef XMLNODE
2#define XMLNODE
3
4#include <iostream>
5#include "bu/list.h"
6#include "bu/hash.h"
7#include "bu/fstring.h"
8
9/**
10 * Maintains all data pertient to an XML node, including sub-nodes and content.
11 * All child nodes can be accessed through index and through name via a hash
12 * table. This makes it very easy to gain simple and fast access to all of
13 * your data. For most applications, the memory footprint is also rather
14 * small. While XmlNode objects can be used directly to create XML structures
15 * it is highly reccomended that all operations be performed through the
16 * XmlDocument class.
17 *@author Mike Buland
18 */
19class XmlNode
20{
21public:
22 /**
23 * Construct a new XmlNode.
24 *@param sName The name of the node.
25 *@param pParent The parent node.
26 *@param sContent The initial content string.
27 */
28 XmlNode(
29 const Bu::FString &sName,
30 XmlNode *pParent=NULL
31 );
32
33 /**
34 * Delete the node and cleanup all memory.
35 */
36 virtual ~XmlNode();
37
38 /**
39 * Change the name of the node.
40 *@param sName The new name of the node.
41 */
42 //void setName( const char *sName );
43
44 /**
45 * Construct a new node and add it as a child to this node, also return a
46 * pointer to the newly constructed node.
47 *@param sName The name of the new node.
48 *@param sContent The initial content of the new node.
49 *@returns A pointer to the newly created child node.
50 */
51 XmlNode *addChild( const Bu::FString &sName );
52
53 /**
54 * Add an already created XmlNode as a child to this node. The new child
55 * XmlNode's parent will be changed appropriately and the parent XmlNode
56 * will take ownership of the child.
57 *@param pChild The child XmlNode to add to this XmlNode.
58 *@returns A pointer to the child node that was just added.
59 */
60 XmlNode *addChild( XmlNode *pChild );
61
62 /**
63 * Add a new property to the XmlNode. Properties are name/value pairs.
64 *@param sName The name of the property. Specifying a name that's already
65 * in use will overwrite that property.
66 *@param sValue The textual value of the property.
67 */
68 void addProperty( const Bu::FString &sName, const Bu::FString &sValue );
69
70 /**
71 * Get a pointer to the parent node, if any.
72 *@returns A pointer to the node's parent, or NULL if there isn't one.
73 */
74 XmlNode *getParent();
75
76 /**
77 * Tells you if this node has children.
78 *@returns True if this node has at least one child, false otherwise.
79 */
80 bool hasChildren();
81
82 /**
83 * Tells you how many children this node has.
84 *@returns The number of children this node has.
85 */
86 int getNumChildren();
87
88 /**
89 * Get a child with the specified name, and possibly skip value. For an
90 * explination of skip values see the HashTable.
91 *@param sName The name of the child to find.
92 *@param nSkip The number of nodes with that name to skip.
93 *@returns A pointer to the child, or NULL if no child with that name was
94 * found.
95 */
96 XmlNode *getChild( const Bu::FString &sName, int nSkip=0 );
97
98 /**
99 * Get a pointer to the name of this node. Do not change this, use setName
100 * instead.
101 *@returns A pointer to the name of this node.
102 */
103 Bu::FString getName();
104
105 /**
106 * Set the content of this node, optionally at a specific index. Using the
107 * default of -1 will set the content after the last added node.
108 *@param sContent The content string to use.
109 *@param nIndex The index of the content.
110 */
111 //void setContent( const char *sContent, int nIndex=-1 );
112
113 /**
114 * Get the number of properties in this node.
115 *@returns The number of properties in this node.
116 */
117 int getNumProperties();
118
119 /**
120 * Get a propery's value by name.
121 *@param sName The name of the property to examine.
122 *@returns A pointer to the value of the property specified, or NULL if none
123 * found.
124 */
125 Bu::FString getProperty( const Bu::FString &sName );
126
127 /**
128 * Delete a child node, possibly replacing it with some text. This actually
129 * fixes all content strings around the newly deleted child node.
130 *@param nIndex The index of the node to delete.
131 *@param sReplacementText The optional text to replace the node with.
132 *@returns True of the node was found, and deleted, false if it wasn't
133 * found.
134 */
135 //void deleteNode( int nIndex, const char *sReplacementText = NULL );
136
137 /**
138 * Delete a given node, but move all of it's children and content up to
139 * replace the deleted node. All of the content of the child node is
140 * spliced seamlessly into place with the parent node's content.
141 *@param nIndex The node to delete.
142 *@returns True if the node was found and deleted, false if it wasn't.
143 */
144 //void deleteNodeKeepChildren( int nIndex );
145
146 /**
147 * Detatch a given child node from this node. This effectively works just
148 * like a deleteNode, except that instead of deleting the node it is removed
149 * and returned, and all ownership is given up.
150 *@param nIndex The index of the node to detatch.
151 *@param sReplacementText The optional text to replace the detatched node
152 * with.
153 *@returns A pointer to the newly detatched node, which then passes
154 * ownership to the caller.
155 */
156 //XmlNode *detatchNode( int nIndex, const char *sReplacementText = NULL );
157
158 /**
159 * Replace a given node with a different node that is not currently owned by
160 * this XmlNode or any ancestor.
161 *@param nIndex The index of the node to replace.
162 *@param pNewNode The new node to replace the old node with.
163 *@returns True if the node was found and replaced, false if it wasn't.
164 */
165 //void replaceNode( int nIndex, XmlNode *pNewNode );
166
167 /**
168 * Replace a given node with the children and content of a given node.
169 *@param nIndex The index of the node to replace.
170 *@param pNewNode The node that contains the children and content that will
171 * replace the node specified by nIndex.
172 *@returns True if the node was found and replaced, false if it wasn't.
173 */
174 //void replaceNodeWithChildren( int nIndex, XmlNode *pNewNode );
175
176 /**
177 * Get a copy of this node and all children. getCopy is recursive, so
178 * beware copying large trees of xml.
179 *@returns A newly created copy of this node and all of it's children.
180 */
181 //XmlNode *getCopy();
182
183 enum ChildType
184 {
185 typeNode,
186 typeContent
187 };
188
189private:
190 typedef struct
191 {
192 uint8_t nType;
193 union {
194 XmlNode *pNode;
195 Bu::FString *pContent;
196 };
197 } Child;
198 Bu::FString sName; /**< The name of the node. */
199 Bu::List<Child> lChildren; /**< The children. */
200 Bu::Hash<Bu::FString, Bu::FString> hProperties; /**< Property hashtable. */
201 Bu::Hash<Bu::FString, Bu::List<XmlNode *> > hChildren; /**< Children hashtable. */
202 XmlNode *pParent; /**< A pointer to the parent of this node. */
203 int nCurContent; /**< The current content we're on, for using the -1 on
204 setContent. */
205};
206
207#endif
diff --git a/src/old/xmlreader.cpp b/src/old/xmlreader.cpp
deleted file mode 100644
index 38cad5f..0000000
--- a/src/old/xmlreader.cpp
+++ /dev/null
@@ -1,604 +0,0 @@
1#include "bu/xmlreader.h"
2#include "bu/exceptions.h"
3#include <string.h>
4
5XmlReader::XmlReader( Bu::Stream &sIn, bool bStrip ) :
6 sIn( sIn ),
7 bStrip( bStrip )
8{
9 buildDoc();
10}
11
12XmlReader::~XmlReader()
13{
14}
15
16char XmlReader::getChar( int nIndex )
17{
18 if( sBuf.getSize() <= nIndex )
19 {
20 int nInc = nIndex-sBuf.getSize()+1;
21 char *buf = new char[nInc];
22 sIn.read( buf, nInc );
23 sBuf.append( buf, nInc );
24 delete[] buf;
25 }
26
27 return sBuf[nIndex];
28}
29
30void XmlReader::usedChar( int nAmnt )
31{
32 if( nAmnt >= sBuf.getSize() )
33 {
34 sBuf.clear();
35 }
36 else
37 {
38 char *s = sBuf.getStr();
39 memcpy( s, s+nAmnt, sBuf.getSize()-nAmnt );
40 sBuf.resize( sBuf.getSize()-nAmnt );
41 }
42}
43
44void XmlReader::addEntity( const Bu::FString &name, const Bu::FString &value )
45{
46 htEntity[name] = value;
47}
48
49#define gcall( x ) if( x == false ) return false;
50
51bool XmlReader::isws( char chr )
52{
53 return ( chr == ' ' || chr == '\t' || chr == '\n' || chr == '\r' );
54}
55
56bool XmlReader::ws()
57{
58 while( true )
59 {
60 char chr = getChar();
61 if( isws( chr ) )
62 {
63 usedChar();
64 }
65 else
66 {
67 return true;
68 }
69 }
70 return true;
71}
72
73bool XmlReader::buildDoc()
74{
75 // take care of initial whitespace
76 gcall( ws() );
77 textDecl();
78 entity();
79 addEntity("gt", ">");
80 addEntity("lt", "<");
81 addEntity("amp", "&");
82 addEntity("apos", "\'");
83 addEntity("quot", "\"");
84 gcall( node() );
85
86 return true;
87}
88
89void XmlReader::textDecl()
90{
91 if( getChar() == '<' && getChar( 1 ) == '?' )
92 {
93 usedChar( 2 );
94 for(;;)
95 {
96 if( getChar() == '?' )
97 {
98 if( getChar( 1 ) == '>' )
99 {
100 usedChar( 2 );
101 return;
102 }
103 }
104 usedChar();
105 }
106 }
107}
108
109void XmlReader::entity()
110{
111 for(;;)
112 {
113 ws();
114
115 if( getChar() == '<' && getChar( 1 ) == '!' )
116 {
117 usedChar( 2 );
118 ws();
119 Bu::FString buf;
120 for(;;)
121 {
122 char chr = getChar();
123 usedChar();
124 if( isws( chr ) ) break;
125 buf += chr;
126 }
127
128 if( strcmp( buf.c_str(), "ENTITY") == 0 )
129 {
130 ws();
131 Bu::FString name;
132 for(;;)
133 {
134 char chr = getChar();
135 usedChar();
136 if( isws( chr ) ) break;
137 name += chr;
138 }
139 ws();
140 char quot = getChar();
141 usedChar();
142 if( quot != '\'' && quot != '\"' )
143 {
144 throw Bu::XmlException(
145 "Only quoted entity values are supported."
146 );
147 }
148 Bu::FString value;
149 for(;;)
150 {
151 char chr = getChar();
152 usedChar();
153 if( chr == '&' )
154 {
155 Bu::FString tmp = getEscape();
156 value += tmp;
157 }
158 else if( chr == quot )
159 {
160 break;
161 }
162 else
163 {
164 value += chr;
165 }
166 }
167 ws();
168 if( getChar() == '>' )
169 {
170 usedChar();
171
172 addEntity( name.c_str(), value.c_str() );
173 }
174 else
175 {
176 throw Bu::XmlException(
177 "Malformed ENTITY: unexpected '%c' found.",
178 getChar()
179 );
180 }
181 }
182 else
183 {
184 throw Bu::XmlException(
185 "Unsupported header symbol: %s",
186 buf.c_str()
187 );
188 }
189 }
190 else
191 {
192 return;
193 }
194 }
195}
196
197bool XmlReader::node()
198{
199 gcall( startNode() )
200
201 // At this point, we are closing the startNode
202 char chr = getChar();
203 if( chr == '>' )
204 {
205 usedChar();
206
207 // Now we process the guts of the node.
208 gcall( content() );
209 }
210 else if( chr == '/' )
211 {
212 // This is the tricky one, one more validation, then we close the node.
213 usedChar();
214 if( getChar() == '>' )
215 {
216 closeNode();
217 usedChar();
218 }
219 else
220 {
221 throw Bu::XmlException("Close node in singleNode malformed!");
222 }
223 }
224 else
225 {
226 throw Bu::XmlException("Close node expected, but not found.");
227 return false;
228 }
229
230 return true;
231}
232
233bool XmlReader::startNode()
234{
235 if( getChar() == '<' )
236 {
237 usedChar();
238
239 if( getChar() == '/' )
240 {
241 // Heh, it's actually a close node, go figure
242 Bu::FString sName;
243 usedChar();
244 gcall( ws() );
245
246 while( true )
247 {
248 char chr = getChar();
249 if( isws( chr ) || chr == '>' )
250 {
251 // Here we actually compare the name we got to the name
252 // we already set, they have to match exactly.
253 if( getCurrent()->getName() == sName )
254 {
255 closeNode();
256 break;
257 }
258 else
259 {
260 throw Bu::XmlException("Got a mismatched node close tag.");
261 }
262 }
263 else
264 {
265 sName += chr;
266 usedChar();
267 }
268 }
269
270 gcall( ws() );
271 if( getChar() == '>' )
272 {
273 // Everything is cool.
274 usedChar();
275 }
276 else
277 {
278 throw Bu::XmlException("Got extra junk data instead of node close tag.");
279 }
280 }
281 else
282 {
283 // We're good, format is consistant
284 //addNode();
285
286 // Skip extra whitespace
287 gcall( ws() );
288 gcall( name() );
289 gcall( ws() );
290 gcall( paramlist() );
291 gcall( ws() );
292 }
293 }
294 else
295 {
296 throw Bu::XmlException("Expected to find node opening char, '<'.");
297 }
298
299 return true;
300}
301
302bool XmlReader::name()
303{
304 Bu::FString sName;
305
306 while( true )
307 {
308 char chr = getChar();
309 if( isws( chr ) || chr == '>' || chr == '/' )
310 {
311 addNode( sName );
312 return true;
313 }
314 else
315 {
316 sName += chr;
317 usedChar();
318 }
319 }
320
321 return true;
322}
323
324bool XmlReader::paramlist()
325{
326 while( true )
327 {
328 char chr = getChar();
329 if( chr == '/' || chr == '>' )
330 {
331 return true;
332 }
333 else
334 {
335 gcall( param() );
336 gcall( ws() );
337 }
338 }
339
340 return true;
341}
342
343Bu::FString XmlReader::getEscape()
344{
345 if( getChar( 1 ) == '#' )
346 {
347 // If the entity starts with a # it's a character escape code
348 int base = 10;
349 usedChar( 2 );
350 if( getChar() == 'x' )
351 {
352 base = 16;
353 usedChar();
354 }
355 char buf[4];
356 int j = 0;
357 for( j = 0; getChar() != ';'; j++ )
358 {
359 buf[j] = getChar();
360 usedChar();
361 }
362 usedChar();
363 buf[j] = '\0';
364 buf[0] = (char)strtol( buf, (char **)NULL, base );
365 buf[1] = '\0';
366
367 return buf;
368 }
369 else
370 {
371 // ...otherwise replace with the appropriate string...
372 Bu::FString buf;
373 usedChar();
374 for(;;)
375 {
376 char cbuf = getChar();
377 usedChar();
378 if( cbuf == ';' ) break;
379 buf += cbuf;
380 }
381
382 return htEntity[buf];
383 }
384}
385
386bool XmlReader::param()
387{
388 Bu::FString sName;
389 Bu::FString sValue;
390
391 while( true )
392 {
393 char chr = getChar();
394 if( isws( chr ) || chr == '=' )
395 {
396 break;
397 }
398 else
399 {
400 sName.append( chr );
401 usedChar();
402 }
403 }
404
405 gcall( ws() );
406
407 if( getChar() == '=' )
408 {
409 usedChar();
410
411 gcall( ws() );
412
413 char chr = getChar();
414 if( chr == '"' )
415 {
416 // Better quoted rhs
417 usedChar();
418
419 while( true )
420 {
421 chr = getChar();
422 if( chr == '"' )
423 {
424 usedChar();
425 addProperty( sName.getStr(), sValue.getStr() );
426 return true;
427 }
428 else
429 {
430 if( chr == '&' )
431 {
432 sValue += getEscape();
433 }
434 else
435 {
436 sValue += chr;
437 usedChar();
438 }
439 }
440 }
441 }
442 else
443 {
444 // Simple one-word rhs
445 while( true )
446 {
447 chr = getChar();
448 if( isws( chr ) || chr == '/' || chr == '>' )
449 {
450 addProperty( sName.getStr(), sValue.getStr() );
451 return true;
452 }
453 else
454 {
455 if( chr == '&' )
456 {
457 sValue += getEscape();
458 }
459 else
460 {
461 sValue += chr;
462 usedChar();
463 }
464 }
465 }
466 }
467 }
468 else
469 {
470 throw Bu::XmlException("Expected an equals to seperate the params.");
471 return false;
472 }
473
474 return true;
475}
476
477bool XmlReader::content()
478{
479 Bu::FString sContent;
480
481 if( bStrip ) gcall( ws() );
482
483 while( true )
484 {
485 char chr = getChar();
486 if( chr == '<' )
487 {
488 if( getChar(1) == '/' )
489 {
490 if( sContent.getSize() > 0 )
491 {
492 if( bStrip )
493 {
494 int j;
495 for( j = sContent.getSize()-1; isws(sContent[j]); j-- );
496 sContent[j+1] = '\0';
497 }
498 setContent( sContent.getStr() );
499 }
500 usedChar( 2 );
501 gcall( ws() );
502 Bu::FString sName;
503 while( true )
504 {
505 chr = getChar();
506 if( isws( chr ) || chr == '>' )
507 {
508 if( !strcasecmp( getCurrent()->getName().getStr(), sName.getStr() ) )
509 {
510 closeNode();
511 break;
512 }
513 else
514 {
515 throw Bu::XmlException("Mismatched close tag found: <%s> to <%s>.", getCurrent()->getName().getStr(), sName.getStr() );
516 }
517 }
518 else
519 {
520 sName += chr;
521 usedChar();
522 }
523 }
524 gcall( ws() );
525 if( getChar() == '>' )
526 {
527 usedChar();
528 return true;
529 }
530 else
531 {
532 throw Bu::XmlException("Malformed close tag.");
533 }
534 }
535 else if( getChar(1) == '!' )
536 {
537 // We know it's a comment, let's see if it's proper
538 if( getChar(2) != '-' ||
539 getChar(3) != '-' )
540 {
541 // Not a valid XML comment
542 throw Bu::XmlException("Malformed comment start tag found.");
543 }
544
545 usedChar( 4 );
546
547 // Now burn text until we find the close tag
548 for(;;)
549 {
550 if( getChar() == '-' )
551 {
552 if( getChar( 1 ) == '-' )
553 {
554 // The next one has to be a '>' now
555 if( getChar( 2 ) != '>' )
556 {
557 throw Bu::XmlException("Malformed comment close tag found. You cannot have a '--' that isn't followed by a '>' in a comment.");
558 }
559 usedChar( 3 );
560 break;
561 }
562 else
563 {
564 // Found a dash followed by a non dash, that's ok...
565 usedChar( 2 );
566 }
567 }
568 else
569 {
570 // Burn comment chars
571 usedChar();
572 }
573 }
574 }
575 else
576 {
577 if( sContent.getSize() > 0 )
578 {
579 if( bStrip )
580 {
581 int j;
582 for( j = sContent.getSize()-1; isws(sContent[j]); j-- );
583 sContent[j+1] = '\0';
584 }
585 setContent( sContent.getStr() );
586 sContent.clear();
587 }
588 gcall( node() );
589 }
590
591 if( bStrip ) gcall( ws() );
592 }
593 else if( chr == '&' )
594 {
595 sContent += getEscape();
596 }
597 else
598 {
599 sContent += chr;
600 usedChar();
601 }
602 }
603}
604
diff --git a/src/old/xmlreader.h b/src/old/xmlreader.h
deleted file mode 100644
index 7c85ddb..0000000
--- a/src/old/xmlreader.h
+++ /dev/null
@@ -1,144 +0,0 @@
1#ifndef XMLREADER
2#define XMLREADER
3
4#include <stdio.h>
5#include "bu/xmldocument.h"
6#include "bu/hash.h"
7#include "bu/fstring.h"
8#include "bu/stream.h"
9
10/**
11 * Takes care of reading in xml formatted data from a file. This could/should
12 * be made more arbitrary in the future so that we can read the data from any
13 * source. This is actually made quite simple already since all data read in
14 * is handled by one single helper function and then palced into a FlexBuf for
15 * easy access by the other functions. The FlexBuf also allows for block
16 * reading from disk, which improves speed by a noticable amount.
17 * <br>
18 * There are also some extra features implemented that allow you to break the
19 * standard XML reader specs and eliminate leading and trailing whitespace in
20 * all read content. This is useful in situations where you allow additional
21 * whitespace in the files to make them easily human readable. The resturned
22 * content will be NULL in sitautions where all content between nodes was
23 * stripped.
24 *@author Mike Buland
25 */
26class XmlReader : public XmlDocument
27{
28public:
29 /**
30 * Create a standard XmlReader. The optional parameter bStrip allows you to
31 * create a reader that will strip out all leading and trailing whitespace
32 * in content, a-la html.
33 *@param bStrip Strip out leading and trailing whitespace?
34 */
35 XmlReader( Bu::Stream &sIn, bool bStrip=false );
36
37 /**
38 * Destroy this XmlReader.
39 */
40 virtual ~XmlReader();
41
42 /**
43 * Build a document based on some kind of input. This is called
44 * automatically by the constructor.
45 */
46 bool buildDoc();
47
48private:
49 /**
50 * This is called by the low level automoton in order to get the next
51 * character. This function should return a character at the current
52 * position plus nIndex, but does not increment the current character.
53 *@param nIndex The index of the character from the current stream position.
54 *@returns A single character at the requested position, or 0 for end of
55 * stream.
56 */
57 virtual char getChar( int nIndex = 0 );
58
59 /**
60 * Called to increment the current stream position by a single character.
61 */
62 virtual void usedChar( int nAmnt = 1 );
63
64 /**
65 * Automoton function: is whitespace.
66 *@param chr A character
67 *@returns True if chr is whitespace, false otherwise.
68 */
69 bool isws( char chr );
70
71 /**
72 * Automoton function: ws. Skips sections of whitespace.
73 *@returns True if everything was ok, False for end of stream.
74 */
75 bool ws();
76
77 /**
78 * Automoton function: node. Processes an XmlNode
79 *@returns True if everything was ok, False for end of stream.
80 */
81 bool node();
82
83 /**
84 * Automoton function: startNode. Processes the begining of a node.
85 *@returns True if everything was ok, False for end of stream.
86 */
87 bool startNode();
88
89 /**
90 * Automoton function: name. Processes the name of a node.
91 *@returns True if everything was ok, False for end of stream.
92 */
93 bool name();
94
95 /**
96 * Automoton function: textDecl. Processes the xml text decleration, if
97 * there is one.
98 */
99 void textDecl();
100
101 /**
102 * Automoton function: entity. Processes an entity from the header.
103 */
104 void entity();
105
106 /**
107 * Adds an entity to the list, if it doesn't already exist.
108 *@param name The name of the entity
109 *@param value The value of the entity
110 */
111 void addEntity( const Bu::FString &name, const Bu::FString &value );
112
113 Bu::FString getEscape();
114
115 /**
116 * Automoton function: paramlist. Processes a list of node params.
117 *@returns True if everything was ok, False for end of stream.
118 */
119 bool paramlist();
120
121 /**
122 * Automoton function: param. Processes a single parameter.
123 *@returns True if everything was ok, False for end of stream.
124 */
125 bool param();
126
127 /**
128 * Automoton function: content. Processes node content.
129 *@returns True if everything was ok, False for end of stream.
130 */
131 bool content();
132
133 Bu::FString sContent; /**< buffer for the current node's content. */
134 Bu::FString sParamName; /**< buffer for the current param's name. */
135 Bu::FString sParamValue; /**< buffer for the current param's value. */
136 Bu::Stream &sIn;
137 bool bStrip; /**< Are we stripping whitespace? */
138
139 Bu::Hash<Bu::FString,Bu::FString> htEntity; /**< Entity type definitions. */
140
141 Bu::FString sBuf;
142};
143
144#endif
diff --git a/src/old/xmlstringreader.cpp b/src/old/xmlstringreader.cpp
deleted file mode 100644
index 3956ff3..0000000
--- a/src/old/xmlstringreader.cpp
+++ /dev/null
@@ -1,38 +0,0 @@
1#include "xmlstringreader.h"
2#include "exceptions.h"
3#include <string.h>
4
5XmlStringReader::XmlStringReader( const char *sString, bool bStrip )
6 : XmlReader( bStrip )
7{
8 this->sString = sString;
9
10 nIndex = 0;
11 nLength = strlen( sString );
12
13 buildDoc();
14}
15
16XmlStringReader::~XmlStringReader()
17{
18}
19
20char XmlStringReader::getChar( int nAdd )
21{
22 if( nLength >= nIndex+nAdd+1 )
23 {
24 return sString[nIndex+nAdd];
25 }
26 else
27 {
28 throw XmlException("End of XML stream read.");
29 }
30}
31
32void XmlStringReader::usedChar( int nAmnt )
33{
34 if( nLength >= nIndex+nAmnt )
35 {
36 nIndex += nAmnt;
37 }
38}
diff --git a/src/old/xmlstringreader.h b/src/old/xmlstringreader.h
deleted file mode 100644
index 1239ef4..0000000
--- a/src/old/xmlstringreader.h
+++ /dev/null
@@ -1,49 +0,0 @@
1#ifndef XMLSTRINGREADER
2#define XMLSTRINGREADER
3
4#include <stdio.h>
5#include "xmlreader.h"
6#include "flexbuf.h"
7
8/**
9 * Takes care of reading in xml formatted data from a file. This could/should
10 * be made more arbitrary in the future so that we can read the data from any
11 * source. This is actually made quite simple already since all data read in
12 * is handled by one single helper function and then palced into a FlexBuf for
13 * easy access by the other functions. The FlexBuf also allows for block
14 * reading from disk, which improves speed by a noticable amount.
15 * <br>
16 * There are also some extra features implemented that allow you to break the
17 * standard XML reader specs and eliminate leading and trailing whitespace in
18 * all read content. This is useful in situations where you allow additional
19 * whitespace in the files to make them easily human readable. The resturned
20 * content will be NULL in sitautions where all content between nodes was
21 * stripped.
22 *@author Mike Buland
23 */
24class XmlStringReader : public XmlReader
25{
26public:
27 /**
28 * Create a new string reader around an already created and formatted
29 * null-terminated string.
30 *@param sString A pointer to the string data that will be used. This data
31 * is not changed during processing.
32 *@param bStrip Strip out leading and trailing whitespace.
33 */
34 XmlStringReader( const char *sString, bool bStrip=false );
35
36 /**
37 * Destroy this string reader.
38 */
39 virtual ~XmlStringReader();
40
41private:
42 char getChar( int nIndex = 0 );
43 void usedChar( int nAmnt = 1 );
44 const char *sString; /**< Internal pointer to the input string. */
45 int nIndex; /**< Our index into the string */
46 int nLength; /**< The computed length of the string */
47};
48
49#endif
diff --git a/src/old/xmlstringwriter.cpp b/src/old/xmlstringwriter.cpp
deleted file mode 100644
index adeed6a..0000000
--- a/src/old/xmlstringwriter.cpp
+++ /dev/null
@@ -1,23 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include "xmlstringwriter.h"
4
5XmlStringWriter::XmlStringWriter( const char *sIndent ) :
6 XmlWriter( sIndent )
7{
8}
9
10XmlStringWriter::~XmlStringWriter()
11{
12}
13
14void XmlStringWriter::writeString( const char *sString )
15{
16 sXml += sString;
17}
18
19std::string &XmlStringWriter::getString()
20{
21 return sXml;
22}
23
diff --git a/src/old/xmlstringwriter.h b/src/old/xmlstringwriter.h
deleted file mode 100644
index 0d567b9..0000000
--- a/src/old/xmlstringwriter.h
+++ /dev/null
@@ -1,50 +0,0 @@
1#ifndef XML_STRING_WRITER
2#define XML_STRING_WRITER
3
4#include "xmlnode.h"
5#include "xmlwriter.h"
6
7/**
8 * Implements xml writing in the XML standard format. Also allows you to
9 * break that format and auto-indent your exported xml data for ease of
10 * reading. The auto-indenting will only be applied to sections that
11 * have no content of their own already. This means that except for
12 * whitespace all of your data will be preserved perfectly.
13 * You can create an XmlWriter object around a file, or access the static
14 * write function directly and just hand it a filename and a root XmlNode.
15 * When using an XmlWriter object the interface is identicle to that of
16 * the XmlDocument class, so reference that class for API info. However
17 * when the initial (or root) node is closed, and the document is finished
18 * the file will be created and written to automatically. The user can
19 * check to see if this is actually true by calling the isFinished
20 * function in the XmlDocument class.
21 *@author Mike Buland
22 */
23class XmlStringWriter : public XmlWriter
24{
25public:
26 /**
27 * Construct a string writer using an internal string buffer.
28 *@param sIndent Optional indent to add to each line.
29 */
30 XmlStringWriter( const char *sIndent=NULL );
31
32 /**
33 * Destroy the string writer and the internal string.
34 */
35 virtual ~XmlStringWriter();
36
37 /**
38 * Get the string that was built. This is only valid after the document has
39 * been completed, so check isCompleted or be sure your addNode and
40 * closeNode calls match up.
41 *@returns A reference to the internal string object.
42 */
43 std::string &getString();
44
45private:
46 void writeString( const char *sString );
47 std::string sXml; /**< The string object we "write" to. */
48};
49
50#endif
diff --git a/src/old/xmlwriter.cpp b/src/old/xmlwriter.cpp
deleted file mode 100644
index 7dc6ca9..0000000
--- a/src/old/xmlwriter.cpp
+++ /dev/null
@@ -1,167 +0,0 @@
1#include <stdio.h>
2#include <stdlib.h>
3#include "xmlwriter.h"
4
5XmlWriter::XmlWriter( const Bu::FString &sIndent, XmlNode *pRoot ) :
6 XmlDocument( pRoot ),
7 sIndent( sIndent )
8{
9}
10
11XmlWriter::~XmlWriter()
12{
13}
14
15void XmlWriter::write()
16{
17 write( getRoot(), sIndent.c_str() );
18}
19
20void XmlWriter::write( XmlNode *pRoot, const Bu::FString &sIndent )
21{
22 writeNode( pRoot, 0, sIndent );
23}
24
25void XmlWriter::closeNode()
26{
27 XmlDocument::closeNode();
28
29 if( isCompleted() )
30 {
31 write( getRoot(), sIndent.c_str() );
32 }
33}
34
35void XmlWriter::writeIndent( int nIndent, const Bu::FString &sIndent )
36{
37 if( sIndent == NULL ) return;
38 for( int j = 0; j < nIndent; j++ )
39 {
40 writeString( sIndent );
41 }
42}
43
44Bu::FString XmlWriter::escape( const Bu::FString &sIn )
45{
46 Bu::FString sOut;
47
48 int nMax = sIn.getSize();
49 for( int j = 0; j < nMax; j++ )
50 {
51 char c = sIn[j];
52 if( ((c >= ' ' && c <= '9') ||
53 (c >= 'a' && c <= 'z') ||
54 (c >= 'A' && c <= 'Z') ) &&
55 (c != '\"' && c != '\'' && c != '&')
56 )
57 {
58 sOut += c;
59 }
60 else
61 {
62 sOut += "&#";
63 char buf[4];
64 sprintf( buf, "%u", (unsigned char)c );
65 sOut += buf;
66 sOut += ';';
67 }
68 }
69
70 return sOut;
71}
72
73void XmlWriter::writeNodeProps( XmlNode *pNode, int nIndent, const Bu::FString &sIndent )
74{
75 for( int j = 0; j < pNode->getNumProperties(); j++ )
76 {
77 writeString(" ");
78 //writeString( pNode->getPropertyName( j ) );
79 writeString("=\"");
80 //writeString( escape( pNode->getProperty( j ) ).c_str() );
81 writeString("\"");
82 }
83}
84
85void XmlWriter::writeNode( XmlNode *pNode, int nIndent, const Bu::FString &sIndent )
86{
87 if( pNode->hasChildren() )
88 {
89 writeIndent( nIndent, sIndent );
90 writeString("<");
91 writeString( pNode->getName() );
92 writeNodeProps( pNode, nIndent, sIndent );
93 if( sIndent != "" )
94 writeString(">\n");
95 else
96 writeString(">");
97/*
98 if( pNode->getContent( 0 ) )
99 {
100 writeIndent( nIndent+1, sIndent );
101 if( sIndent != "" )
102 {
103 writeString( pNode->getContent( 0 ) );
104 writeString("\n");
105 }
106 else
107 writeString( pNode->getContent( 0 ) );
108 }
109
110 int nNumChildren = pNode->getNumChildren();
111 for( int j = 0; j < nNumChildren; j++ )
112 {
113 writeNode( pNode->getChild( j ), nIndent+1, sIndent );
114 if( pNode->getContent( j+1 ) )
115 {
116 writeIndent( nIndent+1, sIndent );
117 if( sIndent )
118 {
119 writeString( pNode->getContent( j+1 ) );
120 writeString("\n");
121 }
122 else
123 writeString( pNode->getContent( j+1 ) );
124 }
125 }
126*/
127 writeIndent( nIndent, sIndent );
128 if( sIndent != "" )
129 {
130 writeString("</");
131 writeString( pNode->getName() );
132 writeString(">\n");
133 }
134 else
135 {
136 writeString("</");
137 writeString( pNode->getName() );
138 writeString(">");
139 }
140 }/*
141 else if( pNode->getContent() )
142 {
143 writeIndent( nIndent, sIndent );
144 writeString("<");
145 writeString( pNode->getName() );
146 writeNodeProps( pNode, nIndent, sIndent );
147 writeString(">");
148 writeString( pNode->getContent() );
149 writeString("</");
150 writeString( pNode->getName() );
151 writeString(">");
152 if( sIndent )
153 writeString("\n");
154 }*/
155 else
156 {
157 writeIndent( nIndent, sIndent );
158 writeString("<");
159 writeString( pNode->getName() );
160 writeNodeProps( pNode, nIndent, sIndent );
161 if( sIndent != "" )
162 writeString("/>\n");
163 else
164 writeString("/>");
165 }
166}
167
diff --git a/src/old/xmlwriter.h b/src/old/xmlwriter.h
deleted file mode 100644
index 7e3c876..0000000
--- a/src/old/xmlwriter.h
+++ /dev/null
@@ -1,96 +0,0 @@
1#ifndef XMLWRITER
2#define XMLWRITER
3
4#include "xmlnode.h"
5#include "xmldocument.h"
6
7/**
8 * Implements xml writing in the XML standard format. Also allows you to
9 * break that format and auto-indent your exported xml data for ease of
10 * reading. The auto-indenting will only be applied to sections that
11 * have no content of their own already. This means that except for
12 * whitespace all of your data will be preserved perfectly.
13 * You can create an XmlWriter object around a file, or access the static
14 * write function directly and just hand it a filename and a root XmlNode.
15 * When using an XmlWriter object the interface is identicle to that of
16 * the XmlDocument class, so reference that class for API info. However
17 * when the initial (or root) node is closed, and the document is finished
18 * the file will be created and written to automatically. The user can
19 * check to see if this is actually true by calling the isFinished
20 * function in the XmlDocument class.
21 *@author Mike Buland
22 */
23class XmlWriter : public XmlDocument
24{
25public:
26 /**
27 * Construct a standard XmlWriter.
28 *@param sIndent Set this to something other than NULL to include it as an
29 * indent before each node in the output that doesn't already have content.
30 * If you are using the whitespace stripping option in the XmlReader and set
31 * this to a tab or some spaces it will never effect the content of your
32 * file.
33 */
34 XmlWriter( const Bu::FString &sIndent="", XmlNode *pRoot=NULL );
35
36 /**
37 * Destroy the writer.
38 */
39 virtual ~XmlWriter();
40
41 /**
42 * This override of the parent class closeNode function calls the parent
43 * class, but also triggers a write operation when the final node is closed.
44 * This means that by checking the isCompleted() function the user may also
45 * check to see if their file has been written or not.
46 */
47 void closeNode();
48
49 void write();
50
51private:
52 Bu::FString sIndent; /**< The indent string */
53
54 Bu::FString escape( const Bu::FString &sIn );
55
56 /**
57 * Write the file.
58 *@param pNode The root node
59 *@param sIndent The indent text.
60 */
61 void write( XmlNode *pNode, const Bu::FString &sIndent );
62
63 /**
64 * Write a node in the file, including children.
65 *@param pNode The node to write.
66 *@param nIndent The indent level (the number of times to include sIndent)
67 *@param sIndent The indent text.
68 */
69 void writeNode( XmlNode *pNode, int nIndent, const Bu::FString &sIndent );
70
71 /**
72 * Write the properties of a node.
73 *@param pNode The node who's properties to write.
74 *@param nIndent The indent level of the containing node
75 *@param sIndent The indent text.
76 */
77 void writeNodeProps( XmlNode *pNode, int nIndent, const Bu::FString &sIndent );
78
79 /**
80 * Called to write the actual indent.
81 *@param nIndent The indent level.
82 *@param sIndent The indent text.
83 */
84 void writeIndent( int nIndent, const Bu::FString &sIndent );
85
86 /**
87 * This is the function that must be overridden in order to use this class.
88 * It must write the null-terminated string sString, minus the mull,
89 * verbatum to it's output device. Adding extra characters for any reason
90 * will break the XML formatting.
91 *@param sString The string data to write to the output.
92 */
93 virtual void writeString( const Bu::FString &sString ) = 0;
94};
95
96#endif