C++ TCP Socket Client Fails to Send Data - c++

I am writing a simple socket client in c++. Here is the code:
main.h:
#ifndef CC_Client_main_h
#define CC_Client_main_h
void error(std::string msg);
#endif
main.cpp
#include <iostream>
#include "communications.h"
#include "main.h"
void error(std::string msg) {
std::cerr << msg;
exit(-1);
}
int main(int argc, char **argv) {
Communication communication = Communication("localhost", 8888);
communication.print_hosts();
int success = communication.send_str("hello!\n");
if (success<0) {
std::cerr << "Error writing data.\n";
}
return 0;
}
communications.h
#ifndef __CC_Client__communications__
#define __CC_Client__communications__
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <sys/types.h>
#include <time.h>
#include <netdb.h>
#include <string>
#include <iostream>
#include main.h
class Communication {
private:
int sock;
struct hostent *host;
struct sockaddr_in server_address;
char *host_str;
int port;
public:
Communication(char *host, int port);
~Communication(void);
hostent &get_host();
void print_hosts(void);
int send_str(char *send_string);
};
#endif /* defined(__CC_Client__communications__) */
communications.cpp
#include "communications.h"
#include "main.h"
void print_addr(unsigned char *address) {
printf("%d.%d.%d.%d\n", address[0], address[1], address[2], address[3]);
}
Communication::Communication(char *host, int port) {
this->port = port;
this->host_str = host;
this->sock = socket(AF_INET, SOCK_STREAM, 0);
if (this->sock<0) {
error("Failed to build socker object.\n");
}
this->host = gethostbyname(host);
if (!this->host) {
error("Failed to resolve host.\n");
}
memset((char*)&this->server_address, 0, sizeof(this->server_address));
server_address.sin_family = AF_INET;
server_address.sin_port = htons(port);
memcpy((void *)&this->server_address.sin_addr, this->host->h_addr_list[0], this->host->h_length);
if (connect(this->sock, (struct sockaddr*)&server_address, sizeof(this->server_address))<0) {
error("Failed to connect socket.\n");
}
}
Communication::~Communication() {
std::cout << "Closing connection. . .\n";
shutdown(this->sock, SHUT_RDWR);
std::cout << "Communication object at " << this << " being destroyed\n";
}
void Communication::print_hosts() {
for (int i=0; this->host->h_addr_list[i]!=0; i++) {
print_addr((unsigned char*) this->host->h_addr_list[i]);
}
}
int Communication::send_str(char *send_string) {
char buffer[strlen(send_string)];
int num_bytes = write(this->sock, buffer, sizeof(buffer));
return num_bytes;
}
I tried to use netcat to test the client like this:
$ nc -lv 8888
But the data it receives seems is incorrect:
$ nc -lv 8888
??_?
My program does not give me any errors when I run it. Where is this data coming from?
I am running Mac OS X Mavericks.

you didnt put any data into buffer in send_str
also i suspect that sizeof(buffer) doesn't do what you expect. My guess is that it will be sizeof(char*)

Related

Data losses while converting a struct to a byte array and sending it over UDP in C++

