Question

Im developing a C code to do a GET request and handle variable size response.

I use realloc to resize the heap chunk where i am storing the response. The problem is that i am getting an error related with the CrtIsValidHeapPointer function of the realloc call.

The loop is working during 6 times but it is throwing up an error at the 7th loop. I have here the code for you:

#include "stdafx.h"

using namespace std;
int GET_request(char *hostname, char *path);
char *scat(char *, char *);
int _tmain(int argc, _TCHAR* argv[])
{
    GET_request("www.marca.com", "/");
}

int GET_request(char *hostname, char *path){

char request[256];
WSADATA wsaData;
if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
    printf("WSAStartup failed.\n");
    system("pause");
    return 1;
}
SOCKET Socket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
struct hostent *host;
host = gethostbyname(hostname);
SOCKADDR_IN SockAddr;
SockAddr.sin_port = htons(80);
SockAddr.sin_family = AF_INET;
SockAddr.sin_addr.s_addr = *((unsigned long*)host->h_addr);
printf("Connecting...\n");
if (connect(Socket, (SOCKADDR*)(&SockAddr), sizeof(SockAddr)) != 0){
    printf("Could not connect");
    system("pause");
    return 1;
}
printf("Connected.\n");

if ((strlen(hostname) + strlen(path)) > 197)
{
    printf("Lenght too long for a GET path");
    return 1;
}
else
{
    const char *method = "GET ";
    strcpy_s(request, method);
    strcat_s(request, path);
    strcat_s(request, " HTTP/1.1\r\n");
    strcat_s(request, "Host: ");
    strcat_s(request, hostname);
    strcat_s(request, "\r\n");
    strcat_s(request, "Connection: close\r\n\r\n");
}

//printf_s(request);

int len;
len = strlen(request);
system("pause");
send(Socket, request, strlen(request), 0);
char *ptr = (char*)calloc(sizeof(char),1024);
char *ptr2 = NULL;
int nDataLength;
int i = 0;
while ((nDataLength = recv(Socket, ptr, 1023, 0)) > 0){

    if (i > 0){//prepare in case that the response is bigger than 1024 bytes
        //printf("Data len: %d\n", nDataLength);    
        //system("pause");
        printf("%p apunta a %d len: %d e i vale: %d\n", ptr2, *ptr2, ((1023 * i) + nDataLength), i);
        system("pause");
        ptr2 = (char*)realloc(ptr2, ((1023 * i) + nDataLength));
        if (ptr2==NULL){
            printf("Some error reallocating memory\n");
            system("pause");
            i++;
        }
        else{
            memcpy(ptr2 + (1024 * i), ptr, nDataLength);
            //printf("%s\n", ptr2);
            //system("pause");
            i++;
        }

    }
    else{
        ptr2 = (char*)realloc(ptr2, ((1023 * i) + nDataLength));
        memcpy(ptr2, ptr, nDataLength);
        i++;
    }
}
printf("%s",ptr2);
system("pause");

closesocket(Socket);
WSACleanup();
system("pause");
FILE* pFile;
pFile = fopen("myfile.txt", "wb");
fwrite(ptr2, 1, strlen(ptr2), pFile);
fclose(pFile);
free(ptr2);
return 0;
}

You can just check the while loop. I just wanted to give you all the code in case that you want to try it. Im getting this:

Connecting... Connected. Press any key to continue . . . 0033D500 apunta a 72 len: 2046 e i vale: 1 Press any key to continue . . . 0033D500 apunta a 72 len: 3069 e i vale: 2 Press any key to continue . . . 0033D500 apunta a 72 len: 4092 e i vale: 3 Press any key to continue . . . 0033D500 apunta a 72 len: 5115 e i vale: 4 Press any key to continue . . . 0033D500 apunta a 72 len: 6138 e i vale: 5 Press any key to continue . . . 0033D500 apunta a 72 len: 7161 e i vale: 6 Press any key to continue . . .

Thanks

Was it helpful?

Solution

You are allocating with

ptr2 = (char*)realloc(ptr2, ((1023 * i) + nDataLength));

using 1023*i, but in copy doing

memcpy(ptr2 + (1024 * i), ptr, nDataLength);

i.e. using 1024*i

So you are writing to more than you allocated. Referring to unallocated memory is undefined behavior and most likely cause fatal error at some point.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top