喜欢写bug的猿 2019-01-08 17:32 采纳率: 0%
浏览 872

为什么在MFC中使用线程会出现程序崩溃?是我实用的方法不敌还是怎么回事?

在使用MFC中使用的线程是 API函数,调用CreateThread(); 可是使用的时候调试一步一步走都是正常的,但是一起运行就发现程序崩溃。我是一个初学的菜鸟,可能是代码有点乱,麻烦看一下!!!
谢谢各位大佬:


// UDPserver.cpp : 实现文件
//

#include "stdafx.h"
#include "ServerUDP.h"
#include "UDPserver.h"
#include <Winsock2.h>//加裁头文件 
#include <stdio.h>//加载标准输入输出头文件 
#define IDP_SOCKETS_INIT_FAILED            103
SOCKET m_revSocket;
// CUDPserver

CUDPserver::CUDPserver()
{
}

CUDPserver::~CUDPserver()
{
}


// CUDPserver 成员函数
// Server 成员函数
bool CUDPserver::Socket()//初始化
{
    //初始化Winscok
    if (!AfxSocketInit())
    {
        AfxMessageBox(IDP_SOCKETS_INIT_FAILED);
        return 1;
    }
    //  SetSockOpt();
    WORD wVersionRequested;//版本号 
    WSADATA wsaData; 
    int err; 
    wVersionRequested = MAKEWORD( 1, 1 );//1.1版本的套接字 
    err = WSAStartup( wVersionRequested, &wsaData ); 
    if ( err != 0 ) { 
        return false;
    }//加载套接字库,加裁失败则返回 
    if ( LOBYTE( wsaData.wVersion ) != 1 ||HIBYTE( wsaData.wVersion ) != 1 ) 
    { 
        WSACleanup( );
        return false; 
    }//如果不是1.1的则退出 
    return true;
}
#include"Set_up.h"
CSet_up up;
bool CUDPserver::GetLocalAddress(){



    CString strAddress;
    int nCardNo = 1;
    //PIP_ADAPTER_INFO结构体指针存储本机网卡信息
    PIP_ADAPTER_INFO pIpAdapterInfo = new IP_ADAPTER_INFO();
    //得到结构体大小,用于GetAdaptersInfo参数
    unsigned long stSize = sizeof(IP_ADAPTER_INFO);
    //调用GetAdaptersInfo函数,填充pIpAdapterInfo指针变量;其中stSize参数既是一个输入量也是一个输出量
    int nRel = GetAdaptersInfo(pIpAdapterInfo,&stSize);
    //记录网卡数量
    int netCardNum = 0;
    //记录每张网卡上的IP地址数量
    int IPnumPerNetCard = 0;
    if (ERROR_BUFFER_OVERFLOW == nRel)
    {
        //如果函数返回的是ERROR_BUFFER_OVERFLOW
        //则说明GetAdaptersInfo参数传递的内存空间不够,同时其传出stSize,表示需要的空间大小
        //这也是说明为什么stSize既是一个输入量也是一个输出量
        //释放原来的内存空间
        delete pIpAdapterInfo;
        //重新申请内存空间用来存储所有网卡信息
        pIpAdapterInfo = (PIP_ADAPTER_INFO)new BYTE[stSize];
        //再次调用GetAdaptersInfo函数,填充pIpAdapterInfo指针变量
        nRel=GetAdaptersInfo(pIpAdapterInfo,&stSize);    
    }
    if (ERROR_SUCCESS == nRel)
    {
        //输出网卡信息
        //可能有多网卡,因此通过循环去判断
        while (pIpAdapterInfo)
        {
            //可能网卡有多IP,因此通过循环去判断
            IP_ADDR_STRING *pIpAddrString =&(pIpAdapterInfo->IpAddressList);
            switch(pIpAdapterInfo->Type)
            {
            case MIB_IF_TYPE_OTHER:
            case MIB_IF_TYPE_ETHERNET:
            case MIB_IF_TYPE_TOKENRING:
            case MIB_IF_TYPE_FDDI:
            case MIB_IF_TYPE_PPP:
            case MIB_IF_TYPE_LOOPBACK:
            case MIB_IF_TYPE_SLIP:
                {
                    strAddress = pIpAddrString->IpAddress.String;
                    // 需要注意的是有时可能获取的IP地址是0.0.0.0,这时需要过滤掉
                    if(CString("0.0.0.0")==strAddress)
                        break;
                    //   std::cout<<_T("第")<< nCardNo<<_T("张网卡的IP地址是")<< strAddress<<std::endl;
                    //  long PID = _ttol(strAddress);  //CString 转成 char*,该语句缺一不
                    //   mxcj.m_strIP = (DWORD)PID; // 再强制转换成DWORD


                    m_DIP= strAddress;
                    nCardNo++;
                    break;
                }
            default:
                // 未知类型网卡就跳出
                break;
            }
            pIpAdapterInfo = pIpAdapterInfo->Next;
        }
    }
    //释放内存空间
    if (pIpAdapterInfo)
    {
        delete pIpAdapterInfo;
    }

    //initsocket();//创建套接字

    return true;
}
bool CUDPserver::initsocket()
{
    /*创建套接字*/
    //AF_INET表示IPv4,SOCK_STREAM数据传输方式,IPPROTO_TCP传输协议;
    m_listenSocket = socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
    if (m_listenSocket == INVALID_SOCKET)
    {
        //printf("套接字创建失败");
        WSACleanup();
        return 0;
    }
    Bind();
    return true;
}

