Reputation: 21
I am having some difficulty with finding out how to correct the segmentation fault. client.cpp
#include <errno.h>
#include <signal.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdlib.h>
#include <string.h>
#include <iostream>
#include <arpa/inet.h>
using namespace std;
int call_socket(char *hostname, unsigned short portnum)
{
struct sockaddr_in sa;
struct hostent *hp;
int a;
int s;
if ((hp = gethostbyname(hostname)) == NULL)
{
errno = ECONNREFUSED;
return(-1);
}
memset(&sa, 0, sizeof(sa));
memcpy((char*) &sa.sin_addr, hp->h_addr, hp->h_length);
sa.sin_family = hp->h_addrtype;
sa.sin_port = htons((u_short)portnum);
if ((s=socket(hp->h_addrtype, SOCK_STREAM, 0)) < 0)
{
return(-1);
}
if (connect(s, (struct sockaddr*)&sa, sizeof (sa)) < 0)
{
close(s);
return(-1);
}
return(s);
}
int main(int argc, char* argv[])
{
int n;
int s;
int b;
char username[256];
string hostname;
string usern;
string terminated = "Server Terminated";
string doesnotexist = "does not exist.";
hostname = "localhost";
char *hostn[hostname.size()+1];
strcpy(*hostn, hostname.c_str());
cout << "Enter a server port number: " << endl;
cin >> s;
while (s <2000 || s > 65535)
{
cout << "Server port number must be between 2000 and 65535. Please enter the server port number again." << endl;
cin >> s;
}
if ((b = call_socket(*hostn,s)) < 0)
{
perror("call Socket");
exit(1);
}
cout << "Enter a user name: " << endl;
cin >> usern;
strcpy(username, usern.c_str());
n = write(b, username, strlen(username));
if (n < 0)
{
cout << "Error writing to socket" << endl;
}
bzero(username, 256);
n = read(b,username,255);
if (n < 0)
{
cout << "Error reading from socket" << endl;
}
if (username == terminated)
{
printf("%s\n",username);
}
else if (username == doesnotexist)
{
cout << "The username: " << usern << ", ";
printf("%s\n",username);
}
else
{
cout << "The public key for " << usern << " is: ";
printf("%s\n",username);
}
close(b);
return 0;
}
I tried valgrind and got: Conditional jump or move depends on uninitialised value(s), Use of uninitialised value of size 8, Invalid write of size 8. As I am unexperienced with valgrind, I don't really know how to fix it.
Upvotes: 0
Views: 146
Reputation: 30569
Your problem is almost certainly here:
char *hostn[hostname.size()+1];
strcpy(*hostn, hostname.c_str());
This has several issues:
hostn
is a variable-length-array, which is not a standard part of C++hostn
is an array of char*
, not an array of char
hostn
are uninitialized, and thus don't point anywhere useful.hostn
to strcpy
as the destinationSince strcpy
will attempt to dereference the pointer passed to it and that pointer is uninitialized, that means your program's behavior is undefined.
Note that all of this could be avoided easily. Just get rid of hostn
entirely. It's not serving any purpose beyond what hostname.c_str()
already serves. Simply change call_socket
to accept a const char*
instead of a char*
, and you can call it directly using hostname.c_str()
(i.e. call_socket(hostname.c_str(), s)
)
Upvotes: 1