I have a client who wants to send a message to the server over UDP.
I have a message struct:
struct Msg1
{
uint8_t tag = 1;
uint32_t nonce = 0;
uint16_t length = 0;
char *name;
};
I convert it to an uint32_t array, send it over UDP and reconvert it. But the output is:
1 Byte: TAG:
4 Byte: NONCE: 1111111
2 Byte: LENGTH: 5
8 Byte: NAME:
Now I am confused, because two variables are right and two are not. Maybe someone has an idea?
// EDIT example files
/* Client.cpp */
#include "Client.h"
#include <gmp.h>
Client::Client(){}
void Client::start()
{
this->prepareMsg1();
this->sendMsg1();
}
void Client::prepareMsg1()
{
// generate random Na and copy
MyRandom *r = new MyRandom();
myMsg1->nonce = r->getNewRandom();
this->na = myMsg1->nonce;
// copy name and length
myMsg1->name = new char[nameMsg1.size()];
strcpy(myMsg1->name, nameMsg1.c_str());
myMsg1->length = nameMsg1.size();
}
void Client::sendMsg1()
{
// set the size of data
udp->data = new uint8_t[sizeof(myMsg1) - 1 + myMsg1->length];
int pos = 0;
memcpy(udp->data, &myMsg1->tag, sizeof(myMsg1->tag));
memcpy(udp->data + (pos += sizeof(myMsg1->tag)), &myMsg1->nonce, sizeof(myMsg1->nonce));
memcpy(udp->data + (pos += sizeof(myMsg1->nonce)), &myMsg1->length, sizeof(myMsg1->length));
memcpy(udp->data + (pos += sizeof(myMsg1->length)), myMsg1->name, myMsg1->length);
udp->write(client);
}
/* Client.h */
#ifndef CLIENT_H_
#define CLIENT_H_
#include <cstdint> // int32_t
#include <gmp.h>
#include <iostream> // cout, endl
#include <string> // string
#include <stdlib.h>
#include "Random.h"
#include "messages.h"
#include "UDP.h"
using std::cout;
using std::endl;
using std::string;
class Client
{
public:
Client();
void start();
void prepareMsg1();
void sendMsg1();
string nameMsg1 = "Alice";
Msg1 *myMsg1 = new Msg1();
UDP *udp = new UDP();
};
#endif /* CLIENT_H_ */
/* UDP.cpp */
#include "UDP.h"
void die(char *s)
{
perror(s);
exit(1);
}
UDP::UDP(){}
void UDP::listen()
{
data = new uint8_t[BUFLEN];
struct sockaddr_in si_me, si_other;
int s = sizeof(si_other), recv_len;
socklen_t slen = sizeof(si_other);
// create UDP socket
if ((s = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) == -1)
die("socket");
// zero out the structure
memset((char *) &si_me, 0, sizeof(si_me));
si_me.sin_family = AF_INET;
si_me.sin_port = htons(PORT);
si_me.sin_addr.s_addr = htonl(INADDR_ANY);
// bind socket to port
if (bind(s, (struct sockaddr*) &si_me, sizeof(si_me)) == -1)
die("bind");
fflush(stdout);
if ((recv_len = recvfrom(s, data, BUFLEN, 0, (struct sockaddr *) &si_other, &slen)) == -1)
die("recvfrom()");
close(s);
}
void UDP::write(Device d)
{
struct sockaddr_in si_other;
int s = sizeof(si_other);
socklen_t slen = sizeof(si_other);
memset((char *) &si_other, 0, sizeof(si_other));
if ((s = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) == -1)
die("socket");
si_other.sin_family = AF_INET;
si_other.sin_port = htons(PORT);
if(d == client)
{
if (inet_aton(SERVER, &si_other.sin_addr) == 0)
{
fprintf(stderr, "inet_aton() failed\n");
exit(1);
}
}
else if(d == server)
{
if (inet_aton(CLIENT, &si_other.sin_addr) == 0)
{
fprintf(stderr, "inet_aton() failed\n");
exit(1);
}
}
if (sendto(s, data, sizeof(data), 0, (struct sockaddr *) &si_other, slen) == -1)
die("sendto()");
close(s);
}
/* UDP.h */
#ifndef UDP_H_
#define UDP_H_
#include <iostream> // cout, endl
#include <stdio.h> // printf
#include <string.h> // memset
#include <stdlib.h> // exit(0);
#include <unistd.h> // close
#include <arpa/inet.h>
#include <sys/socket.h>
#include "messages.h"
#define BUFLEN 512
#define PORT 8888
#define CLIENT "192.168.2.106"
#define SERVER "192.168.2.104"
using std::cout;
using std::endl;
class UDP
{
public:
UDP();
void listen();
void write(Device);
bool output = true;
uint8_t *data = new uint8_t[BUFLEN];
};
#endif /* UDP_H_ */
/* Server.cpp */
#include "Server.h"
Server::Server(){}
Server::~Server(){}
void Server::start()
{
udp->listen();
this->printMsg1();
}
void Server::printMsg1()
{
int pos = 0;
memcpy(&myMsg1->tag, udp->data, sizeof(myMsg1->tag));
memcpy(&myMsg1->nonce, udp->data + (pos += sizeof(myMsg1->tag)), sizeof(myMsg1->nonce));
memcpy(&myMsg1->length, udp->data + (pos += sizeof(myMsg1->nonce)), sizeof(myMsg1->length));
myMsg1->name = new char[myMsg1->length];
memcpy(myMsg1->name, udp->data + (pos += myMsg1->length), myMsg1->length);
if(output)
{
cout << sizeof(myMsg1->tag) << " Byte: TAG : " << (int8_t) myMsg1->tag
<< endl;
cout << sizeof(myMsg1->nonce) << " Byte: NONCE : " << myMsg1->nonce
<< endl;
cout << sizeof(myMsg1->length) << " Byte: LENGTH : " << myMsg1->length
<< endl;
cout << sizeof(myMsg1->name) << " Byte: NAME : ";
for(int i = 0; i<myMsg1->length; i++)
cout << myMsg1->name[i];
}
}
/* Server.h */
#ifndef SERVER_H_
#define SERVER_H_
#include <cstdint> // int32_t
#include <gmp.h>
#include <iostream> // cout, endl
#include <string> // string
#include <stdlib.h>
#include "Random.h"
#include "messages.h"
#include "UDP.h"
using std::cout;
using std::endl;
using std::string;
class Server
{
public:
Server();
virtual ~Server();
void start();
void printMsg1();
Msg1 *myMsg1 = new Msg1();
UDP *udp = new UDP();
};
#endif /* SERVER_H_ */

