2012-04-18 61 views
0

這是怎麼回事,希望你沒事! 嗯,問題是我正在做一個聊天客戶端/服務器應用程序,但做了一些與服務器的測試,我發現我有一個問題發送消息。我使用的是結構,插座和DWORD WINAPI線程... 所以在結構中的代碼是:結構和線程DWORD WINAPI

DWORD WINAPI threadSendMessages(LPVOID vpParam); //THREAD 
typedef struct messagesServerChat{ //STRUCT 

const char *messageServEnv; 

}MESSAGE, *SMESSAGES; 

然後在主方法我稱之爲結構使用爲const char messageServEnv,一個HeapAlloc到給一些內存到是要送我用來

char mServer[1024] = ""; //variable to pre-store the message 
SMESSAGES messages; //call the struct 
messages = (SMESSAGES) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(MESSAGE)); 

存儲消息在main方法的消息和char變量線程,我要求用戶插入他要發送消息和我使用結構來存儲消息並將其作爲參數發送給線程:

cout<<"Dear user, please insert your message: "; 

setbuf(stdin, NULL); 
fgets(mServer, 1024, stdin); 
messages->messageServEnv = mServer; 
DWORD hSend; //send the parameters to the thread function 
HANDLE sendThread = CreateThread(0, 0, threadSendMessages, mServer, 0, &hSend); 

終於線程代碼功能

DWORD WINAPI threadSendMessages(LPVOID lpParam){ 

SMESSAGES messages; 
messages = (SMESSAGES)lpParam; 
int mesa; 
mesa = send(sConnect, (char *)messages->messageServEnv, sizeof messages->messageServEnv, 0); 
//sConnect is the socket 
//messages = to use the struct, and messageServEnv is the struct data that should contain the message 
return 0; 
} 

- 編輯 - 我用雷米的解決方案解決了很多問題,但也許我失去了一些東西...在Thread threadSendMessages(SMESSAGES lpMessage)

char *ptr = messages->messageServEnv; 
int len = strlen(messages->messageServEnv); 

我得到和錯誤,指出消息的undifined,然後,我改成:

SMESSAGES messages; 
char *ptr = messages->messageServEnv; 
int len = strlen(messages->messageServEnv); 

現在我可以用消息和結構值messageServEnv但如果我開始調試Visual Studio和我嘗試發送一個消息,我得到說消息沒有被初始化使用了錯誤的話,我改變部分到

SMESSAGES messages = new MESSAGE; 

,現在我可以將消息發送到客戶端,但只有字符和垃圾代碼

+0

關於編輯,請參閱我的更新答案。 – 2012-04-19 08:39:36

回答

0

你需要動態分配的內存每封郵件的字符串數據,然後讓線程釋放內存發送完它時, 。

您也正在傳遞lpParameter參數CreateThread()的錯誤指針,您正在傳遞您的char[]緩衝區而不是您分配的MESSAGE結構。

您在致電send()時也正在使用sizeof()。由於messageServEnvchar*指針,因此sizeof()將返回4(32位)或8(64位),而不是指向的字符串的實際大小。

我建議直接移動char[]緩衝器入結構,而不是使用一個指針到外部緩衝器,例如:

typedef struct messagesServerChat 
{ 
    char messageServEnv[1024]; 
} 
MESSAGE, *SMESSAGES; 

DWORD WINAPI threadSendMessages(SMESSAGES lpMessage); 

cout << "Dear user, please insert your message: "; 
setbuf(stdin, NULL); 

SMESSAGES message = new MESSAGE; 
fgets(message->messageServEnv, sizeof(message->messageServEnv), stdin); 

DWORD hSend; 
HANDLE sendThread = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)&threadSendMessages, message, 0, &hSend); 
if (!sendThread) 
    delete message; 

DWORD WINAPI threadSendMessages(SMESSAGES lpMessage) 
{ 
    // send() is not guaranteed to send the entire message 
    // in one go, so call it in a loop... 

    char *ptr = lpMessage->messageServEnv; 
    int len = strlen(lpMessage->messageServEnv); // or sizeof() if you really want to send all 1024 bytes instead 

    while (len > 0) 
    { 
     int mesa = send(sConnect, ptr, len, 0); 
     if (mesa > 0) 
     { 
      ptr += mesa; 
      len -= mesa; 
      continue; 
     } 

     // this is only needed if you are using a non-blocking socket... 
     if ((mesa == SOCKET_ERROR) && (WSAGetLastError() == WSAEWOULDBLOCK)) 
     { 
      fd_set fd; 
      FD_ZERO(&fd); 
      FD_SET(sConnect, &fd); 

      timeval tv; 
      tv.tv_sec = 5; 
      tv.tv_usec = 0; 

      if (select(0, NULL, &fd, NULL, &tv) > 0) 
       continue; 
     } 

     ... error handling ... 
     break; 
    } 

    delete message; 
    return 0; 
} 

如果你想傳遞一個動態lengthed字符串,而不是,你是用的std::string代替char[]更好:

typedef struct messagesServerChat 
{ 
    std::string messageServEnv; 
} 
MESSAGE, *SMESSAGES; 

DWORD WINAPI threadSendMessages(SMESSAGES lpMessage); 

cout << "Dear user, please insert your message: "; 
setbuf(stdin, NULL); 

SMESSAGES message = new MESSAGE; 
getline(stdin, message->messageServEnv); 

DWORD hSend; 
HANDLE sendThread = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)&threadSendMessages, message, 0, &hSend); 
if (!sendThread) 
    delete message; 

DWORD WINAPI threadSendMessages(SMESSAGES lpMessage) 
{ 
    // send() is not guaranteed to send the entire message 
    // in one go, so call it in a loop... 

    char *ptr = lpMessage->messageServEnv.c_str(); 
    int len = lpMessage->messageServEnv.length(); // or sizeof() if you really want to send all 1024 bytes instead 

    while (len > 0) 
    { 
     int mesa = send(sConnect, ptr, len, 0); 
     if (mesa > 0) 
     { 
      ptr += mesa; 
      len -= mesa; 
      continue; 
     } 

     // this is only needed if you are using a non-blocking socket... 
     if ((mesa == SOCKET_ERROR) && (WSAGetLastError() == WSAEWOULDBLOCK)) 
     { 
      fd_set fd; 
      FD_ZERO(&fd); 
      FD_SET(sConnect, &fd); 

      timeval tv; 
      tv.tv_sec = 5; 
      tv.tv_usec = 0; 

      if (select(0, NULL, &fd, NULL, &tv) > 0) 
       continue; 
     } 

     ... error handling ... 
     break; 
    } 

    delete message; 
    return 0; 
} 
+0

什麼樣的錯誤?你需要更具體。請不要在評論中放置太多代碼,而是編輯原始問題。 – 2012-04-19 00:50:16

+0

對不起,我使用評論發送新的問題,我編輯了原來的問題與新的錯誤,我知道我錯過了代碼中的東西,因爲我可以發送消息,但只有垃圾代碼和一些符號 – Adrian87 2012-04-19 02:00:41

+0

我已糾正錯誤,我的代碼裏有一些拼寫錯誤。 – 2012-04-19 08:38:31