TCP CLIENT
以下のソースを入力し cl, linkしてみましょう。cmd> cl -c TcpClient.cpp cmd> link TcpClient.obj user32.lib gdi32.lib
file: tcpclient.cpp
#include <winsock2.h> #include <ws2tcpip.h> #pragma comment(lib, "ws2_32.lib") #define ID_SEND 100 #define ID_EDIT 200 WSAEVENT g_hEventExit = NULL; SOCKET InitSocket(LPSTR lpszServerName, LPSTR lpszPort); DWORD WINAPI ThreadProc(LPVOID lpParam); LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wP, LPARAM lP); int WINAPI WinMain(HINSTANCE hInst, HINSTANCE hPrevInst, LPSTR lpszCmdLine, int nCmdShow) { TCHAR szAppName[] = TEXT("TCP CLIENT"); HWND hwnd; MSG msg; WNCDCLASSEX wcex; wcex.cbSize = sizeof(WNDCLASSEX); wcex.style = 0; wcex.lpfnWndProc = WindowProc; wcex.cbClsExtra = 0; wcex.cbWndExtra = 0; wcex.hInstance = hInst; wcex.hIcon = LoadIcon(NULL, IDI_APPLICATION); wcex.hCursor = LoadCursor(NULL, IDC_ARROW); wcex.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH); wcex.lpszMenuName = NULL; wcex.lpszClassName = szAppName; wcex.hIconSm = LoadIcon(NULL, IDI_APPLICATION); if(RegisterClassEx(&wc) == 0) return 0; hwnd = CreateWindowEx(0, szAppName, szAppName, WS_OVERLAPPEDWINDOW, 0, 0, 320, 240, NULL, NULL, hInst, NULL); if(hwnd == NULL) return 0; ShowWindow(hwnd, nCmdShow); UpdateWindow(hwnd); while(GetMessage(&msg, NULL, 0, 0) > 0) { TranslateMessage(&msg); DispatchMessage(&msg); } return (int)msg.wParam; } LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wP, LPARAM lP) { static HWND hwndButton = NULL; static HWND hwndEdit = NULL; static HANDLE hThread = NULL; static SOCKET soc = INVALID_SOCKET; switch(uMsg) { case WM_CREATE: { DWORD dwThreadId; hwndButton = CreateWindowEx(0, TEXT("BUTTON"), TEXT("Send"), WS_CHILD | WS_VISIBLE, 10, 10, 60, 30, hwnd, (HMENU)ID_SEND, ((LPCREATESTRUCT)lP)->hInstance, NULL); hwndEdit = CreateWindowEx(0, TEXT("EDIT"), TEXT("Message to send"), WS_CHILD | WS_VISIBLE | WS_BORDER, 90, 10, 300, 35, hwnd, (HMENU)ID_EDIT, ((LPCREATESTRUCT)lP)->hInstance, NULL); soc = InitSocket("localhost", "49999"); if(soc == INVALID_SOCKET) return -1; g_hEventExit = WSACreateEvent(); hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)ThreadProc, &soc, 0, &dwThreadId); return 0; } case WM_COMMAND: { int nLen; int nResult; TCHAR szData[256]; if(LOWORD(wP) != ID_SEND) return 0; nLen = GetWindowText(hwndEdit, szData, sizeof(szData)); nLen = (nLen + 1) * sizeof(TCHAR); nResult = send(soc, (char *)szData, nLen, 0); if(nResult == SOCKET_ERROR) MessageBox(NULL, TEXT("send error"), NULL, MB_ICONWARNING); return 0; } case WM_DESTROY: { if(Thread != NULL) { WSASetEvent(g_hEventExit); WaitForSingleObject(hThread, 1000); CloseHandle(hThread); WSACloseEvent(g_hEventExit); } if(soc != INVALID_SOCKET) { shutdown(soc, SD_BOTH); closesocket(soc); WSACleanup(); } PostQuitMessage(0); return 0; } default: break; } return DefWindowProc(hwnd, uMsg, wP, lP); } DWORD WINAPI ThreadProc(LPVOID lpParam) { SOCKET soc = *(SOCKET *)lpParam; DWORD dwResult; WSAEVENT hEvent; WSAEVENT hEventArray[2]; WSANETWORKEVENTS events; hEvent = WSACreateEvent(); WSAEventSelect(soc, hEvent, FD_READ | FD_CLOSE); hEventArray[0] = hEvent; hEventArray[1] = g_hEventExit; for(;;) { dwResult = WSAWaitForMultipleEvents(2, hEventArray, FALSE, WSA_INFINITE, FALSE); if(dwResult == WSA_WAIT_FAILED) break; if(dwResult - WSA_WAIT_EVENT_0 == 0) { WSAEnumNetworkEvents(soc, hEvent, &events); if(events.lNetworkEvents & FD_CLOSE) { MessageBox(NULL, TEXT("connection closed"), TEXT("OK"), MB_OK); break; } else if(events.lNetworkEvents & FD_READ) { int nLen; int nResult; TCHAR szBuf[256]; TCHAR szData[256]; nLen = sizeof(szData); nResult = recv(soc, (char *)szData, nLen, 0); wsprintf(szBuf, TEXT("%dbyte received\n%s"), nResult, szData); MessageBox(NULL, szBuf, TEXT("OK"), MB_OK); } else ; WSAResetEvent(hEvent); } else if(dwResult - WSA_WAIT_EVENT_0 == 1) break; else ; } WSACloseEvent(hEvent); return 0; } SOCKET InitSocket(LPSTR lpszServerName, LPSTR lpszPort) { WSADATA wsaData; ADDRINFO addrHints; LPADDRINFO lpAddrList; SOCKET soc; WSAStartup(MAKEWORD(2, 2), &wsaData); ZeroMemory(&addrHints, sizeof(addrinfo)); addrHints.ai_family = AF_INET; addrHints.ai_socktype = SOCK_STREAM; addrHints.ai_protocol = IPPROTO_TCP; if(getaddrinfo(lpszServerName, lpszPort, &addrHints, &lpAddrList) != 0) { MessageBox(NULL, TEXT("Failed to get hostinfo.."), NULL, MB_ICONWARNING); WSACleanup(); return INVALID_SOCKET; } soc = socket(lpAddrList->ai_family, lpAddrList->ai_socktype, lpAddrList->ai_protocol); if(connect(soc, lpAddrList->ai_addr, (int)lpAddrList->ai_addrlen) == SOCKET_ERROR) { int nError = WSAGetLastError(); if(nError == WSAECONNREFUSED) MessageBox(NULL, TEXT("Connection refused."), NULL, MB_ICONWARNING); else if(nError == WSAEHOSTUNREACH) MessageBox(NULL, TEXT("Unreachable."), NULL, MB_ICONWARNING); else MessageBox(NULL, TEXT("Failed to connect"), NULL, MB_ICONWARNING); freeaddrinfo(lpAddrList); closesocket(soc); WSACleanup(); return INVALID_SOCKET; } freeaddrinfo(lpAddrList); return soc; }