Using g++ to compile and link program with header cpp files in subfolder

Very new to this C++ thing and have been trying all night to compile a basic program with header files in a subfolder - I must be something so stupid but easily fixed. Maybe my lack of understanding around namespaces - or how headers are included???
Hopefully someone can help me out
All the examples seem to say I can compile / link on one line or in separate steps - the separate steps seems to give me the least number of errors
I can get the cpp files to compile and create .o files but can't get the output file to be created.
Final try: g++ ProcessCAP.o ./network/SocketClient.o -o ProcessCAP
Error message:
./network/SocketClient.o:(.rodata+0xc0): undefined reference to 'CAP::SocketClient::send(std::string)'
collect2: error: ld returned 1 exit status
Main Program:
#include <iostream>
#include <signal.h>
#include "network/SocketClient.h"
using namespace std;
using namespace CAP;
//int argc, char *argv[]
int main(void){
cout << "Starting CAP Processor Example" << "\n";
SocketClient sc("streaming1.my-url.com", 8080);
sc.connectToServer();
string rec = sc.receive(4096);
while (rec.length() > 0) {
cout << "Received [" << rec << "] \n";
string rec = sc.receive(4096);
}
sc.disconnectFromServer();
cout << "End of CAP Processor Example" << "\n";
}
Files in the "network" subfolder:
SocketClient.cpp
#include "SocketClient.h"
#include <stdio.h>
#include <string.h>
#include <unistd.h>
using namespace std;
namespace CAP {
SocketClient::SocketClient(std::string serverName, int portNumber) {
this->socketfd = -1;
this->server = NULL;
this->serverName = serverName;
this->portNumber = portNumber;
this->isConnected = false;
}
int SocketClient::connectToServer(){
socketfd = socket(AF_INET, SOCK_STREAM, 0);
if (socketfd < 0){
perror("Socket Client: error opening socket.\n");
return 1;
}
server = gethostbyname(serverName.data());
if (server == NULL) {
perror("Socket Client: error - no such host.\n");
return 1;
}
bzero((char *) &serverAddress, sizeof(serverAddress));
serverAddress.sin_family = AF_INET;
bcopy((char *)server->h_addr,(char *)&serverAddress.sin_addr.s_addr, server->h_length);
serverAddress.sin_port = htons(portNumber);
if (connect(socketfd, (struct sockaddr *) &serverAddress, sizeof(serverAddress)) < 0){
perror("Socket Client: error connecting to the server.\n");
return 1;
}
this->isConnected = true;
return 0;
}
string SocketClient::receive(int size=4096){
char readBuffer[size];
int n = read(this->socketfd, readBuffer, sizeof(readBuffer));
if (n < 0){
perror("Socket Client: error reading from socket");
}
return string(readBuffer);
}
int SocketClient::disconnectFromServer(){
this->isConnected = false;
close(this->socketfd);
return 0;
}
SocketClient::~SocketClient() {
if (this->isConnected == true){
disconnectFromServer();
}
}
} /* namespace CAP */
SocketClient.h (also in network subfolder)
#ifndef SOCKETCLIENT_H_
#define SOCKETCLIENT_H_
#include <sys/socket.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <netdb.h>
#include <string>
namespace CAP {
class SocketClient {
private:
int socketfd;
struct sockaddr_in serverAddress;
struct hostent *server;
std::string serverName;
int portNumber;
bool isConnected;
public:
SocketClient(std::string serverName, int portNumber);
virtual int connectToServer();
virtual int disconnectFromServer();
virtual int send(std::string message);
virtual std::string receive(int size);
bool isClientConnected() { return this->isConnected; }
virtual ~SocketClient();
};
}
#endif /* SOCKETCLIENT_H_ */

Segmentation fault sending a struct through TCP socket

