276 lines
5.4 KiB
C++
276 lines
5.4 KiB
C++
|
|
/*!
|
|
* \ file XSock.cpp bal bla
|
|
*
|
|
*/
|
|
|
|
#include "xsock.h"
|
|
|
|
/*!
|
|
* \def VERBOSE Active ou pas le mode verbeux
|
|
*/
|
|
#define VERBOSE 0
|
|
|
|
// constantes utilisées dans XSock.cpp et dans XSockUDP.cpp
|
|
#define NBPORTSPUB 64512
|
|
#define PNUMPORTPUB 1025
|
|
#define GETPORTPUB() PNUMPORTPUB+(rand()%NBPORTSPUB)
|
|
|
|
using namespace std;
|
|
using namespace XSockExcept;
|
|
|
|
namespace XSock {
|
|
|
|
XSock::XSock (xsock_role role,protocol proto){
|
|
/* initialise la structure d'addresse */
|
|
/* on commence par vider la structure pour éviter les déchets... */
|
|
memset(&this->_server, 0, sizeof(this->_server));
|
|
memset(&this->_client, 0, sizeof(this->_client));
|
|
this->_client.sin_family=AF_INET;
|
|
this->_server.sin_family=AF_INET;
|
|
|
|
/* on initialise le systèmes de nombres aléatoires */
|
|
srand(time(NULL));
|
|
/* on initialise avec des addresses locales au cas où... */
|
|
this->_client.sin_addr.s_addr=htonl(INADDR_LOOPBACK);
|
|
this->_server.sin_addr.s_addr=htonl(INADDR_LOOPBACK);
|
|
|
|
/* et les ports au hasard */
|
|
this->_client.sin_port=htons(0);
|
|
this->_server.sin_port=htons(0);
|
|
|
|
/* calcule la taille de la table des descripteurs */
|
|
this->_sockSetDSize = getdtablesize();
|
|
|
|
this->_role=role;
|
|
this->_proto=proto;
|
|
|
|
this->_client_length = sizeof(this->_client);
|
|
this->_server_length = sizeof(this->_server);
|
|
|
|
|
|
}
|
|
|
|
/*!
|
|
* Indique le port à utiliser sur le serveur.
|
|
*/
|
|
void XSock::port(u_short port){
|
|
switch(this->_role){
|
|
case CLIENT:
|
|
this->_server.sin_port=htons(port);
|
|
break;
|
|
case SERVER:
|
|
this->_server.sin_port=htons(port);
|
|
break;
|
|
default:
|
|
throw eUnknownXSockRole();
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
/*!
|
|
* Fixe la taille de la queue d'attente de connexion
|
|
*/
|
|
|
|
void XSock::backlog(int size){
|
|
this->_backlog=size;
|
|
}
|
|
|
|
|
|
/*!
|
|
* Indique l'addresse IP du serveur.
|
|
*/
|
|
|
|
void XSock::ip(int ip){
|
|
switch (this->_role){
|
|
case CLIENT:
|
|
this->_server.sin_addr.s_addr=htonl(ip);
|
|
break;
|
|
case SERVER:
|
|
this->_server.sin_addr.s_addr=htonl(ip);
|
|
break;
|
|
default:
|
|
throw eUnknownXSockRole();
|
|
break;
|
|
}
|
|
}
|
|
|
|
void XSock::dns(string dns){
|
|
struct hostent *he;
|
|
if ((he = gethostbyname(dns.c_str())) == NULL) {
|
|
throw eUnableToResolveName();
|
|
}
|
|
|
|
memcpy(&(this->_server.sin_addr.s_addr), he->h_addr_list[0], he->h_length);
|
|
|
|
switch (this->_role){
|
|
case CLIENT:
|
|
break;
|
|
case SERVER:
|
|
break;
|
|
default:
|
|
throw eUnknownXSockRole();
|
|
break;
|
|
}
|
|
|
|
}
|
|
/*!
|
|
* Connecte XSock au réseau.
|
|
*/
|
|
|
|
void XSock::dump_info(){
|
|
if (VERBOSE>=1){
|
|
printf("XSock server : %d\n",this->_server.sin_addr.s_addr);
|
|
printf("XSock client : %d\n",this->_client.sin_addr.s_addr);
|
|
printf("XSock server port : %d\n",this->_server.sin_port);
|
|
printf("XSock client port : %d\n",this->_client.sin_port);
|
|
}
|
|
}
|
|
|
|
char * XSock::getClientAddress(){
|
|
return inet_ntoa(this->_client.sin_addr);
|
|
}
|
|
|
|
char * XSock::getServerAddress(){
|
|
return inet_ntoa(this->_server.sin_addr);
|
|
}
|
|
|
|
|
|
void XSock::launch(){
|
|
this->dump_info();
|
|
switch (this->_role){
|
|
case CLIENT:
|
|
switch (this->_proto){
|
|
case TCP:
|
|
this->launch_tcp_client();
|
|
break;
|
|
case UDP:
|
|
this->launch_udp_client();
|
|
break;
|
|
case UDP_RELIABLE:
|
|
this->launch_udp_reliable_client();
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
}
|
|
break;
|
|
case SERVER:
|
|
switch (this->_proto){
|
|
case TCP:
|
|
this->launch_tcp_server();
|
|
break;
|
|
case UDP:
|
|
this->launch_udp_server();
|
|
break;
|
|
case UDP_RELIABLE:
|
|
this->launch_udp_reliable_server();
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
}
|
|
break;
|
|
default:
|
|
throw eUnknownXSockRole();
|
|
break;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* Demande a XSock de recevoir des informations.
|
|
* \param bufferData buffer de données.
|
|
* \param size taille du buffer.
|
|
*/
|
|
|
|
ssize_t XSock::recv(void *bufferData, ssize_t size){
|
|
switch(this->_proto){
|
|
case TCP:
|
|
return this->recv_tcp(bufferData, size);
|
|
break;
|
|
case UDP:
|
|
return this->recv_udp(bufferData, size);
|
|
break;
|
|
case UDP_RELIABLE:
|
|
return this->recv_udp_reliable(bufferData, size);
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
}
|
|
}
|
|
|
|
ssize_t XSock::send(const void *bufferData, ssize_t size){
|
|
switch(this->_proto){
|
|
case TCP:
|
|
return this->send_tcp(bufferData, size);
|
|
break;
|
|
case UDP:
|
|
return this->send_udp(bufferData, size);
|
|
break;
|
|
case UDP_RELIABLE:
|
|
return this->send_udp_reliable(bufferData, size);
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
XSock XSock::accept(){
|
|
XSock result(CLIENT,this->_proto);
|
|
switch (this->_role){
|
|
case CLIENT:
|
|
// TODO: râler, car le client ne recoit pas de
|
|
// connexions...
|
|
break;
|
|
case SERVER:
|
|
switch (this->_proto){
|
|
case TCP:
|
|
result=this->accept_tcp();
|
|
break;
|
|
case UDP:
|
|
result=this->accept_udp();
|
|
break;
|
|
case UDP_RELIABLE:
|
|
result=this->accept_udp_reliable();
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
}
|
|
break;
|
|
default:
|
|
throw eUnknownXSockRole();
|
|
break;
|
|
}
|
|
return result;
|
|
}
|
|
|
|
void XSock::close(){
|
|
switch (this->_proto){
|
|
case TCP:
|
|
this->close_tcp();
|
|
break;
|
|
case UDP:
|
|
this->close_udp();
|
|
break;
|
|
case UDP_RELIABLE:
|
|
this->close_udp_reliable();
|
|
break;
|
|
default:
|
|
throw eUnknownProtocol();
|
|
break;
|
|
|
|
}
|
|
//TODO: a faire...
|
|
}
|
|
} // end namespace
|
|
|
|
|
|
|
|
|
|
|
|
|