如何使用winsock send()函数发送宽字符?

时间:2010-12-03 22:04:46

标签: c++ visual-studio-2010 visual-c++ winsock

它说here send函数需要const char *。

如何发送宽字符?我尝试了以下方法:

void MyClass::socksend(const wchar_t* wbuffer) {
   int i;
   char *buffer = (char *)malloc( MB_CUR_MAX );
   wctomb_s(&i,buffer, MB_CUR_MAX, (wchar_t)wbuffer);
   int buflen = strlen(buffer) + 2;
   char sendbuf[DEFAULT_BUFLEN];
   strcpy_s(sendbuf,buflen,buffer);
   sendbuf[buflen - 1] = '\n';
   int senderror = send(this->m_socket, sendbuf, buflen, 0);
   // error handling, etc goes here...

}

这不符合我的预期。它似乎没有向套接字发送任何内容。我该如何解决这个问题?

2 个答案:

答案 0 :(得分:0)

请注意,我不确定在套接字上传输宽字符串的正确方法,因此对于该部分,您可以自己动手。我知道它被描述为非常多毛和令人费解。 :) 考虑到这一点,如果套接字的另一端需要一个wchar_t字符串,你可以使用wcslen来获取wbuffer指向的字符串的长度,给你

int senderror = send( this->m_socket, (char *)wbuffer, wcslen( wbuffer ) * sizeof( wchar_t ), 0 );

您的代码中也存在一些可能的错误。 如果需要将wchar_t字符串转换为多字节,则应使用wcstombs_s而不是wctomb_s。 wctombs_s一次转换一个字符,而wcstombs_s转换字符串。

如果结果字符串长于DEFAULT_BUFLEN,您将最终使用'\ n'修改字符串并删除DEFAULT_BUFLEN以外的所有数据。

send并不总是发送整个缓冲区。您需要循环调用发送,直到发送完所有字节或者您达到某个时间限制或重试或耐心。

有关更多指导,请参阅here

答案 1 :(得分:0)

首先,广泛的角色是什么?它是一个比8位更宽的积分值;这意味着你必须处理Endianness。您需要将宽字符数组编码为char数组,然后将其作为char数组发送。在接收端,您需要将char数组解码为宽字符数组。

函数wctomb_s仅将单个宽字符编码为 char数组。您希望将宽字符数组编码为 char数组的函数是wcstombs_s。相应地,解码使用mbstowcs_s。

错误处理省略(未经测试):

void MyClass::socksend(const wchar_t* wbuffer) { 
   // determine the required buffer size
   size_t buffer_size;
   wcstombs_s(&buffer_size, NULL, 0, wbuffer, _TRUNCATE);

   // do the actual conversion
   char *buffer = (char*) malloc(buffer_size);
   wcstombs_s(&buffer_size, buffer, buffer_size, wbuffer, _TRUNCATE);

   // send the data
   size_t buffer_sent = 0;
   while (buffer_sent < buffer_size) {
       int sent_size = send(this->m_socket, buffer+buffer_sent, buffer_size-buffer_sent, 0);
       buffer_sent += sent_size;
   }

   // cleanup
   free(buffer);
}