0

I have a little problem in my code for a server that when the client closes connection restart it again and remain in listening for another client, without kill/restart the entire program. When I try to send a packet after the restart, I get an error message 'Broken Pipe'. If I kill the entire program and restart it immediately, all works fine. Why? I only close the socket; there is others command to give to close appropriately a connection? Follows my code:

Restart connection part:

if(command[14]==END_TRANS)
{
  command[14] = 0x00;

  // Close serial and TCP communications and Opencv processes
  close_capture = 1;
  serial->~UARTcom();
  tcp_server->~TCPServer();
  std::cout<<""<<std::endl;
  std::cout<<"Restarting connections..."<<std::endl;
  sleep(2);

  // Re-Start serial and TCP communications
  UARTcom *serial = new UARTcom(serial_device);
  TCPServer *tcp_server = new TCPServer(tcp_port);
  memset(size_imudata_buff, 0, sizeof(int)+DATA_SIZE);
  memset(ack_imucomm_buff, 0, sizeof(int)+COMMAND_SIZE);
  if(pthread_create(&th_capture, NULL, capture, NULL))
    {
      perror("main() Create th_stream failed");
      exit(1);
    }
  continue;
}

TCPServer class:

/**********************************************************************
 *CONSTRUCTOR: Create a new socket, establishing a default destination
 *to the port.
 *********************************************************************/
TCPServer::TCPServer(int serv_port)
{  
  // Adress initialization
  memset((char *)&servaddr, 0, sizeof(servaddr));
  servaddr.sin_family = PF_INET;
  servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
  servaddr.sin_port = htons(serv_port);

  // Create socket
  if((serverSock = socket(PF_INET, SOCK_STREAM, 0)) == INVALID_SOCKET)
    {
      std::perror("TCPServer() Create socket failed");
      exit(1);
    }
  std::cout<<"TCPServer() Created socket sd="<<serverSock<<std::endl;

  int optval = 1;
  if(setsockopt(serverSock, SOL_SOCKET, SO_REUSEADDR, &optval, sizeof(optval)) < 0)
    {
      std::perror("TCPServer() Set option failed");
      exit(1);
    }

  // Bind socket
  if(bind(serverSock,(struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
    {
      std::perror("TCPServer() Bind failed"); 
      exit(1);
    }
  std::cout<<"TCPServer() Bind socket"<<std::endl;

  // Listen for incoming connection
  if(listen(serverSock,5) < 0)
    {
      std::perror("TCPServer() Listen failed"); 
      exit(1);
    }
  std::cout<<"TCPServer() --> Waiting for TCP connection on port "<<serv_port<<std::endl;

  // Accept connection and receive client address
  if((connectSock = accept(serverSock,(sockaddr*)&clientaddr,&clientaddrlen))<0)
    {
      std::perror("TCPServer() Accept failed"); 
      exit(1);
    }
  std::cout<<"TCPServer() --> TCP connection estabilished with "<<inet_ntoa(clientaddr.sin_addr)<<std::endl;
}


/**********************************************************************
 *DESTRUCTOR: Close the socket
 *********************************************************************/
TCPServer::~TCPServer(void)
{
  if(close(serverSock) < 0)
    {
      std::perror("TCPServer() Close socket failed");
      exit(1);
    }
  std::cout<<"TCPServer() Socket closed"<<std::endl;
}


/**********************************************************************
 *TCPServer::receiveData() receive data from socket defined
 *through connect() function 
 *********************************************************************/
int TCPServer::receiveData(char* data, int len)
{ 
  return recv(connectSock, data, len, 0);
} 


/**********************************************************************
 *TCPServer::sendData() send data to socket defined through
 *connect() function 
 *********************************************************************/
int TCPServer::sendData(char* data, int len)
{
  return send(connectSock, data, len, 0);
}

The output that I get when I run program and then disconnect-reconnect the client:

UARTcom() Serial port open on /dev/ttyUSB0
TCPServer() Created socket sd=13
TCPServer() Bind socket
TCPServer() --> Waiting for TCP connection on port 8080
TCPServer() --> TCP connection estabilished with 192.168.1.56
UARTcom() Serial connection closed
TCPServer() Socket closed

Restarting connections...
UARTcom() Serial port open on /dev/ttyUSB0
TCPServer() Created socket sd=13
TCPServer() Bind socket
TCPServer() --> Waiting for TCP connection on port 8080
TCPServer() --> TCP connection estabilished with 192.168.1.56
main() Failed to send size of frame and IMU data: Broken pipe
main() Failed to send size of frame and IMU data: Broken pipe
main() Failed to send size of frame and IMU data: Broken pipe
main() Failed to send size of frame and IMU data: Broken pipe

Anyone can explain me why?

  • 1
    Why are you calling your destructors directly? – Galik Dec 12 '14 at 20:44
  • `serial->~UARTcom();` that's not the way to delete the object (if that's what you are trying to do). You should use: `delete serial;`. Maybe get a book and learn from the ground up: http://stackoverflow.com/questions/388242/the-definitive-c-book-guide-and-list – Galik Dec 12 '14 at 20:48
  • This has solved my problem. I'm newbie with C++ (I'm a C migrant) and I didn't know that for cancel an instance needs to call 'delete' routine. Thanks very much. – Andrea Verdecchia Dec 12 '14 at 21:25
  • @Galik turned your answer into a community wiki answer. If you want to post it under your account I'll delete my answer and also give you some internet points. – dsolimano Apr 28 '15 at 21:00

1 Answers1

1

What you are doing here::

serial->~UARTcom();

That's not the way to delete the object (if that's what you are trying to do). You should use:

delete serial;

Maybe get a book and learn from the ground up – ?

Community
  • 1
  • 1
Galik
  • 47,303
  • 4
  • 80
  • 117