I'm writing a simple program about TCP Socket. What I'm going to do is send whatever 1000 data structure from client to server, but it display segmentation fault....
This is my server:
#include <iostream>
#include <string>
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdlib.h>
#include <strings.h>
#include <stdio.h>
using namespace std;
#pragma pack(1)
struct student
{
int id;
string name;
};
main()
{
struct sockaddr_in socketInfo;
socklen_t fromlen;
int socketHandle;
int portNumber = 8080;
bzero(&socketInfo, sizeof(sockaddr_in)); // Clear structure memory
// create socket
if((socketHandle = socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
close(socketHandle);
exit(EXIT_FAILURE);
}
// Load system information into socket data structures
socketInfo.sin_family = AF_INET; //IPv4
socketInfo.sin_addr.s_addr = htonl(INADDR_ANY); // Use any address available to the system
socketInfo.sin_port = htons(portNumber); // Set port number
// Bind the socket to a local socket address
if( bind(socketHandle, (struct sockaddr *) &socketInfo, sizeof(socketInfo)) < 0)
{
close(socketHandle);
perror("bind");
exit(EXIT_FAILURE);
}
listen(socketHandle, 1);
int socketConnection;
while(1)
{
cout<<"Waiting to connect ..."<<endl;
if( (socketConnection = accept(socketHandle, NULL, NULL)) < 0)
{
cout<<"Fail!!"<<endl;
exit(EXIT_FAILURE);
}
//close(socketHandle);
int rc = 0; // Actual number of bytes read
struct student buf;
while(1)
{
rc = recv(socketConnection, &buf, sizeof(struct student)+1, 0);
cout<<"Recieve = "<<rc<<endl;
if (rc<=0)
break;
cout<<buf.id<<endl;
cout<<buf.name<<endl;
}
}
}
This is my client:
#include <iostream>
#include <sstream>
#include <string>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdlib.h>
#include <errno.h>
#include <netinet/in.h>
#include <arpa/inet.h>
using namespace std;
unsigned long inet_addr(const string a);
string int2str( int val ) // interger convert to string
{
ostringstream out;
out<<val;
return out.str();
}
#pragma pack(1)
struct student
{
int id;
string name;
};
main()
{
struct sockaddr_in remoteSocketInfo;
struct hostent *hPtr;
const char *remoteHost="localhost";
int socketHandle;
int portNumber = 8080;
bzero(&remoteSocketInfo, sizeof(sockaddr_in)); // Clear structure memory
if((hPtr = gethostbyname(remoteHost)) == NULL)
{
cerr << "System DNS name resolution not configured properly." << endl;
cerr << "Error number: " << ECONNREFUSED << endl;
exit(EXIT_FAILURE);
}
if((socketHandle = socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
close(socketHandle);
exit(EXIT_FAILURE);
}
// Load system information into socket data structures
memcpy((char *)&remoteSocketInfo.sin_addr, hPtr->h_addr, hPtr->h_length);
remoteSocketInfo.sin_family = AF_INET;
remoteSocketInfo.sin_port = htons(portNumber); // Set port number
if(connect(socketHandle, (struct sockaddr *)&remoteSocketInfo, sizeof(sockaddr_in)) < 0)
{
close(socketHandle);
exit(EXIT_FAILURE);
}
struct student buf[1000];
for (int i=0; i<1000; i++)
{
buf[i].id = i+1;
buf[i].name = "student_" + int2str(i) + "00";
send(socketHandle, &buf[i], sizeof(struct student)+1, 0);
}
}
Result:
Waiting to connect ...
Recieve = 13
1
Segmentation fault (core dumped)
The problem here is that one of the fields in struct student is a std::string object. This can't be sent across the wire directly like you're doing.
Instead, either change it to a fixed-size character array something like this...
struct student
{
int id;
char name[100];
}
... and write your name into there. Or you'll have to send it across the wire in a different way.

Sending string over UDP in C++

I would like to send a string: "Jane Doe" to intranet ip 192.168.0.4 to port 9000 over UDP. I have done this many times via UDP and TCP by Java, but now I have to do it with standard C++ libraries and I can't find any samples only topics where people just can't make it work.
I know that I have to encode "Jane Doe" as array of bytes then just open socket, pack it in datagram and send it.
C++ is not my first language and this is small part of code I can't figure out, I've chosen UDP because it is always much simpler than TCP.
A good source for network programming is Beej's Guide to Network Programming. Below is some sample Unix code.
If this is Windows programming:
"sock" should be of type SOCKET instead of int.
Use closesocket instead of close
#include <winsock2.h> instead of all those unix headers
#include <sys/types.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <memory.h>
#include <ifaddrs.h>
#include <net/if.h>
#include <errno.h>
#include <stdlib.h>
#include <iostream>
int resolvehelper(const char* hostname, int family, const char* service, sockaddr_storage* pAddr)
{
int result;
addrinfo* result_list = NULL;
addrinfo hints = {};
hints.ai_family = family;
hints.ai_socktype = SOCK_DGRAM; // without this flag, getaddrinfo will return 3x the number of addresses (one for each socket type).
result = getaddrinfo(hostname, service, &hints, &result_list);
if (result == 0)
{
//ASSERT(result_list->ai_addrlen <= sizeof(sockaddr_in));
memcpy(pAddr, result_list->ai_addr, result_list->ai_addrlen);
freeaddrinfo(result_list);
}
return result;
}
int main()
{
int result = 0;
int sock = socket(AF_INET, SOCK_DGRAM, 0);
char szIP[100];
sockaddr_in addrListen = {}; // zero-int, sin_port is 0, which picks a random port for bind.
addrListen.sin_family = AF_INET;
result = bind(sock, (sockaddr*)&addrListen, sizeof(addrListen));
if (result == -1)
{
int lasterror = errno;
std::cout << "error: " << lasterror;
exit(1);
}
sockaddr_storage addrDest = {};
result = resolvehelper("192.168.0.4", AF_INET, "9000", &addrDest);
if (result != 0)
{
int lasterror = errno;
std::cout << "error: " << lasterror;
exit(1);
}
const char* msg = "Jane Doe";
size_t msg_length = strlen(msg);
result = sendto(sock, msg, msg_length, 0, (sockaddr*)&addrDest, sizeof(addrDest));
std::cout << result << " bytes sent" << std::endl;
return 0;
}
This is very easy to do if you are willing to use the boost library.
Here is the code snippit
#include "boost/asio.hpp"
using namespace boost::asio;
...
io_service io_service;
ip::udp::socket socket(io_service);
ip::udp::endpoint remote_endpoint;
socket.open(ip::udp::v4());
remote_endpoint = ip::udp::endpoint(ip::address::from_string("192.168.0.4"), 9000);
boost::system::error_code err;
socket.send_to(buffer("Jane Doe", 8), remote_endpoint, 0, err);
socket.close();
I rewrote selbie's code to make it more C++-like and I minimized it a bit.
#include <iostream>
#include <string>
#include <arpa/inet.h> // htons, inet_addr
#include <netinet/in.h> // sockaddr_in
#include <sys/types.h> // uint16_t
#include <sys/socket.h> // socket, sendto
#include <unistd.h> // close
int main(int argc, char const *argv[])
{
std::string hostname{"192.168.0.4"};
uint16_t port = 9000;
int sock = ::socket(AF_INET, SOCK_DGRAM, 0);
sockaddr_in destination;
destination.sin_family = AF_INET;
destination.sin_port = htons(port);
destination.sin_addr.s_addr = inet_addr(hostname.c_str());
std::string msg = "Jane Doe";
int n_bytes = ::sendto(sock, msg.c_str(), msg.length(), 0, reinterpret_cast<sockaddr*>(&destination), sizeof(destination));
std::cout << n_bytes << " bytes sent" << std::endl;
::close(sock);
return 0;
}
For Windows, I took Mikolasan's minimised version of selbie's code and modified according to https://beej.us/guide/bgnet/html/#windows to get a small standalone example.
To get this to compile, you'll need to link the Winsock library.
#include <iostream>
#include <string>
#include <winsock2.h>
int main()
{
// Initialise Winsock DLL
// See https://beej.us/guide/bgnet/html/#windows
WSADATA wsaData;
// MAKEWORD(1,1) for Winsock 1.1, MAKEWORD(2,0) for Winsock 2.0
if (WSAStartup(MAKEWORD(1, 1), &wsaData) != 0) {
fprintf(stderr, "WSAStartup failed.\n");
exit(1);
}
// Set up connection and send
std::string hostname{ "192.168.0.4" };
uint16_t port = 9000;
SOCKET sock = ::socket(AF_INET, SOCK_DGRAM, 0);
sockaddr_in destination;
destination.sin_family = AF_INET;
destination.sin_port = htons(port);
destination.sin_addr.s_addr = inet_addr(hostname.c_str());
std::string msg = "Jane Doe";
int n_bytes = ::sendto(sock, msg.c_str(), msg.length(), 0, reinterpret_cast<sockaddr*>(&destination), sizeof(destination));
std::cout << n_bytes << " bytes sent" << std::endl;
::closesocket(sock);
// Clean up sockets library
WSACleanup();
return 0;
}

client server programming - buffer written

I am trying to develop client server program in c++ in which client is TCP echo client while server is TCP concurrent server using single process(using select system call). However i am succeed to develop it but problem with written buffer.
Server is writing some extra character from previous message after some message exchanged bet client and server,In starting it working fine for some message interchanged.
I am not getting why this happened?
//client code
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include <netdb.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <string.h>
#include <arpa/inet.h>
#include <iostream>
using namespace std;
#define MAXLINE 4096 /*max text line length*/
#define srv_PORT 3000 /*port*/
int main(int argc,char **argv)
{
int sockfd;
struct sockaddr_in srvaddr;
int sendchars,recvchar;
char buf[MAXLINE];
if (argc !=2)
{
cerr<<"Usage: Femto: <IP address of the srv"<<endl;
exit(1);
}
//Create a socket for the client
if ((sockfd = socket (AF_INET, SOCK_STREAM, 0)) <0)
{
cerr<<"Problem in creating the socket"<<endl;
exit(1);
}
//Creation of the socket
memset(&srvaddr, 0, sizeof(srvaddr));
srvaddr.sin_family = AF_INET;
srvaddr.sin_addr.s_addr= inet_addr(argv[1]);
srvaddr.sin_port = htons(srv_PORT);
//Connection of the client to the socket
if (connect(sockfd, (struct sockaddr *) &srvaddr, sizeof(srvaddr))<0)
{
cerr<<"Problem in connecting to the server"<<endl;
exit(1);
}
while (fgets(buf,sizeof(buf), stdin))
{
int n;
buf[MAXLINE]='\0';
sendchars=strlen(buf);
write(sockfd,buf,sendchars);
for(recvchar=0;recvchar<sendchars;recvchar+=n)
{
n=read(sockfd,&buf[recvchar],sendchars-recvchar);
if(n<0)
{
cerr<<"Read faild"<<endl;
}
cout<< "String received from the FGW: ";
fputs(buf, stdout);
}
}
}
//server code
#include <stdlib.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <string.h>
#include <unistd.h>
#include <iostream>
#include <sys/select.h>
#include <sys/time.h>
using namespace std;
#define MAXLINE 4096 /*max text line length*/
#define srv_PORT 3000 /*port*/
#define LISTENQ 65535
int main (int argc, char **argv)
{
int msock,ssock;
fd_set rfds;
fd_set afds;
int fd,nfds;
socklen_t client_len ;
char buf[MAXLINE];
struct sockaddr_in clientaddr, srvaddr;
if ((msock = socket (AF_INET, SOCK_STREAM, 0)) <0)
{
cerr<<"Problem in creating the socket"<<endl;
exit(1);
}
srvaddr.sin_family = AF_INET;
srvaddr.sin_addr.s_addr = htonl(INADDR_ANY);
srvaddr.sin_port = htons(srv_PORT);
bind (msock, (struct sockaddr *) &srvaddr, sizeof(srvaddr));
listen (msock, LISTENQ);
nfds=getdtablesize();
FD_ZERO(&afds);
FD_SET(msock,&afds);
while(1)
{
memcpy(&rfds,&afds,sizeof(rfds));
if(select(nfds,&rfds,(fd_set *)0,(fd_set *)0,(struct timeval * )0)<0)
{
cerr<<"Error in select";
// exit(1);
}
if(FD_ISSET(msock,&rfds))
{
//int ssock;
ssock= accept(msock,(struct sockaddr *)&clientaddr,&client_len);
if(ssock<0)
{
cerr<<"Accept error";
}
FD_SET(ssock,&afds);
}
for(fd=0;fd<nfds;++fd)
if(fd!=msock && FD_ISSET (fd,&rfds))
{
int cc;
char buf[MAXLINE];
cc=read(fd,buf,sizeof(buf));
cout<<"String received from and resent to the client:"<<endl;
puts(buf);
if(cc<0)
{
cerr<<"Read error"<<endl;
exit(1);
}
if(cc && write(fd,buf,cc)<0)
{
cerr<<"Write error"<<endl;
exit(1);
}
}
close(fd);
FD_CLR(fd,&afds);
}
}
buf[MAXLINE]='\0';
Is out of bounds. That may cause any error at any time.
You could declare
char buf[MAXLINE+1]