Skip to content
Snippets Groups Projects
Commit f2a7f283 authored by Sergi Hernandez's avatar Sergi Hernandez
Browse files

Added a new class for UDP sockets.

Added a send and receive examples for the UDP sockets.
parent 8b56cc41
No related branches found
No related tags found
No related merge requests found
......@@ -33,9 +33,9 @@ ELSE(FTDI_INCLUDE_DIR AND FTDI_LIBRARY)
ENDIF(FTDI_INCLUDE_DIR AND FTDI_LIBRARY)
# edit the following line to add all the source code files of the library
SET(sources ./comm.cpp ./cqueue.cpp ./commexceptions.cpp ./serial/rs232.cpp ./serial/rs232exceptions.cpp ./sockets/socket.cpp ./sockets/socketclient.cpp ./sockets/socketserver.cpp ./sockets/socketexceptions.cpp ./can/can.cpp)
SET(sources ./comm.cpp ./cqueue.cpp ./commexceptions.cpp ./serial/rs232.cpp ./serial/rs232exceptions.cpp ./sockets/socket.cpp ./sockets/socketclient.cpp ./sockets/socketserver.cpp ./sockets/socketudp.cpp ./sockets/socketexceptions.cpp ./can/can.cpp)
# edit the following line to add all the header files of the library
SET(headers ./comm.h ./cqueue.h ./commexceptions.h ./serial/rs232.h ./serial/rs232exceptions.h ./sockets/socket.h ./sockets/socketclient.h ./sockets/socketserver.h ./sockets/socketexceptions.h ./can/can.h)
SET(headers ./comm.h ./cqueue.h ./commexceptions.h ./serial/rs232.h ./serial/rs232exceptions.h ./sockets/socket.h ./sockets/socketclient.h ./sockets/socketserver.h ./sockets/socketudp.h ./sockets/socketexceptions.h ./can/can.h)
IF(BUILD_FTDI)
SET(sources ${sources} ./usb_ftdi/ftdiserver.cpp ./usb_ftdi/ftdimodule.cpp ./usb_ftdi/ftdiexceptions.cpp)
......
......@@ -45,3 +45,15 @@ ADD_EXECUTABLE(test_multiple_client test_multiple_client.cpp)
# edit the following line to add the necessary libraries
TARGET_LINK_LIBRARIES(test_multiple_client ${IRIUTILS_LIBRARY} comm pthread)
# edit the following line to add the source code for the example and the name of the executable
ADD_EXECUTABLE(test_udp_rx test_simple_client_udp_rx.cpp)
# edit the following line to add the necessary libraries
TARGET_LINK_LIBRARIES(test_udp_rx ${IRIUTILS_LIBRARY} comm pthread)
# edit the following line to add the source code for the example and the name of the executable
ADD_EXECUTABLE(test_udp_tx test_simple_client_udp_tx.cpp)
# edit the following line to add the necessary libraries
TARGET_LINK_LIBRARIES(test_udp_tx ${IRIUTILS_LIBRARY} comm pthread)
#include "socketclient.h"
#include "socketexceptions.h"
std::string server_ip="192.168.0.13";
std::string server_ip="192.168.100.97";
int server_port=6653;
int main(int argc,char *argv[])
......
#include "socketudp.h"
#include "socketexceptions.h"
std::string server_ip="192.168.100.97";
int server_port=6653;
int main(int argc,char *argv[])
{
TSocket_info info;
CSocketUDP client("client");
unsigned char answer[5];
try{
info.address=server_ip;
info.port=server_port;
client.open(&info);
client.config(NULL);
std::cout << "connected." << std::endl;
while(1)
{
std::cout << "receiving data ..." << std::endl;
client.read(answer,5);
std::cout << "data received: " << answer << std::endl;
sleep(1);
}
std::cout << "closing connection ..." << std::endl;
client.close();
sleep(1);
}catch(CException &e){
std::cout << e.what() << std::endl;
}
}
#include "socketudp.h"
#include "socketexceptions.h"
std::string server_ip="192.168.100.97";
int server_port=6653;
int main(int argc,char *argv[])
{
TSocket_info info;
CSocketUDP client("client");
unsigned char msg[5]="hola";
try{
client.open();
client.config();
std::cout << "connected." << std::endl;
while(1)
{
std::cout << "sending data ..." << std::endl;
client.write_to(server_ip,server_port,msg,5);
sleep(1);
}
std::cout << "closing connection ..." << std::endl;
client.close();
sleep(1);
}catch(CException &e){
std::cout << e.what() << std::endl;
}
}
......@@ -2,8 +2,8 @@
#include "socketserver.h"
#include "eventserver.h"
std::string server_IP_address="127.0.0.1";
int server_port=2012;
std::string server_IP_address="192.168.100.97";
int server_port=6653;
int num_listen=1;
int main(int argc,char *argv[])
......
#include "socket.h"
#include "socketexceptions.h"
#include <string.h>
#include "errno.h"
CSocket::CSocket(const std::string &comm_id) : CComm(comm_id)
CSocket::CSocket(const std::string &comm_id,socket_type_t type) : CComm(comm_id)
{
this->connection_closed_event.clear();
this->connection_closed_event+=comm_id;
this->connection_closed_event+="_closed";
this->event_server->create_event(this->connection_closed_event);
this->cloned=false;
this->type=type;
}
CSocket::CSocket(const std::string &comm_id,const int fd) : CComm(comm_id)
......@@ -49,19 +51,27 @@ void CSocket::hard_open(void *comm_dev)
if(!this->cloned)
{
if((this->socket_fd=socket(AF_INET,SOCK_STREAM,0))<0)
if(this->type==socket_tcp)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Error opening socket", this->comm_id);
if((this->socket_fd=socket(AF_INET,SOCK_STREAM,0))<0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Error opening socket", this->comm_id);
}
}
else
{
if(setsockopt(this->socket_fd,SOL_SOCKET,SO_REUSEADDR,&yes,sizeof(int))<0)
if((this->socket_fd=socket(AF_INET,SOCK_DGRAM,0))<0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Impossible to change socket options",this->comm_id);
throw CSocketException(_HERE_,"Error opening socket", this->comm_id);
}
}
if(setsockopt(this->socket_fd,SOL_SOCKET,SO_REUSEADDR,&yes,sizeof(int))<0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Impossible to change socket options",this->comm_id);
}
}
}
......@@ -94,6 +104,7 @@ int CSocket::hard_write(unsigned char *data, int len)
{
if((num_write=::write(this->socket_fd,data,len))==-1)
{
std::cout << errno << std::endl;
/* handle exceptions */
throw CSocketException(_HERE_,"Error while writing to the socket.",this->comm_id);
}
......@@ -129,6 +140,7 @@ int CSocket::hard_wait_comm_event(void)
FD_ZERO(&error_set);
FD_SET(this->socket_fd,&error_set);
wait_result=select(max_fd,&receive_set,NULL,&error_set,NULL);
std::cout << "new data" << std::endl;
if(wait_result==-1)
{
/* handle exceptions */
......@@ -165,6 +177,11 @@ void CSocket::hard_close(void)
this->cloned=false;
}
socket_type_t CSocket::get_socket_type(void)
{
return this->type;
}
CSocket::~CSocket()
{
this->close();
......
......@@ -40,6 +40,8 @@ typedef struct {
int port;
}TSocket_info;
typedef enum {socket_tcp=0,socket_udp=1} socket_type_t;
/**
* \brief Socket driver
*
......@@ -86,6 +88,11 @@ class CSocket : public CComm
* not be accessed from the outside.
*/
bool cloned;
/**
* \brief
*
*/
socket_type_t type;
protected:
/**
* \brief socket file descriptor.
......@@ -293,7 +300,7 @@ class CSocket : public CComm
* unique identifier for all the threads and events of the
* class.
*/
CSocket(const std::string &comm_id);
CSocket(const std::string &comm_id,socket_type_t type=socket_tcp);
/**
* \brief Function to get the name of Connection Closed Event
*
......@@ -310,6 +317,11 @@ class CSocket : public CComm
* functions of the CEventServer class to wait its activation.
*/
std::string get_connection_closed_event(void);
/**
* \brief
*
*/
socket_type_t get_socket_type(void);
/**
* \brief Destructor
*
......
......@@ -2,7 +2,7 @@
#include "socketexceptions.h"
#include <string.h>
CSocketClient::CSocketClient(const std::string &sock_id) : CSocket(sock_id)
CSocketClient::CSocketClient(const std::string &sock_id) : CSocket(sock_id,socket_tcp)
{
this->connected=false;
this->remote.address.clear();
......
#include "socketudp.h"
#include "socketexceptions.h"
CSocketUDP::CSocketUDP(const std::string &sock_id) : CSocket(sock_id,socket_udp)
{
this->receive.port=-1;
this->receive.address.clear();
}
void CSocketUDP::hard_open(void *comm_dev)
{
TSocket_info *remote=(TSocket_info *)comm_dev;
sockaddr_in sock;
CSocket::hard_open(NULL);
if(remote!=NULL)
{
memset(&sock,0,sizeof(sock));
sock.sin_family=AF_INET;
if(inet_aton(remote->address.c_str(),&sock.sin_addr)==0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Impossible to convert IP address",this->comm_id);
}
else
{
sock.sin_port=htons(remote->port);
// bind to the desired IP and port to receive data from
if((::bind(this->socket_fd,(struct sockaddr *)&sock,sizeof(sock)))<0)
{
/* handle exceptions */
throw CSocketException(_HERE_, "Error with connect function", this->comm_id);
}
else
{
this->receive.port=remote->port;
this->receive.address=remote->address;
}
}
}
}
void CSocketUDP::hard_close(void)
{
CSocket::hard_close();
this->receive.port=-1;
this->receive.address.clear();
}
int CSocketUDP::write_to(std::string &ip,int port,unsigned char *data,int len)
{
sockaddr_in sock;
int written=0;
memset(&sock,0,sizeof(sock));
sock.sin_family=AF_INET;
if(inet_aton(ip.c_str(),&sock.sin_addr)==0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Impossible to convert IP address",this->comm_id);
}
else
{
sock.sin_port=htons(port);
if((written=sendto(this->socket_fd,data,len,0,(struct sockaddr *)&sock,sizeof(sock)))<0)
{
/* handle exceptions */
throw CSocketException(_HERE_,"Impossible to send data to the desired IP and port",this->comm_id);
}
return written;
}
}
CSocketUDP::~CSocketUDP()
{
}
#ifndef _SOCKETUDP_H_
#define _SOCKETUDP_H_
#include "socket.h"
class CSocketUDP : public CSocket
{
private:
TSocket_info receive;
protected:
/**
* \brief Connect function
*
* This function is called when the base class open() function is called, and
* it is used to perform the connection to a server. This function requires a
* TSocket_info structure as parameter which must be provided to the open()
* call. It also calls the hard_open() function of the CSocket class to
* initialize the base class attributes.
*
* The IP address and port within this structure are used to try to stablish
* a communication with a remote server. If the server is already listening,
* the function returns normally with all the internal attributes properly
* initialized.
*
* If the server is not yet listening, this function throws a CSocketNoConnection
* exception. This exception can be catched and used to iterate the process
* until the server is available or terminate the applcation. In case of any
* other error, this function throws a CSocketException.
*
* After the connection is set, it is still necessary to call the config()
* function to properly configure the object to send and receive information.
*
* \param comm_dev a valid pointer to a TSocket_info structure with the IP
* address and listening port of the desired server. See the
* documentation on the TSocket_info structure for more
* information on the IP address and port format.
*/
virtual void hard_open(void *comm_dev=NULL);
/**
* \brief function to close the client socket
*
* This function is called when the close() function of the base class is
* called. It calls the hard_close() function of the CSocket class to
* actually terminate the connection and change all the internal attributes
* to reflect that (the connection flag is set back to false and the server
* IP address and port are set to the default values.
*
* In case of any error, this function throws a CSocketException.
*/
virtual void hard_close(void);
public:
CSocketUDP(const std::string &sock_id);
int write_to(std::string &ip,int port,unsigned char *data,int len);
~CSocketUDP();
};
#endif
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment