#include <iostream>
#include <WS2tcpip.h>
#include "sharedmemory.h"
#pragma comment (lib, "ws2_32.lib")
using namespace std;
#define MAP_OBJECT_NAME "$pcars2$"
void main(int argc, char* argv[])
{
HANDLE fileHandle = OpenFileMapping(PAGE_READONLY, FALSE, MAP_OBJECT_NAME);
I am relatively new to C++, and I happened across this road block. When I'm trying to place any #define
into an argument like on the OpenFileMapping()
line, I get an error saying:
C++ argument of type is incompatible with parameter of type
My end goal with this program is to send a UDP message that grabs data from shared memory.
Is this a result of me using void
instead of int
? I don't know.
TCHAR
is defined as either wchar_t
or char
, depending on whether UNICODE
has been defined or not in your project setup, respectively.
OpenFileMapping()
is a TCHAR
-based preprocessor macro. It is defined as taking a const TCHAR*
pointer to a null-terminated string in its 3rd parameter.
In reality, what happens is that OpenFileMapping()
maps to either the OpenFileMappingA()
(ANSI) or OpenFileMappingW()
(Unicode) function, depending on whether UNICODE
is defined:
// in winbase.h
WINBASEAPI
__out
HANDLE
WINAPI
OpenFileMappingA(
__in DWORD dwDesiredAccess,
__in BOOL bInheritHandle,
__in LPCSTR lpName
);
WINBASEAPI
__out
HANDLE
WINAPI
OpenFileMappingW(
__in DWORD dwDesiredAccess,
__in BOOL bInheritHandle,
__in LPCWSTR lpName
);
#ifdef UNICODE
#define OpenFileMapping OpenFileMappingW
#else
#define OpenFileMapping OpenFileMappingA
#endif // !UNICODE
Most legacy Win32 APIs that deal with character data are separated into A
and W
versions like this. Newer APIs introduced in recent years tend to be Unicode-only.
In your case, UNICODE
is defined, so you are trying to pass a narrow string literal (const char[]
) where a Unicode string (const wchar_t*
) is expected. That is why you are getting a type mismatch error.
When using character/string literals with TCHAR
-based APIs, use the TEXT()
macro to ensure the literal uses the correct character type that TCHAR
actually maps to, eg:
#include <iostream>
#include <WS2tcpip.h>
#include "sharedmemory.h"
#pragma comment (lib, "ws2_32.lib")
using namespace std;
#define MAP_OBJECT_NAME TEXT("$pcars2$") // <-- HERE
void main(int argc, char* argv[])
{
HANDLE fileHandle = OpenFileMapping(PAGE_READONLY, FALSE, MAP_OBJECT_NAME);
Which is effectively doing the following when UNICODE
is defined:
#include <iostream>
#include <WS2tcpip.h>
#include "sharedmemory.h"
#pragma comment (lib, "ws2_32.lib")
using namespace std;
#define MAP_OBJECT_NAME L"$pcars2$"
void main(int argc, char* argv[])
{
HANDLE fileHandle = OpenFileMappingW(PAGE_READONLY, FALSE, MAP_OBJECT_NAME);
And doing this when UNICODE
is not defined:
#include <iostream>
#include <WS2tcpip.h>
#include "sharedmemory.h"
#pragma comment (lib, "ws2_32.lib")
using namespace std;
#define MAP_OBJECT_NAME "$pcars2$"
void main(int argc, char* argv[])
{
HANDLE fileHandle = OpenFileMappingA(PAGE_READONLY, FALSE, MAP_OBJECT_NAME);
However, modern coding practices should not rely on TCHAR
APIs at all. They are meant for backwards compatibility with legacy Win9x/ME code during Microsoft's push to migrate users to adopt Unicode in the early 2000s. You should use the ANSI or Unicode functions directly instead as needed.