2 Copyright (C) 2004 by Intra2net AG
4 The software in this package is distributed under the GNU General
5 Public License version 2 (with a special exception described below).
7 A copy of GNU General Public License (GPL) is included in this distribution,
8 in the file COPYING.GPL.
10 As a special exception, if other files instantiate templates or use macros
11 or inline functions from this file, or you compile this file and link it
12 with other works to produce a work based on this file, this file
13 does not by itself cause the resulting work to be covered
14 by the GNU General Public License.
16 However the source code for this file must still be made available
17 in accordance with section (3) of the GNU General Public License.
19 This exception does not invalidate any other reasons why a work based
20 on this file might be covered by the GNU General Public License.
22 #include <sys/types.h>
33 #include <boost/bind.hpp>
35 #include <cppunit/extensions/TestFactoryRegistry.h>
36 #include <cppunit/ui/text/TestRunner.h>
37 #include <cppunit/extensions/HelperMacros.h>
39 #include <t2n_exception.hxx>
40 #include <socket_client.hxx>
41 #include <socket_server.hxx>
42 #include <command_client.hxx>
49 using namespace libt2n;
50 using namespace CppUnit;
52 // this is an evil hack to get access to real_write, don't ever do this in an app!!!
53 class real_write_connection: public socket_server_connection
56 void real_write(const std::string& data)
57 { socket_write(data); }
60 class test_hello : public TestFixture
62 CPPUNIT_TEST_SUITE(test_hello);
64 CPPUNIT_TEST(HelloOk);
66 CPPUNIT_TEST(BadVersion);
67 CPPUNIT_TEST(SeparatorMissing);
68 CPPUNIT_TEST(WrongByteOrder);
69 CPPUNIT_TEST(OtherServerBig);
70 CPPUNIT_TEST(OtherServerSmall);
72 CPPUNIT_TEST_SUITE_END();
83 // make sure the server-child is dead before the next test runs
84 kill(child_pid,SIGKILL);
88 void send_hello(string hello_string, socket_server* ss, int conn_id)
90 server_connection *sc=ss->get_connection(conn_id);
91 sc->write(hello_string);
94 void send_raw_socket(string hello_string, socket_server* ss, int conn_id)
96 socket_server_connection *ssc=dynamic_cast<socket_server_connection*>(ss->get_connection(conn_id));
98 // this is an evil hack to get access to real_write, don't ever do this in an app!!!
99 real_write_connection *rwc=(real_write_connection*)ssc;
100 rwc->real_write(hello_string);
105 switch(child_pid=fork())
109 CPPUNIT_FAIL("fork error");
117 socket_server ss("./socket");
120 hello << "T2Nv" << PROTOCOL_VERSION << ';';
121 int byteordercheck=1;
122 hello.write((char*)&byteordercheck,sizeof(byteordercheck));
125 ss.add_callback(new_connection,bind(&test_hello::send_hello, boost::ref(*this), hello.str(),&ss, _1));
128 for (int i=0; i < 10; i++)
129 ss.fill_buffer(1000000);
132 std::cerr << "exception in child. ignoring\n";
135 // don't call atexit and stuff
144 // wait till server is up
146 socket_client_connection sc("./socket");
147 command_client cc(&sc);
154 switch(child_pid=fork())
158 CPPUNIT_FAIL("fork error");
166 socket_server ss("./socket");
171 ss.add_callback(new_connection,bind(&test_hello::send_hello, boost::ref(*this), hello.str(),&ss, _1));
174 for (int i=0; i < 10; i++)
175 ss.fill_buffer(1000000);
178 std::cerr << "exception in child. ignoring\n";
181 // don't call atexit and stuff
190 // wait till server is up
192 socket_client_connection sc("./socket");
194 command_client cc(&sc);
196 t2n_exception* ep=cc.get_constuctor_exception();
202 CPPUNIT_ASSERT_EQUAL(string("illegal hello received (T2N)"),errormsg);
209 switch(child_pid=fork())
213 CPPUNIT_FAIL("fork error");
221 socket_server ss("./socket");
224 // lets hope we don't ever get near such a version number...
225 hello << "T2Nv" << 4982271 << ';';
226 int byteordercheck=1;
227 hello.write((char*)&byteordercheck,sizeof(byteordercheck));
230 ss.add_callback(new_connection,bind(&test_hello::send_hello, boost::ref(*this), hello.str(),&ss, _1));
233 for (int i=0; i < 10; i++)
234 ss.fill_buffer(1000000);
237 std::cerr << "exception in child. ignoring\n";
240 // don't call atexit and stuff
249 // wait till server is up
251 socket_client_connection sc("./socket");
253 command_client cc(&sc);
255 t2n_exception* ep=cc.get_constuctor_exception();
261 CPPUNIT_ASSERT_EQUAL(string("not compatible with the server protocol version"),errormsg);
266 void SeparatorMissing()
268 switch(child_pid=fork())
272 CPPUNIT_FAIL("fork error");
280 socket_server ss("./socket");
283 hello << "T2Nv" << PROTOCOL_VERSION;
284 int byteordercheck=1;
285 hello.write((char*)&byteordercheck,sizeof(byteordercheck));
288 ss.add_callback(new_connection,bind(&test_hello::send_hello, boost::ref(*this), hello.str(),&ss, _1));
291 for (int i=0; i < 10; i++)
292 ss.fill_buffer(1000000);
295 std::cerr << "exception in child. ignoring\n";
298 // don't call atexit and stuff
307 // wait till server is up
309 socket_client_connection sc("./socket");
311 command_client cc(&sc);
313 t2n_exception* ep=cc.get_constuctor_exception();
319 CPPUNIT_ASSERT_EQUAL(string("illegal hello received (1. ;)"),errormsg);
324 void WrongByteOrder()
326 switch(child_pid=fork())
330 CPPUNIT_FAIL("fork error");
338 socket_server ss("./socket");
341 hello << "T2Nv" << PROTOCOL_VERSION << ';';
342 int byteordercheck=1;
344 char* si=(char*)&byteordercheck;
345 char* di=(char*)&dst;
352 hello.write((char*)&dst,sizeof(dst));
355 ss.add_callback(new_connection,bind(&test_hello::send_hello, boost::ref(*this), hello.str(),&ss, _1));
358 for (int i=0; i < 10; i++)
359 ss.fill_buffer(1000000);
362 std::cerr << "exception in child. ignoring\n";
365 // don't call atexit and stuff
374 // wait till server is up
376 socket_client_connection sc("./socket");
378 command_client cc(&sc);
380 t2n_exception* ep=cc.get_constuctor_exception();
386 CPPUNIT_ASSERT_EQUAL(string("host byte order not matching"),errormsg);
391 void OtherServerBig()
393 switch(child_pid=fork())
397 CPPUNIT_FAIL("fork error");
405 socket_server ss("./socket");
408 // hmm, we got the wrong socket
409 hello << "* OK intradev.net.lan Cyrus IMAP4 v2.2.13 server ready";
411 ss.add_callback(new_connection,bind(&test_hello::send_raw_socket, boost::ref(*this), hello.str(),&ss, _1));
414 for (int i=0; i < 3; i++)
415 ss.fill_buffer(1000000);
418 std::cerr << "exception in child. ignoring\n";
421 // don't call atexit and stuff
430 // wait till server is up
432 socket_client_connection sc("./socket");
434 command_client cc(&sc);
436 t2n_exception* ep=cc.get_constuctor_exception();
442 CPPUNIT_ASSERT_EQUAL(string("illegal hello received (T2N)"),errormsg);
447 void OtherServerSmall()
449 switch(child_pid=fork())
453 CPPUNIT_FAIL("fork error");
461 socket_server ss("./socket");
464 // hmm, we got the wrong socket
467 ss.add_callback(new_connection,bind(&test_hello::send_raw_socket, boost::ref(*this), hello.str(),&ss, _1));
470 for (int i=0; i < 3; i++)
471 ss.fill_buffer(1000000);
474 std::cerr << "exception in child. ignoring\n";
477 // don't call atexit and stuff
486 // wait till server is up
488 socket_client_connection sc("./socket");
490 command_client cc(&sc);
492 t2n_exception* ep=cc.get_constuctor_exception();
498 CPPUNIT_ASSERT_EQUAL(string("illegal hello received (T2N)"),errormsg);
505 CPPUNIT_TEST_SUITE_REGISTRATION(test_hello);