C++ CreateFileMapping错误代码8

C++ CreateFileMapping错误代码8,c++,winapi,memory,file-mapping,C++,Winapi,Memory,File Mapping,CreateFileMapping错误代码8。没有足够的存储空间来处理此命令。我试图在64位Win 10 Visual C++中创建4 GB(0xFFFFFFFF)的文件映射。 #define UBS_MEM_SIZE 0xffffffff HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, HIWORD(UBS_MEM_SIZE), LOWORD(UBS

CreateFileMapping错误代码8。没有足够的存储空间来处理此命令。我试图在64位Win 10 Visual C++中创建4 GB(0xFFFFFFFF)的文件映射。
#define UBS_MEM_SIZE 0xffffffff

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr,           
PAGE_READWRITE, HIWORD(UBS_MEM_SIZE), LOWORD(UBS_MEM_SIZE),     
TEXT("dllmemfilemap"));

如何解决这个“错误8”问题

HIWORD
LOWORD
用于从32位
DWORD
中提取16位高位和低位字<另一方面,code>CreateFileMapping需要两个DWORD组成一个64位无符号整数,即映射对象的大小

HIWORD(UBS\u MEM\u SIZE)
LOWORD(UBS\u MEM\u SIZE)
产生
0xffff
(两个16位的一半),然后将其转换为32位无符号整数(这是函数所期望的)

因此,您实际要做的是请求大小为
0x0000ffff0000ffff
的文件映射。这超过了
255 TB
。由于您使用的是
无效的\u句柄\u值
,因此必须由RAM或系统页面文件支持;我怀疑你那里有那么多可用的

如果
UBS\u MEM\u SIZE
始终为32位,则只需使用

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr,
   PAGE_READWRITE, 0, UBS_MEM_SIZE,
   TEXT("dllmemfilemap"));
如果您实际需要处理超过
4 GB的大小,可以执行以下操作:

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, 
   static_cast<DWORD>(UBS_MEM_SIZE >> 32), static_cast<DWORD>(UBS_MEM_SIZE), 
   TEXT("dllmemfilemap"));
inline HANDLE MyCreateMapping(unsigned long long size, LPCTSTR name)
{
   return CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE,
      static_cast<DWORD>(size >> 32), static_cast<DWORD>(size), name);
}
(顺便说一下,使用
const
…)

为了更安全,我会把电话包装成这样:

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, 
   static_cast<DWORD>(UBS_MEM_SIZE >> 32), static_cast<DWORD>(UBS_MEM_SIZE), 
   TEXT("dllmemfilemap"));
inline HANDLE MyCreateMapping(unsigned long long size, LPCTSTR name)
{
   return CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE,
      static_cast<DWORD>(size >> 32), static_cast<DWORD>(size), name);
}
内联句柄MyCreateMapping(无符号长大小,LPCTSTR名称)
{
返回CreateFileMapping(无效的\u句柄\u值、空ptr、页\u读写、,
静态(尺寸>>32)、静态(尺寸)、名称;
}

这样,您就不需要记住任何有关位、移位和整数类型大小的棘手细节。

HIWORD
LOWORD
用于从32位
DWORD
中提取16位高位和低位字<另一方面,code>CreateFileMapping
需要两个DWORD组成一个64位无符号整数,即映射对象的大小

   CreateFileMapping(..., HIWORD(UBS_MEM_SIZE), LOWORD(UBS_MEM_SIZE), ...)
HIWORD(UBS\u MEM\u SIZE)
LOWORD(UBS\u MEM\u SIZE)
产生
0xffff
(两个16位的一半),然后将其转换为32位无符号整数(这是函数所期望的)

因此,您实际要做的是请求大小为
0x0000ffff0000ffff
的文件映射。这超过了
255 TB
。由于您使用的是
无效的\u句柄\u值
,因此必须由RAM或系统页面文件支持;我怀疑你那里有那么多可用的

如果
UBS\u MEM\u SIZE
始终为32位,则只需使用

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr,
   PAGE_READWRITE, 0, UBS_MEM_SIZE,
   TEXT("dllmemfilemap"));
如果您实际需要处理超过
4 GB的大小,可以执行以下操作:

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, 
   static_cast<DWORD>(UBS_MEM_SIZE >> 32), static_cast<DWORD>(UBS_MEM_SIZE), 
   TEXT("dllmemfilemap"));
inline HANDLE MyCreateMapping(unsigned long long size, LPCTSTR name)
{
   return CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE,
      static_cast<DWORD>(size >> 32), static_cast<DWORD>(size), name);
}
(顺便说一下,使用
const
…)

为了更安全,我会把电话包装成这样:

HANDLE hMapObject = CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE, 
   static_cast<DWORD>(UBS_MEM_SIZE >> 32), static_cast<DWORD>(UBS_MEM_SIZE), 
   TEXT("dllmemfilemap"));
inline HANDLE MyCreateMapping(unsigned long long size, LPCTSTR name)
{
   return CreateFileMapping(INVALID_HANDLE_VALUE, nullptr, PAGE_READWRITE,
      static_cast<DWORD>(size >> 32), static_cast<DWORD>(size), name);
}
内联句柄MyCreateMapping(无符号长大小,LPCTSTR名称)
{
返回CreateFileMapping(无效的\u句柄\u值、空ptr、页\u读写、,
静态(尺寸>>32)、静态(尺寸)、名称;
}
这样,您就不需要记住关于位、移位和整数类型大小的任何棘手细节

   CreateFileMapping(..., HIWORD(UBS_MEM_SIZE), LOWORD(UBS_MEM_SIZE), ...)
LO/HIWORD宏生成一个16位值的字。您需要一个0xffff0000ffff内存映射文件。这是282TB。当前的x64处理器仅限于48位虚拟机地址,最多可达8 TB。所以是的,错误8(错误内存不足)是完全可以预料的

不要使用那些宏。您可以使用大整数作为替代:

LARGE_INTEGER size;
size.QuadPart = UBS_MEM_SIZE;
HANDLE hMapObject = CreateFileMapping(..., size.HighPart, size.LowPart, ...);
LO/HIWORD宏生成一个16位值的字。您需要一个0xffff0000ffff内存映射文件。这是282TB。当前的x64处理器仅限于48位虚拟机地址,最多可达8 TB。所以是的,错误8(错误内存不足)是完全可以预料的

不要使用那些宏。您可以使用大整数作为替代:

LARGE_INTEGER size;
size.QuadPart = UBS_MEM_SIZE;
HANDLE hMapObject = CreateFileMapping(..., size.HighPart, size.LowPart, ...);

您正在生成64位exe吗?是的,我尝试生成64位和86位,相同的错误。但这有关系吗?是的,因为不可能在32位程序中使用4Gb。您是如何确定16GB(或GiB?)的虚拟内存的?虚拟内存空间与已安装的RAM不对应。也就是说,错误8的含义是什么?VC IDE附带了一个错误查找工具,用它来找出错误!另外,使用此方法可以成功映射的最大大小是多少?我的错,在64位中有16 EB的虚拟内存。您正在生成64位exe吗?是的,我尝试生成64和86,相同的错误。但这有关系吗?是的,因为不可能在32位程序中使用4Gb。您是如何确定16GB(或GiB?)的虚拟内存的?虚拟内存空间与已安装的RAM不对应。也就是说,错误8的含义是什么?VC IDE附带了一个错误查找工具,用它来找出错误!另外,使用这种方法可以成功映射的最大大小是多少?糟糕,在64位中有16 EB的虚拟内存。Ty 4详细响应!TY4详细回复!