我正在尝试测试客户端程序以确保它正确发送和接收来自服务器的消息。当我运行程序时,我从 malloc 收到这个奇怪的错误。任何帮助都会很棒。我一直在看这段代码太久了。提前致谢。这是错误:
// 第一个测试运行正常
TEST 1 :
Connected to server
-> Socket open success
-> Request sent success
-> Response received success
Testing print:
Response received: <replyLoadAvg>0.228027:0.250000:0.280273</replyLoadAvg>
LoadAvg for 1min :: 0.228027
LoadAvg for 5min :: 0.250000
LoadAvg for 15min :: 0.280273
Real response -> <replyLoadAvg>0.228027:0.250000:0.280273</replyLoadAvg>
//然后由于某种原因我收到此错误
clientc(17781) malloc: ********* error for object 0x7fd048404318: incorrect checksum for
freed object - object was probably modified after being freed.
********* set a breakpoint in malloc_error_break to debug
Abort trap: 6
这是客户端代码:
// prototype
char* verifyString(char*);
void printLoadAvg(char*);
int receiveResponse(int, char **);
int main(int argc, char *argv[])
{
int sockfd;
char *name;
char *port;
struct sockaddr_in * dest;
if(argc != 3)
{
printf("Not enough arguments -- Exiting program\n");
return 0;
}
name = argv[1];
port = argv[2];
char * received;
char send[256];
char testMessages[5][256] = {"<loadavg/>", "<echo>Hello World!</echo>", "<echo> </echo>", "", "<echo>Bye Bye World...<echo>"};
char expectedResponses[5][256] = {"", "<reply>Hello World!</reply>", "<reply></reply>","<error>unknown format</error>", "<error>unknown format</error>"};
int i;
srand(time(NULL));
for(i = 0; i < 5; i++)
{
printf("\nTEST %i", i+1);
printf(((rand() % 2) ? ":\n" : " :\n"));
sprintf(send, "%s", testMessages[i]);
sockfd = createSocket(name, atoi(port), &dest);
if(sockfd < 0){
printf(" xx Open socket failed\n");
}
else{
printf(" -> Socket open success\n");
if(sendRequest(sockfd, send, dest) < 0){
printf(" xx Send failed\n");
}
else{
printf(" -> Request sent success\n");
if(receiveResponse(sockfd, &received) < 0){
printf(" xx Receive failed\n");
}
else{
printf(" -> Response received success\n");
if(i!=0 && strcmp(received, expectedResponses[i]) != 0){
printf("Incorrect message\n");
printf("Expected: %s\n", expectedResponses[i]);
printf("Received: %s\n", received);
}
else if(i!=0){
printf("Test %i. passed successfully!\n", i+1);
}
else{
printf("Testing print:\n");
printResponse(received);
fprintf(stdout, "Real response -> %s\n", received);
}
}
}
}
free(received);
free(dest);
if(closeSocket(sockfd)==0){
printf(" -> Socket closed success\n");
}
else{
printf(" XX Close failed\n");
}
}
return 0;
}
int createSocket( char* hostname, int port, struct sockaddr_in** dest)
{
// fill in the socket address struct
(*dest) = (struct sockaddr_in *)malloc(sizeof(struct sockaddr_in));
struct hostent *hostptr;
hostptr = gethostbyname(hostname);
int socketfd;
memset((void *) (*dest), 0, (size_t)sizeof(struct sockaddr_in));
(*dest)->sin_family = (short)(AF_INET);
memcpy((void*)& (*dest)->sin_addr, (void *) hostptr->h_addr, hostptr->h_length);
(*dest)->sin_port = htons((u_short)port);
// now get the file descriptor for the socket
if((socketfd = socket(PF_INET, SOCK_STREAM, 0)) < 0) {
return -1;
}
// connect to the server at the location displayed by TCPserver.c
if(connect(socketfd, (struct sockaddr*)(*dest), sizeof(struct sockaddr)) < 0) {
perror("Error: call to connect()\n");
return -1;
}
printf("Connected to server\n");
return socketfd;
}
int sendRequest(int sock, char* request, struct sockaddr_in* dest)
{
// send a request through the socket to the server.
if(write(sock, request, BUFFERSIZE) < 0)
{
return -1;
}
return 0;
}
int receiveResponse(int sock, char ** response)
{
// dynamically allocate memory to be used in this function
(*response) = malloc(sizeof(char));
// wait for a response from the server
if(read(sock, (*response), BUFFERSIZE) < 0)
{
return -1;
}
return 0;
}
int closeSocket(int sock)
{
int error = 0;
if(close(sock))
{
perror("Error: Failed to close socket\n");
error = -1;
}
return error;
}
void printResponse(char* response)
{
char* buffer = "<replyloadavg>";
int i, isLoadAvg = 0;
// verify the string is in the correct format by calling the verifty string function
// then print the string to the screen.
printf("Response received: %s\n", verifyString(response));
for(i = 0; i < 14; i++)
{
if(response[i] == buffer[i])
isLoadAvg = 0;
else
{
isLoadAvg = 1;
i = 15;
}
}
if (isLoadAvg)
{
printLoadAvg(response);
}
}
char* verifyString(char* string)
{
int i, count = 0;
// step through the array until you come to the last '>' (the end of the string)
// then insert the NULL terminator at the end of the string.
for(i = 0; i < BUFFERSIZE; i++)
{
if(string[i] == '>')
count++;
if(count == 2)
{
string[i + 1] = '\0';
i = BUFFERSIZE;
}
}
return string;
}
void printLoadAvg(char* string)
{
int i = 0, j;
// these three arrays hold the newly formated strings, the ones that are easier to read.
char s1[BUFFERSIZE], s2[BUFFERSIZE], s3[BUFFERSIZE];
// step through the string until you reach the end of the string
while(string[i] != '>')
{
i++;
}
i++;
// now insert a colon and then save the contents of the string to the appropriate s array.
for(j = 0; string[i] != ':'; j++, i++)
{
s1[j] = string[i];
}
// be sure to set the null terminator at the end.
s1[j] = '\0';
i++;
for(j = 0; string[i] != ':'; j++, i++)
{
s2[j] = string[i];
}
// be sure to set the null terminator at the end.
s2[j] = '\0';
i++;
// now move to the beginning of the end of the string array
for(j = 0; string[i] != '<'; j++, i++)
{
s3[j] = string[i];
}
// now insert one more null terminator for the final s array.
s3[j] = '\0';
// now print out the newly fomrated strings.
printf("\nLoadAvg for 1min :: %s\n", s1);
printf("LoadAvg for 5min :: %s\n", s2);
printf("LoadAvg for 15min :: %s\n", s3);
}