bool CUDPserver::Bind()// 绑定地址端口
{
    sockaddr_in addrListen;
    addrListen.sin_family = AF_INET;     //指定IP格式
    addrListen.sin_port = htons(m_iDKH);   //绑定端口号
    addrListen.sin_addr.S_un.S_addr = INADDR_ANY;  //表示任何IP   service.sin_addr.s_addr = inet_addr("127.0.0.1");
    if (bind(m_listenSocket, (SOCKADDR*)&addrListen, sizeof(addrListen)) == SOCKET_ERROR)  //(SOCKADDR*)
    {
        //printf("绑定失败");
        closesocket(m_listenSocket);
        return 0;
    }

    Connect(); //连接开始监听
    return true;
}



unsigned int WINAPI ThreadProFunc(void *pParam);
bool CUDPserver::Connect() //连接
{
    /*开始监听*/
    if (listen(m_listenSocket, 5) == SOCKET_ERROR)
    {
        //printf("监听出错");
        closesocket(m_listenSocket);
        return 0;
    }
    /*等待连接,连接后建立一个新的套接字*/
    //SOCKET revSocket;  //对应此时所建立连接的套接字的句柄
    //HANDLE hThread;
//  DWORD dwThreadId;
    //sockaddr_in remoteAddr;   //接收连接到服务器上的地址信息
    //int remoteAddrLen = sizeof(remoteAddr);   
    //printf("等待连接...\n");
    /*等待客户端请求,服务器接收请求*/   
    //m_revSocket = accept(m_listenSocket, (SOCKADDR*)&remoteAddr, &remoteAddrLen);  //等待客户端接入,直到有客户端连接上来为止
    /*if (m_revSocket == INVALID_SOCKET)
    {

        closesocket(m_listenSocket);
        WSACleanup();
        return 0;
    }
    else
    {

        /* 启动等待连接线程 */
      HANDLE acceptThread = CreateThread(NULL, 0, WaitAcceptThread, (LPVOID)m_listenSocket, 0, NULL);




          WaitForSingleObject(acceptThread, INFINITE);  // 等待线程结束 
    //  return 0;
    //}


    return true;

}







unsigned int WINAPI ThreadProFunc(void *pParam)
{
    CUDPserver server;
    server.Receive();
    char revData[255] = "";
    while(1){
    /*通过建立的连接进行通信*/
    int res = recv(server.m_revSocket, revData, 255, 0);
    if (res > 0)
    {
        //printf("Bytes received: %d\n", res);
        //  server.m_wndOutputBuild.AddString(_T("调试输出正显示在此处。"));
        //printf("客户端发送的数据: %s\n", revData);
        return 0;
    }
        //sleep(1000);
        return 0;
}
}
UINT __cdecl CUDPserver::hellothread(LPVOID lparam){


    CUDPserver server;
    server.Receive();
    char revData[255] = "";
    while(1){
    /*通过建立的连接进行通信*/
    int res = recv(server.m_revSocket, revData, 255, 0);
    if (res > 0)
    {
        //printf("Bytes received: %d\n", res);
        //  server.m_wndOutputBuild.AddString(_T("调试输出正显示在此处。"));
        //printf("客户端发送的数据: %s\n", revData);
        return 0;
    }
        //sleep(1000);
        return 0;
}


}

