socket方式发送Http GET消息

#include <stdio.h>  
#include <WinSock2.h>  
  
#pragma comment(lib, "ws2_32.lib")  
  
// 连接服务器发送消息并将接收数据保存到 pReceiveBuf 中,此过程会 select 并 recv 消息,直到没有数据到达或者接收缓存已满  
int connectAndSendData(const char *szHost, unsigned short nPort, const char *pDataToSend, unsigned int nDataSize, char *pReceiveBuf = NULL, unsigned int *pnReceiveSize = NULL)  
{  
    WORD wVersionRequested = MAKEWORD(1, 1);  
    WSADATA wsaData;  
  
    int err = ::WSAStartup(wVersionRequested, &wsaData);  
    if ( 0 != err )  
    {  
        printf("[connectAndSendData]: WSAStartup failed. return %d. \r\n", err);  
        return -1;  
    }  
  
    if ( wsaData.wVersion != wVersionRequested )  
    {  
        printf("[connectAndSendData]: wsaData.wVersion %d is not equal to wVersionRequested %d.\r\n", wsaData.wVersion, wVersionRequested);  
        ::WSACleanup();  
        return -2;  
    }  
  
    SOCKET sock = ::socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);  
    if ( INVALID_SOCKET == sock )  
    {  
        printf("[connectAndSendData]: socket error %d. \r\n", WSAGetLastError());  
        return -3;  
    }  
  
    struct hostent *p_hostent = gethostbyname(szHost);  
    if( NULL == p_hostent )  
    {  
        printf("[gethostbyname]: socket error %d. \r\n", WSAGetLastError());  
        ::closesocket(sock);  
        ::WSACleanup();  
        return -4;  
    }  
  
    SOCKADDR_IN addr_server;  
    addr_server.sin_family  = AF_INET;  
    addr_server.sin_addr    = *((struct in_addr*)p_hostent->h_addr);  
    memset(addr_server.sin_zero, 0, 8);  
    addr_server.sin_port    = htons(nPort);  
  
    err = ::connect(sock, (SOCKADDR*)&addr_server, sizeof(addr_server));  
    if ( SOCKET_ERROR == err )  
    {  
        printf("[connectAndSendData]: connect %s:%d error %d. \r\n", szHost, nPort, WSAGetLastError());  
        ::closesocket(sock);  
        ::WSACleanup();  
        return -5;  
    }  
  
    err = ::send(sock, pDataToSend, nDataSize, 0);  
    if ( SOCKET_ERROR == err )  
    {  
        printf("[connectAndSendData]: send error %d. \r\n", WSAGetLastError());  
    }  
  
    if ( NULL != pReceiveBuf && NULL != pnReceiveSize )  
    {  
        char *p_receive = pReceiveBuf;  
        char *p_buf = p_receive;  
        int n_buf_len = *pnReceiveSize;  
        int n_len = n_buf_len - 1;  
        int n_read = 0;  
        char temp[256];  
        int n_head_len = -1;  
        int n_content_len = -1;  
        const char *content = NULL;  
  
        while (1)  
        {  
            fd_set fds;  
            FD_ZERO(&fds);  
            FD_SET(sock, &fds);  
            struct timeval timeo;  
            timeo.tv_sec = 10;  
            timeo.tv_usec = 1000;  
  
            int ret = select(sock, &fds, NULL, NULL, &timeo);  
            if (ret <= 0)  
                break;  
  
            if (FD_ISSET(sock, &fds))  
            {  
                n_read = ::recv(sock, p_buf, n_len, 0);  
                if (n_read <= 0)  
                    break;  
  
                p_buf += n_read;  
                n_len -= n_read;  
                if ( n_len == 0 )  
                    break;  
  
                const char *rnrn = strstr(p_receive, "\r\n\r\n");  
                if (NULL != rnrn && rnrn < p_buf)  
                {  
                    rnrn += 4;  
                    content = rnrn;  
  
                    if (-1 == n_content_len)  
                    {  
                        const char *content_length = strstr(p_receive, "Content-Length: ");  
                        if (NULL != content_length && content_length < p_buf)  
                        {  
                            content_length += 16;  
                            const char *rn = strstr(content_length, "\r\n");  
                            if (NULL != rn && rn < p_buf)  
                            {  
                                int count = rn - content_length;  
                                strncpy(temp, content_length, count);  
                                temp[count] = '\0';  
                                n_content_len = atoi(temp);  
                            }  
                        }  
  
                        if (-1 == n_content_len)  
                        {  
                            const char *rn = strstr(rnrn, "\r\n");  
                            if (NULL != rn && rn < p_buf)  
                            {  
                                int count = rn - rnrn;  
                                strncpy(temp, rnrn, count);  
                                temp[count] = '\0';  
                                if (1 == sscanf(temp, "%x", &n_content_len) )  
                                {  
                                    n_content_len += 7; // 0D 0A 30 0D 0A 0D 0A  
                                    content = rn + 2;  
                                }  
                            }  
                        }  
  
                        if (-1 == n_content_len)  
                        {  
                            const char *connection = strstr(p_receive, "Connection: ");  
                            if (NULL != connection && connection < p_buf)  
                            {  
                                connection += 12;  
                                const char *rn = strstr(connection, "\r\n");  
                                if (NULL != rn && rn < p_buf)  
                                {  
                                    int count = rn - connection;  
                                    strncpy(temp, connection, count);  
                                    temp[count] = '\0';  
                                    connection = _strupr(temp);  
                                    if (0 == strcmp(connection, "CLOSE"))  
                                        n_content_len = 0;  
                                }  
                            }  
                        }  
                    }  
                }  
  
                if (NULL != content && n_content_len > 0)  
                {  
                    n_head_len = content - p_receive;  
                    int n_cur_len = p_buf - p_receive;  
                    if ( n_cur_len >= n_head_len + n_content_len )  
                        break;  
                }  
            }  
        }  
  
        n_len = n_buf_len - 1 - n_len;  
        n_buf_len = n_len;  
        p_receive[n_len] = '\0';  
    }  
  
    err = ::closesocket(sock);  
    if ( SOCKET_ERROR == err )  
    {  
        printf("[connectAndSendData]: closesocket error %d. \r\n", WSAGetLastError());  
    }  
  
    ::WSACleanup();  
  
    return 0;  
}  
  
int main()  
{  
    char request_buffer[1024];  
    request_buffer[0] = '\0';  
  
    // 写 HTTP 头信息  
    // HTPP 头可以有多行,每行都以 \r\n 结尾,最后再以 \r\n 结束  
    strcat(request_buffer, "GET /index.php?id=1 HTTP/1.1\r\n");  
    strcat(request_buffer, "Host: 127.0.0.1:80\r\n");  
    strcat(request_buffer, "Connection: keep-alive\r\n");  
    strcat(request_buffer, "Accept: */*\r\n");  
    strcat(request_buffer, "\r\n");  
  
    char receive_buff[102400];  
    unsigned n_receive_len = 102400;  
    receive_buff[0] = '\0';  
    connectAndSendData("127.0.0.1", 80, request_buffer, strlen(request_buffer), receive_buff, &n_receive_len);  
    printf(receive_buff);  
  
    getchar();  
    return 0;  
}  


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值