socket_server::socket_server(int port, const std::string& ip)
: server(), socket_handler(0,tcp_s)
{
- // TODO
+ /* Create the socket. */
+ sock = socket (PF_INET, SOCK_STREAM, 0);
+ if (sock < 0)
+ {
+ string err="error opening socket: ";
+ err+=strerror(errno);
+ log(error, err);
+ throw t2n_server_error(err);
+ }
+
+ set_socket_options(sock);
+
+ /* Give the socket a name. */
+ struct sockaddr_in sockaddr;
+ sockaddr.sin_family = AF_INET;
+ sockaddr.sin_port = htons(port);
+
+ if (inet_aton(ip.c_str(),&sockaddr.sin_addr) == 0)
+ {
+ string err="failed listening on invalid ip ";
+ err+=ip;
+ log(error, err);
+ throw t2n_server_error(err);
+ }
+
+ if (bind (sock, (struct sockaddr *) &sockaddr, sizeof (sockaddr)) < 0)
+ {
+ string err="error binding socket: ";
+ err+=strerror(errno);
+ log(error, err);
+ throw t2n_server_error(err);
+ }
+
+ start_listening();
}
/** @brief create a new unix-socked-based server
}
}
+ start_listening();
+}
+
+socket_server::~socket_server()
+{
+ socket_handler::close();
+
+ if (get_type()==unix_s)
+ unlink(unix_path.c_str());
+}
+
+/// start listening on a new server socket (called by the constructors)
+void socket_server::start_listening()
+{
if (listen (sock, 5) < 0)
{
string err="error listening to socket: ";
FD_SET (sock, &connection_set);
}
-socket_server::~socket_server()
-{
- socket_handler::close();
-
- if (get_type()==unix_s)
- unlink(unix_path.c_str());
-}
-
+/// handle a new connection from a client
void socket_server::new_connection()
{
struct sockaddr_un clientname;
return false;
}
+/// call fill_buffer() on all connections, called from fill_buffer()
bool socket_server::fill_connection_buffers()
{
bool data_found;
return data_found;
}
+/// remove the socket of a connection after the connection has been closed
void socket_server::remove_connection_socket(int sock)
{
FD_CLR(sock, &connection_set);
}
}
+/// close this connection. complete data waiting in the buffer can still be retrieved.
void socket_server_connection::close()
{
if (!server_connection::is_closed())
CPPUNIT_TEST(UnixCommToServer);
CPPUNIT_TEST(UnixCommToServerAndBack);
+ CPPUNIT_TEST(IPCommToServer);
CPPUNIT_TEST_SUITE_END();
}
}
+ void IPCommToServer()
+ {
+ pid_t pid;
+ string data;
+
+ switch(pid=fork())
+ {
+ case -1:
+ {
+ CPPUNIT_FAIL("fork error");
+ break;
+ }
+ case 0:
+ // child
+ {
+ // wait till server is up
+ sleep(1);
+ socket_client_connection sc("localhost",6666,socket_client_connection::max_retries_default);
+ sc.write("hello");
+ // don't call atexit and stuff
+ _exit(0);
+ }
+
+ default:
+ // parent
+ {
+ socket_server ss(6666);
+
+ // max 10 sec
+ for (int i=0; i < 10; i++)
+ {
+ ss.fill_buffer(1000000);
+
+ if(ss.get_packet(data))
+ break;
+ }
+ }
+ }
+ CPPUNIT_ASSERT_EQUAL(string("hello"),data);
+ }
+
};
CPPUNIT_TEST_SUITE_REGISTRATION(test_comm);