• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            山寨:不是最好的,是最適合我們的!歡迎體驗山寨 中文版MSDN

            Blog @ Blog

            當華美的葉片落盡,生命的脈絡才歷歷可見。 -- 聶魯達

            常用鏈接

            統(tǒng)計

            積分與排名

            BBS

            Blog

            Web

            最新評論

            啟動服務流程代碼

            //主對話框啟動服務
            void CTCPUDPDlg::OnBtnStartServer() 

            //Server對話框繼承類CSocketComm的CreateSocket
            bool CServer::CreateSock(LPCTSTR strServerName, int nProtocol, int nType, UINT uOptions)

            //啟動服務,主要實現(xiàn)啟動套接字(socket();setsockopt();bind()(UDP服務端需要);listen()(TCP服務端需要禎聽);closesocket())
            bool CSocketComm::CreateSocket(LPCTSTR strServerName, int nProtocol, int nType, UINT uOptions)

            //啟動Socket線程
            bool CSocketComm::WatchServerSocket()

            UINT WINAPI CSocketComm::SocketServerThreadProc(LPVOID pParam)
            //服務端線程

            void CSocketComm::ServerRun()//Server主線程函數(shù)

            附主要函數(shù)流程具體代碼
            bool CSocketComm::CreateSocket(LPCTSTR strServerName, int nProtocol, int nType, UINT uOptions)
            {
                
            // 如果已經(jīng)打開,則返回false
                if ( IsOpen() )
                    
            return false;

                SOCKADDR_IN sockAddr 
            = 0 };
                
            //地址設定 //SOCKET
                SOCKET sock = socket(nProtocol, nType, 0);//unsigned int 0~4294967295 
                if (INVALID_SOCKET != sock)
                
            {
                    sockAddr.sin_port 
            = htons( GetPortNumber( strServerName ) );
                    
            if ( 0 != sockAddr.sin_port)
                    
            {
                        sockAddr.sin_addr.s_addr 
            = htonl( INADDR_ANY );
                        sockAddr.sin_family 
            = nProtocol;
                        
            if (uOptions & SO_REUSEADDR) //設定相關選項
                        {
                            BOOL optval 
            = TRUE;
                            
            if (SOCKET_ERROR == setsockopt( sock, SOL_SOCKET, SO_REUSEADDR,(char *&optval,sizeof( BOOL )))
                            
            {
                                closesocket( sock );
                                
            return false;
                            }

                        }

                        
            if (nType == SOCK_DGRAM) //如果是UDP協(xié)議
                        {
                            
            if (uOptions & SO_BROADCAST)//如果允許廣播
                            {
                                BOOL optval 
            = TRUE;
                                
            if (SOCKET_ERROR == setsockopt(sock,SOL_SOCKET,SO_BROADCAST,(char *&optval, sizeof(BOOL)))
                                
            {
                                    closesocket( sock );
                                    
            return false;
                                }

                                m_bBroadcast 
            = true;// 設定變量
                            }

                            m_hMutex 
            = CreateMutex(NULL, FALSE, NULL);// 如果需要廣播,則需要設定進程互斥
                            if (NULL == m_hMutex)
                            
            {
                                closesocket( sock );
                                
            return false;
                            }

                        }

                        
            if ( SOCKET_ERROR == bind(sock, (LPSOCKADDR)&sockAddr, sizeof(SOCKADDR_IN)))// 綁定一個本地地址
                        {
                            closesocket( sock );
                            m_bBroadcast 
            = false;
                            
            if (NULL != m_hMutex)
                                CloseHandle( m_hMutex );
                            m_hMutex 
            = NULL;
                            
            return false;
                        }

                        
            if (SOCK_STREAM == nType)// 如果是TCP連接
                        {
                            
            if ( SOCKET_ERROR == listen(sock, SOMAXCONN))
                            
            {
                                closesocket( sock );
                                
            return false;
                            }

                        }

                        m_hSocket 
            = (HANDLE) sock;// 保存socket
                        return true;
                    }

                    
            else
                        SetLastError(ERROR_INVALID_PARAMETER); 
            //不能找到端口
                    closesocket( sock );// 刪除socket
                    return false;
                }

                
            else//創(chuàng)建失敗
                {
                    CString strError;
                    strError.Format(
            "Create Socket Error Code : %d",GetLastError());//獲取錯誤代碼
                    return false;
                }

            }


            //啟動Socket線程
            BOOL CSocketComm::WatchServerSocket()
            {
                
            //首先判斷線程是否啟動
                if(!IsStart())
                
            {
                    
            //判斷是否打開通信,即socket是否成功創(chuàng)建
                    if(IsOpen())
                    
            {
                        HANDLE hThread;
                        UINT uiThreadId 
            = 0;
                        
            //啟動線程,使用_beginthreadex
                        hThread = (HANDLE)_beginthreadex(NULL,    // 安全參數(shù)
                                                            0,    // 堆棧
                                            SocketServerThreadProc,    // 線程程序
                                                        this,    // 線程參數(shù)
                                            CREATE_SUSPENDED,    //創(chuàng)建模式
                                                &uiThreadId);    // 線程ID
                        
            //如果線程不為空
                        if(hThread != NULL)
                        
            {
                            
            //繼續(xù)線程
                            ::ResumeThread(hThread);
                            m_hThread 
            = hThread;
                            
            return TRUE;
                        }

                    }

                }

                
            return false;
            }


            //服務端線程
            UINT WINAPI CSocketComm::SocketServerThreadProc(LPVOID pParam)
            {
                
            //reinterpret_cast用于各種指針的轉化
                CSocketComm* pThis = reinterpret_cast<CSocketComm*>(pParam);
                _ASSERTE( pThis 
            != NULL );

                pThis
            ->ServerRun();

                
            return 1L;
            }


            //Server主線程函數(shù),WaitForConnection()實際引用;
            void CSocketComm::ServerRun()
            {
                BYTE buffer[BUFFER_SIZE];
                DWORD dwBytes 
            = 0L;

                HANDLE hThread 
            = ::GetCurrentThread();
                DWORD dwTimeout 
            = DEFAULT_TIMEOUT;

                
            struct sockaddr_in ClientSockAddr; 
                
            int addrlen = sizeof(ClientSockAddr); 
                
                
            //int FAR* addrlen       
                
            //是否廣播模式
                if(!IsBroadCast())
                
            {
                    SOCKET sock 
            = (SOCKET) m_hSocket;
                    sock 
            = WaitForConnection(sock,(struct sockaddr *)&ClientSockAddr,&addrlen);//accept()
                    
            //等待新的連接
                    if(sock != INVALID_SOCKET)
                    
            {
                        
            //關閉連接
                        ShutDownConnection((SOCKET)m_hSocket);    //closesocket()
                        m_hSocket = (HANDLE) sock;
                        OnEvent(EVT_CONSUCCESS,ClientSockAddr);
            //connect
                    }

                    
            else
                    
            {
                        
            //如果已經(jīng)關閉則不發(fā)送事件,否則發(fā)送
                        if(IsOpen())
                            OnEvent(EVT_CONFAILURE,ClientSockAddr);
            //等待失敗
                        return;
                    }

                }

                
            //如果SOCKET 已經(jīng)創(chuàng)建
                while(IsOpen())
                
            {
                    
            //采用阻塞式SOCKET,等待事件通知
                    dwBytes = ReadComm(buffer,sizeof(buffer),dwTimeout);//recvfrom() or recv()
                    
            // 如果有錯誤發(fā)生
                    if (dwBytes == (DWORD)-1)
                    
            {
                        
            // 如果要關閉,則不發(fā)送事件
                        if (IsOpen())
                            OnEvent( EVT_CONDROP,ClientSockAddr ); 
            // 失去連接
                        break;
                    }

                    
            // 是否有數(shù)據(jù)收到
                    if (IsSmartAddressing() && dwBytes == sizeof(SOCKADDR_IN))
                        OnEvent( EVT_ZEROLENGTH ,ClientSockAddr);
                    
            else if (dwBytes > 0L)
                    
            {
                        OnDataReceived(buffer, dwBytes);
                    }

                    Sleep(
            0);
                }

            }


            //讀數(shù)據(jù)函數(shù)select();recvfrom();recv()
            DWORD CSocketComm::ReadComm(LPBYTE lpBuffer, DWORD dwSize, DWORD dwTimeout)
            {
                _ASSERTE(IsOpen());
                _ASSERTE(lpBuffer 
            != NULL);
                
            if(lpBuffer == NULL || dwSize<1L)
                    
            return 0L;

                fd_set fdRead 
            = {0};
                TIMEVAL stTime;
                TIMEVAL 
            *pstTime = NULL;

                
            if(INFINITE != dwTimeout)
                
            {
                    stTime.tv_sec
            =0;
                    stTime.tv_usec
            =dwTimeout*1000;
                    pstTime 
            = &stTime;
                }

                SOCKET s
            =(SOCKET)m_hSocket;
                
            //設定描述符
                if(!FD_ISSET(s,&fdRead))
                    FD_SET(s,
            &fdRead);

                
            //選擇函數(shù),設定超時時間
                DWORD dwBytesRead = 0L;
                
            int res = select(s+1,&fdRead,NULL,NULL,pstTime);
                
            if(res > 0)
                
            {
                    
            if(IsBroadCast() || IsSmartAddressing())
                    
            {
                        SOCKADDR_IN sockAddr 
            = {0};//獲得地址
                        int nOffset = IsSmartAddressing()?sizeof(sockAddr):0;
                        
            int nLen = sizeof(sockAddr);
                        
            if(dwSize < (DWORD)nLen)//緩沖區(qū)太小
                        {
                            ::SetLastError(ERROR_INVALID_USER_BUFFER);
                            
            return -1L;
                        }

                        
            //獲得數(shù)據(jù)
                        res = ::recvfrom(s,(LPSTR)&lpBuffer[nOffset],dwSize,0,(LPSOCKADDR)&sockAddr,&nLen);
                        
                        memset(
            &sockAddr.sin_addr,0,sizeof(sockAddr.sin_zero));
                        
            if(res>=0)
                        
            {
                            LockList();
            //鎖定地址列表
                            
            //刪除調重復地址
                            SockAddrIn sockin;
                            sockin.SetAddr(
            &sockAddr);
                            m_AddrList.remove(sockin);
                            m_AddrList.insert(m_AddrList.end(),sockin);

                            
            if(IsSmartAddressing())
                            
            {
                                memcpy(lpBuffer,
            &sockAddr,sizeof(sockAddr));
                                res
            +=sizeof(sockAddr);
                            }

                            UnlockList();
            //解開地址列表
                        }

                    }

                    
            else
                    
            {
                        res 
            = recv(s,(LPSTR)lpBuffer,dwSize,0);
                    }

                    dwBytesRead 
            = (DWORD)((res>0)?(res):(-1));
                }

                
                 
            return dwBytesRead;
            }

            posted on 2008-05-02 10:06 isabc 閱讀(717) 評論(0)  編輯 收藏 引用

            廣告信息(免費廣告聯(lián)系)

            中文版MSDN:
            歡迎體驗

            久久久一本精品99久久精品88| 国产91久久综合| 久久婷婷五月综合色奶水99啪 | 国产精品狼人久久久久影院| 久久久久久久综合综合狠狠| 久久久无码精品亚洲日韩京东传媒| 日本强好片久久久久久AAA | 久久综合九色综合网站| 国产高潮国产高潮久久久91 | 久久久久久久波多野结衣高潮 | 久久青青草视频| 中文字幕亚洲综合久久2| 亚洲精品无码久久久久去q| 国产高清美女一级a毛片久久w| 99久久精品国产一区二区| 久久综合九色综合久99| 色综合久久最新中文字幕| 麻豆亚洲AV永久无码精品久久 | 欧美va久久久噜噜噜久久| 亚洲伊人久久成综合人影院 | 热re99久久6国产精品免费| 久久久久国产一级毛片高清板| 色综合久久精品中文字幕首页| 久久久久亚洲AV成人片| 亚洲国产精品无码久久久秋霞2 | 国产精品久久久久…| 色欲综合久久中文字幕网| 久久热这里只有精品在线观看| 久久精品人妻一区二区三区| 青青草原综合久久大伊人精品| 亚洲va久久久噜噜噜久久| 色综合久久无码五十路人妻| 久久AV无码精品人妻糸列| 久久精品国产亚洲AV忘忧草18| 久久99热这里只频精品6| 少妇人妻综合久久中文字幕| 亚洲欧美成人久久综合中文网| 亚洲国产成人精品无码久久久久久综合| 亚洲乱亚洲乱淫久久| 国产精品欧美久久久久天天影视| 国产精品99久久久久久www|