HANDLE bufferMutex;
DWORD WINAPI WaitAcceptThread(LPVOID IpParameter)
{
    SOCKET m_socket = (SOCKET)IpParameter;
    // int rval;
    sockaddr_in remoteAddr;   //接收连接到服务器上的地址信息
    int remoteAddrLen = sizeof(remoteAddr); 
     while(true){
    /*等待客户端请求,服务器接收请求*/   
      m_revSocket = accept(m_socket, (SOCKADDR*)&remoteAddr, &remoteAddrLen);  //等待客户端接入,直到有客户端连接上来为止
            if (m_revSocket == INVALID_SOCKET)
    {
        //printf("客户端发出请求,服务器接收请求失败:\n",WSAGetLastError());
        closesocket(m_revSocket);
        WSACleanup();
        return 0;
    }
    HANDLE receiveThread = CreateThread(NULL, 0, RecMsgThread, (LPVOID)m_revSocket, 0, NULL);

     WaitForSingleObject(bufferMutex, INFINITE);
         if(NULL == receiveThread) {   
            //printf("\nCreatThread AnswerThread() failed.\n");   
         return 0;
        }   
         ReleaseSemaphore(bufferMutex, 1, NULL);

     }


}
DWORD WINAPI RecMsgThread(LPVOID IpParameter)
{
    SOCKET ClientSocket=(SOCKET)(LPVOID)IpParameter;
     int rval;
while(1)
    {

        char recvBuf[1024];  
        rval = recv(ClientSocket, recvBuf, 1024, 0);  
        WaitForSingleObject(bufferMutex, INFINITE);
        if (rval == SOCKET_ERROR)
        {
         //   printf("ONE Client Exit\n");
          //  vector<SOCKET>::iterator result = find(clientSocketGroup.begin(), clientSocketGroup.end(), ClientSocket);  
        //    clientSocketGroup.erase(result);  
        //    for (map<SOCKET, string>::iterator i=m_ipSocket.begin(); i!=m_ipSocket.end(); i++)  
         //   {  
         //       if (i->first == ClientSocket)  
         //       {  
                  //  printf("%s下线\n",m_ipSocket[ClientSocket].c_str());
         //           m_ipSocket.erase(i);
          //          break;
          //      }  
         //   }  
            closesocket(ClientSocket);  
            ReleaseSemaphore(bufferMutex, 1, NULL);
            break;
        }
        recvBuf;
        if(recvBuf[0] == -113){
            if(recvBuf[0]== -1){
            return 0;
            }

        }
      //  printf("%s Says: %s\n", m_ipSocket[ClientSocket].c_str(), recvBuf);     // 接收信息
        Sleep(1000);
        ReleaseSemaphore(bufferMutex, 1, NULL);
    }



  return 0;
}
  • 写回答

1条回答 默认 最新

  • CSDN-Ada助手 CSDN-AI 官方账号 2022-09-20 21:19
    关注
    不知道你这个问题是否已经解决, 如果还没有解决的话:

    如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^
    评论

报告相同问题?

悬赏问题

  • ¥15 名为“Product”的列已属于此 DataTable
  • ¥15 安卓adb backup备份应用数据失败
  • ¥15 eclipse运行项目时遇到的问题
  • ¥15 关于#c##的问题:最近需要用CAT工具Trados进行一些开发
  • ¥15 南大pa1 小游戏没有界面,并且报了如下错误,尝试过换显卡驱动,但是好像不行
  • ¥15 没有证书,nginx怎么反向代理到只能接受https的公网网站
  • ¥50 成都蓉城足球俱乐部小程序抢票
  • ¥15 yolov7训练自己的数据集
  • ¥15 esp8266与51单片机连接问题(标签-单片机|关键词-串口)(相关搜索:51单片机|单片机|测试代码)
  • ¥15 电力市场出清matlab yalmip kkt 双层优化问题