是不是socket都要用线程?我直接用函数,send()能成功,但recv()不行。
如果是,能给我个代码例程吗?

解决方案 »

  1.   

    你用的是csokcet还是winsock
    然后用的是什么网络模型?
      

  2.   

    用的是winsock 
    WSAAsyncSelect 模型
      

  3.   

    你要多接收几次,比如你发送20byte,你接收了10byte那还有10个要在接收!
      

  4.   

    你要多接收几次,比如你发送20byte,你接收了10byte那还有10个要在接收!
      

  5.   

    你要多接收几次,比如你发送20byte,你接收了10byte那还有10个要在接收!
      

  6.   

    WSAAsyncSelect不需要用线程,接收消息即可
      

  7.   

    1. if (WSAAsyncSelect(m_hSocket, m_hMainWnd, nMsgID, lEvent) == SOCKET_ERROR)
    return FALSE;2. 指定消息映射函数3. 消息处理LPARAM OnClientSockMsg(WPARAM wParam, LPARAM lParam)
    {
    if (wParam == 0 && lParam == 0)
    return 0; if (WSAGETSELECTERROR(lParam))
    {
    OnSocketClose();
    m_status = STATUS_NONE;
    return 0;
    } switch (WSAGETSELECTEVENT(lParam))
    {
    case FD_CONNECT:
    {
    if (!InitThread(SelectModelMsgThread, (LPVOID)this))
    break;
    OnSocketConnect();
    m_status = STATUS_CONNECT;
    }
    break; case FD_CLOSE:
    {
    OnSocketClose();
    m_status = STATUS_NONE;
    }
    break; case FD_READ:
    {
    OnSocketRead();
    m_status = STATUS_READ;
    }
    break; default:
    break;
    }
    return 1;
    }
      

  8.   

    我的代码:
    1、对话框初始化程序,socket主程序
    BOOL CsocketDlg::OnInitDialog()
    {
          .....
    // TODO: Add extra initialization here    //----------------------
        // Declare and initialize variables.
        WSADATA wsaData;
        int iResult;
    CString strMessageTemp;    
        struct sockaddr_in clientService; 
        char *sendbuf = "abc";   
      
        //----------------------
        // Initialize Winsock
        iResult = WSAStartup(MAKEWORD(2,2), &wsaData);
        if (iResult != NO_ERROR) 
    {
    strMessageTemp.Format(_T("WSAStartup error:%d"), iResult);
    AfxMessageBox(strMessageTemp);
    return FALSE;
        }    //----------------------
        // Create a SOCKET for connecting to server
        m_ConnectSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
        if (m_ConnectSocket == INVALID_SOCKET) 
    {
    strMessageTemp.Format(_T("socket error:%d"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
            WSACleanup();
            return FALSE;
        }     //----------------------
        // The sockaddr_in structure specifies the address family,
        // IP address, and port of the server to be connected to.
        clientService.sin_family = AF_INET;
        clientService.sin_addr.s_addr = inet_addr( "127.10.0.1" );
        clientService.sin_port = htons( 5000);    //----------------------
        // Connect to server.
        iResult = connect( m_ConnectSocket, (SOCKADDR*) &clientService, sizeof(clientService) );
        if ( iResult == SOCKET_ERROR)
    {
            closesocket (m_ConnectSocket);
    strMessageTemp.Format(_T("connect error:%d"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
            WSACleanup();
            return FALSE;
        } //----------------------
    //network events[WSAAsyncSelect model], if there is data to read or write, WM_SOCKET message will be activated
    iResult = WSAAsyncSelect(m_ConnectSocket, this->m_hWnd, WM_SOCKET, FD_READ|FD_WRITE|FD_CLOSE);
    if (iResult != 0) 
    {
    strMessageTemp.Format(_T("WSAAsyncSelect failed: %d\n"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
            closesocket(m_ConnectSocket);
            WSACleanup();
            return FALSE;
        } // Send an initial buffer
        iResult = send( m_ConnectSocket, sendbuf, (int)strlen(sendbuf), 0 );
        if (iResult == SOCKET_ERROR)
    {
    strMessageTemp.Format(_T("send failed: %d\n"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
            closesocket(m_ConnectSocket);
            WSACleanup();
            return FALSE;
        } strMessageTemp.Format(_T("Bytes Sent: %d\n"), iResult);
    AfxMessageBox(strMessageTemp);    // Disable the function of sending since no more data will be sent
    iResult = shutdown(m_ConnectSocket, SD_SEND);
        if (iResult == SOCKET_ERROR) 
    {
    strMessageTemp.Format(_T("shutdown failed: %d\n"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
            closesocket(m_ConnectSocket);
            WSACleanup();
            return FALSE;
        }     // cleanup
        closesocket(m_ConnectSocket);
        WSACleanup();
    return TRUE;  // return TRUE  unless you set the focus to a control
    }2、消息函数
    LRESULT CsocketDlg::OnSocket(WPARAM wParam, LPARAM lParam)
    {
    int iResult;
    char recvbuf[DEFAULT_BUFLEN];
        int recvbuflen = DEFAULT_BUFLEN;
    CString strMessageTemp; if (wParam == 0 && lParam == 0) 
    return 0;  if (WSAGETSELECTERROR(lParam)) 

    //OnSocketClose(); 
    return 0; 
    }  switch (WSAGETSELECTEVENT(lParam)) 
    {
    case FD_CONNECT: 
    {
    //if (!InitThread(SelectModelMsgThread, (LPVOID)this)) 
    //break; 
    AfxMessageBox(_T("connecting..."));; 
    }
    break; case FD_CLOSE: 
    {
    AfxMessageBox(_T("close..."));; 
    }
    break; case FD_WRITE: 
    {
    AfxMessageBox(_T("send..."));; 
    }
    break; case FD_READ: 
    {
    AfxMessageBox(_T("read..."));;
    do { iResult = recv(m_ConnectSocket, recvbuf, recvbuflen, 0);
    if ( iResult > 0 )
    {
    strMessageTemp.Format(_T("Bytes received: %d\n"), iResult);
    AfxMessageBox(strMessageTemp);
    }
    else if ( iResult == 0 )
    AfxMessageBox(_T("Connection has been gracefully closed\n"));
    else
    {
    strMessageTemp.Format(_T("recv failed: %d\n"), WSAGetLastError());
    AfxMessageBox(strMessageTemp);
    } } while( iResult > 0 );
    }
    break; default: 
    break; 
    }
    // Receive until the peer closes the connection
    return 1;
    }结果:发送成功,接收部分不能触发。请教[happysheepherder],是什么问题?
      

  9.   

    WSAAsyncSelect本来就是异步模式,靠消息驱动,不需要多线程。
    MFC可以重载pretranslate函数实现
      

  10.   

    ON_MESSAGE(WM_CLIENT_ACCEPT,OnAccept)
    ON_MESSAGE(WM_CLIENT_READCLOSE,OnReadClose)你有没有消息映射
      

  11.   

    BEGIN_MESSAGE_MAP(CsocketDlg, CDialog)
    ON_WM_SYSCOMMAND()
    ON_WM_PAINT()
    ON_WM_QUERYDRAGICON()
    ON_MESSAGE(WM_SOCKET, OnSocket)
    //}}AFX_MSG_MAP
    END_MESSAGE_MAP()