我正在为应用程序创建DLL。应用程序调用DLL并接收长度为8到50的字符串。
我遇到的问题是显示应用程序收到的任何消息的仅第一个字母。
以下是GetMethodVersion函数。
#include "stdafx.h"
STDAPI_(void) GetMethodVersion(LPTSTR out_strMethodVersion, int in_intSize)
{
if ((int)staticMethodVersion.length() > in_intSize)
return;
_tcscpy_s(out_strMethodVersion, 12, _T("Test"));
//staticMethodVersion should be insted of _T("Test")
}
项目设置设置为Unicode。 经过一些研究后我相信Unicode格式存在问题以及它的运作方式。感谢您提供任何帮助。
答案 0 :(得分:2)
您在问题中写道,项目设置是Unicode:这两个 DLL和调用EXE是否正确?确保它们都匹配。
在Unicode版本中,丑陋的TCHAR宏变为:
LPTSTR --> wchar_t*
_tcscpy_s --> wcscpy_s
_T("Test") --> L"Test"
所以你有:
STDAPI_(void) GetMethodVersion(wchar_t* out_strMethodVersion,
int in_intSize)
{
...
wcscpy_s(out_strMethodVersion, 12, L"Test");
}
您确定“幻数” 12是否正确? out_strMethodVersion
指向的目标字符串缓冲区的大小至少为12 wchar_t
s(包括终止NUL)?
然后,查看呼叫网站(您尚未展示)。
如何打印返回的字符串?也许您正在使用 ANSI char函数,因此返回的字符串被误解为为char*
ANSI字符串,因此第一个0x00
字节为Unicode UTF-16字符串在调用站点被误解为NUL终止符,并且字符串在打印时会在第一个字符处被截断?
Text: T e s t NUL
UTF-16 bytes: 54 00 65 00 73 00 74 00 00 00
(hex) **<--+
|
First 00 byte misinterpreted as
NUL terminator in char* ANSI string,
so only 'T' (the first character) gets printed.
修改强>
您在评论中澄清了以下事实:
我将DLL切换到ANSI,EXE显然也是如此,尽管exe被记录为Unicode。
让我认为EXE采用 UTF-8 Unicode编码。
就像在ANSI字符串中一样,UTF-8中的0x00
字节是字符串NUL终止符,因此先前对UTF-16 0x00
字节的分析(在wchar_t
中)< em>误解释作为字符串NUL终止符适用。
请注意,纯ASCII是UTF-8的正确子集:因此,如果您只使用纯ASCII字符(如"Test"
)并将其传递给EXE,则代码可能会起作用。
但是,如果记录的EXE使用Unicode UTF-8,您可能需要做正确的事并从DLL返回UTF-8字符串。
字符串是通过char*
返回的(与ANSI字符串一样),但重要的是确保 UTF-8 是DLL用来返回该字符串的编码,以避免将来出现微妙的错误。
虽然Windows API和Visual Studio中使用的一般术语是“Unicode”,但它实际上意味着在这些上下文中使用 UTF-16 Unicode编码。
但是,UTF-16并不是唯一可用的Unicode编码。例如,要在Internet上交换文本,广泛使用 UTF-8 编码。在您的情况下,听起来您的EXE期望Unicode UTF-8字符串。
答案 1 :(得分:0)
在#define UNICODE
之后到#include "stdafx.h"
已经很晚了。它应该在#include
本身的第一个stdafx.h
之前定义。但正确的方法是在项目属性中设置它(菜单Project&gt; Properties&gt; Configuration Properties&gt; General&gt; Character Set&gt;“Use Unicode Character Set”)。