• 实现基于IOCP的回声服务器端


      1 #include <stdio.h>
      2 #include <stdlib.h>
      3 #include <process.h>
      4 #include <winsock2.h>
      5 #include <windows.h>
      6 
      7 #define BUF_SIZE 1024
      8 #define READ 3
      9 #define WRITE 5
     10 
     11 typedef struct  //socket info
     12 {
     13     SOCKET hClntSock;
     14     SOCKADDR_IN clntAdr;
     15 }PER_HANDLE_DATA, *LPPER_HANDLE_DATA;
     16 
     17 typedef struct  //buffer info
     18 {
     19     OVERLAPPED overlapped;
     20     WSABUF wsaBuf;
     21     char buffer[BUF_SIZE];
     22     int rwMode; // READ or WRITE
     23 }PER_IO_DATA, *LPPER_IO_DATA;
     24 
     25 unsigned WINAPI EchoThreadMain(LPVOID CompletionPortIO);
     26 void ErrorHanding(char *msg);
     27 
     28 int main(int argc, char *argv[])
     29 {
     30     WSADATA wsaData;
     31     HANDLE hComPort;
     32     SYSTEM_INFO sysInfo;
     33     LPPER_IO_DATA ioInfo;
     34     LPPER_HANDLE_DATA handleInfo;
     35 
     36     SOCKET hServSock;
     37     SOCKADDR_IN servAdr;
     38     int recvBytes, i, flags = 0;
     39     if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0)
     40         ErrorHanding("WSAStartUp() error!");
     41 
     42     hComPort = CreateIoCompletionPort(INVALID_HANDLE_VALUE, NULL, 0, 0);
     43     GetSystemInfo(&sysInfo);
     44     for (i = 0; i < sysInfo.dwNumberOfProcessors; i++)
     45         _beginthreadex(NULL, 0, EchoThreadMain, (LPVOID)hComPort, 0, NULL);
     46 
     47     hServSock = WSASocket(AF_INET, SOCK_STREAM, 0, NULL, 0, WSA_FLAG_OVERLAPPED);
     48     memset(&servAdr, 0, sizeof(servAdr));
     49     servAdr.sin_family = AF_INET;
     50     servAdr.sin_addr.s_addr = htonl(INADDR_ANY);
     51     servAdr.sin_port = htons(atoi(argv[1]));
     52 
     53     bind(hServSock, (SOCKADDR *)&servAdr, sizeof(servAdr));
     54     listen(hServSock, 5);
     55 
     56     while (1)
     57     {
     58         SOCKET hClntSock;
     59         SOCKADDR_IN clntAdr;
     60         int addrLen = sizeof(clntAdr);
     61 
     62         hClntSock = accept(hServSock, (SOCKADDR *)&servAdr, &addrLen);
     63         handleInfo = (LPPER_HANDLE_DATA)malloc(sizeof(PER_HANDLE_DATA));
     64         handleInfo->hClntSock = hClntSock;
     65         memcpy(&(handleInfo->clntAdr), &clntAdr, addrLen);
     66 
     67         CreateIoCompletionPort((HANDLE)hClntSock, hComPort, (DWORD)handleInfo, 0);
     68 
     69         ioInfo = (LPPER_IO_DATA)malloc(sizeof(PER_IO_DATA));
     70         memset(&(ioInfo->overlapped), 0, sizeof(OVERLAPPED));
     71         ioInfo->wsaBuf.len = BUF_SIZE;
     72         ioInfo->wsaBuf.buf = ioInfo->buffer;
     73         ioInfo->rwMode = READ;
     74         WSARecv(handleInfo->hClntSock, &(ioInfo->wsaBuf), 1, (LPDWORD)&recvBytes, (LPDWORD)&flags, &(ioInfo->overlapped), NULL);
     75     }
     76     return 0;
     77 } // end of main function
     78 
     79 unsigned WINAPI EchoThreadMain(LPVOID pComPort)
     80 {
     81     HANDLE hComPort = (HANDLE)pComPort;
     82     SOCKET sock;
     83     DWORD bytesTrans;
     84     LPPER_HANDLE_DATA handleInfo;
     85     LPPER_IO_DATA ioInfo;
     86     DWORD flags = 0;
     87 
     88     while (1)
     89     {
     90         GetQueuedCompletionStatus(hComPort, &bytesTrans, (LPDWORD) &handleInfo, (LPOVERLAPPED *) &ioInfo, INFINITE);
     91         sock = handleInfo->hClntSock;
     92 
     93         if (ioInfo->rwMode == READ)
     94         {
     95             puts("message received!");
     96             if (bytesTrans == 0)
     97             {
     98                 closesocket(sock);
     99                 free(handleInfo);
    100                 free(ioInfo);
    101                 continue;
    102             }
    103 
    104             memset(&(ioInfo->overlapped), 0, sizeof(OVERLAPPED));
    105             ioInfo->wsaBuf.len = bytesTrans;
    106             ioInfo->rwMode = WRITE;
    107             WSASend(sock, &(ioInfo->wsaBuf), 1, NULL, 0, &(ioInfo->overlapped), NULL);
    108             
    109             ioInfo = (LPPER_IO_DATA)malloc(sizeof(PER_IO_DATA));
    110             memset(&(ioInfo->overlapped), 0, sizeof(OVERLAPPED));
    111             ioInfo->wsaBuf.len = BUF_SIZE;
    112             ioInfo->wsaBuf.buf = ioInfo->buffer;
    113             ioInfo->rwMode = READ;
    114             WSARecv(sock, &(ioInfo->wsaBuf), 1, NULL, &flags, &(ioInfo->overlapped), NULL);
    115         }
    116         else
    117         {
    118             puts("message sent!");
    119             free(ioInfo);
    120         }
    121     }
    122     return 0;
    123 }
    124 
    125 void ErrorHanding(char *msg)
    126 {
    127     fputs(msg, stderr);
    128     fputc('
    ', stderr);
    129     exit(1);
    130 }
  • 相关阅读:
    MySQL--字符集参数
    MySQL--字符集基础
    Cassandra基础2
    Cassandra基础
    Cassandra -- Cassandra 3.0版本安装
    Cassandra Demo--Python操作cassandra
    MySQL--批量插入导致自增跳号问题
    MySQL Disk--SSD和HDD的性能
    MySQL Lock--并发插入导致的死锁
    TCL-视图
  • 原文地址:https://www.cnblogs.com/wisdomroc/p/11867766.html
Copyright © 2020-2023  润新知