C-сокет HTTP-запрос асинхронно печатает ответ, когда нет явной команды для этого - PullRequest
0 голосов
/ 15 мая 2018

Я пытаюсь изучить C-сокеты прямо сейчас, делая простой веб-скребок, но сам выполняю программирование сокетов и HTTP-запросы, в настоящее время используя библиотеки сокетов. Я написал функцию, которая успешно отправляет не-SSL-запрос на http://mirror.vcu.edu и сохраняет вывод в переменной с именем response.

char *noSSLRequest(REQUEST_HEADER_INFO *request_header_info) {
    struct sockaddr_in serverAddress;
    char *requestHeader;
    unsigned short serverPort;
    char serverIP[13];
    domainToIP(request_header_info->host, serverIP);
    char *response = calloc(0, 0);
    ssize_t bytesReceived = 0;


    int sockFD; //Only supporting IPV4 right now, returns file descriptor for socket

    if ((sockFD = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) < -1) {
        freeRequestHeaderInfo(request_header_info);
        fprintf(stderr, "Error, could not open socket in http.c getHTMLBody(). Reason for error %s", strerror(errno));
        exit(-1);
    }
    printf(ANSI_COLOR_GREEN "LOG: Socket file descriptor is %d" ANSI_COLOR_RESET, sockFD);
    serverPort = 80;
    memset(&serverAddress, 0, sizeof(serverAddress));
    serverAddress.sin_family = AF_INET;
    serverAddress.sin_port = htons(80);
    inet_aton(serverIP, &serverAddress.sin_addr);

    if (connect(sockFD, (const struct sockaddr *) &serverAddress, sizeof(serverAddress)) < 0) {
        freeRequestHeaderInfo(request_header_info);
        fprintf(stderr, "Error, could not connect socket in http.c getHTMLBody(). Reason for error %s",
                strerror(errno));
        exit(-1);
    }

    printf(ANSI_COLOR_GREEN "\nLOG: Connected socket at descriptor %d to IP %s and port %d" ANSI_COLOR_RESET, sockFD,
           serverIP, serverPort);

    requestHeader = craftRequestHeader(request_header_info);

    if (send(sockFD, requestHeader, strlen(requestHeader), 0) < 0) {
        freeRequestHeaderInfo(request_header_info);
        fprintf(stderr, "Error, could not send request. Reason for error %s",
                strerror(errno));
        exit(-1);
    }

    printf(ANSI_COLOR_GREEN "\nLOG: Sent HTTP request from socket at descriptor %d to IP %s and port %d." ANSI_COLOR_RESET,
           sockFD,
           serverIP, serverPort);


    free(requestHeader);
    printf(ANSI_COLOR_GREEN "\nLOG: Starting receive operation" ANSI_COLOR_RESET);
    ssize_t bytesReceivedPrevious = -1;
    char buffer[RESPONSE_BUFFER_SIZE];


    while (bytesReceived < (RESPONSE_MAX_LEN * sizeof(char)) && bytesReceived > bytesReceivedPrevious) {
        bytesReceivedPrevious = bytesReceived;
        bytesReceived = recv(sockFD, buffer, RESPONSE_BUFFER_SIZE, 0);
        response = realloc(response, sizeof(*response) + RESPONSE_BUFFER_SIZE);
        strcat(response, buffer); //Append to the end, safe because recv takes care of limiting buffer size
    }
    response = realloc(response, sizeof(*response) + sizeof(char));
    response[strlen(response)] = '\0';
    printf(ANSI_COLOR_GREEN "\nLOG: Received HTTP response from socket at descriptor %d to IP %s and port %d.\n\n\n\n\n" ANSI_COLOR_RESET,
           sockFD,
           serverIP, serverPort);
    if (close(sockFD) < 0) {
        freeRequestHeaderInfo(request_header_info);
        fprintf(stderr, "Error, could not close socket in http.c getHTMLBody(). Reason for error %s", strerror(errno));
        exit(-1);
    }
    printf(ANSI_COLOR_GREEN "\nLOG: Closed socket at descriptor %d" ANSI_COLOR_RESET, sockFD);
    freeRequestHeaderInfo(request_header_info);

    return response;
}

Все работает нормально, отклик имеет нулевой терминатор, и жизнь хороша, за исключением того, что в моей консоли по какой-то причине выводится вывод response. Я чувствую, что что-то где-то просачивается, потому что этот вывод также отображается зеленым, хотя после каждого журнала я возвращаю цвет по умолчанию. Я знаю, что некоторые флаги и другие вещи там не показаны, я не мог получить всю информацию и код здесь, поэтому у меня есть репозиторий github и более подробная проблема .

Изображение журнала включено здесь и в выпуске, хотя я не смог получить полный вывод, поэтому проблема в цветном текстовом сообщении.

Image of function log output

1 Ответ

0 голосов
/ 15 мая 2018

Этот код

response = realloc(response, sizeof(response) + RESPONSE_BUFFER_SIZE);

и этот код

response = realloc(response, sizeof(response) + sizeof(char));

оба вызывают неопределенное поведение.

response - это char * - указатель. sizeof() указатель - это размер указателя , а не длина строки, на которую он указывает.

Обратите внимание также, что sizeof(char) является одним по определению.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...