Shared Memory Between User Mode and Kernel Mode
Asked Answered
F

1

9

I am writing some kernel side code for Windows7 to access shared memory created in user mode, as suggested here.
The shared memory is created in user space with name:

"MySharedMem"

Opening the shared memory in user space works.
Opening the same shared memory in kernel mode calling ZwOpenSection fails returning:

#define STATUS_OBJECT_NAME_NOT_FOUND     ((NTSTATUS)0xC0000034L)

The kernel code is:

NTSTATUS CModule1::OpenShared()
{
SIZE_T vs = 256;
WCHAR stringBuffer[] =  L"\\BaseNamedObjects\\MySharedMem";
UNICODE_STRING  sectionName;

RtlInitUnicodeString(&sectionName,stringBuffer);

OBJECT_ATTRIBUTES myAttributes;

InitializeObjectAttributes(&myAttributes,&sectionName,0,NULL,NULL);
NTSTATUS status0 = ZwOpenSection(&sectionHandle_,SECTION_MAP_READ|SECTION_MAP_WRITE,&myAttributes);

NTSTATUS status = ZwMapViewOfSection(&sectionHandle_, ZwCurrentProcess(), (PVOID *)&pSharedData_, 0, 0, NULL, &vs, ViewShare, 0, PAGE_READWRITE); 
return status;
}

I tried several names (L"\\MySharedMem" or L"MySharedMem") but I got other errors as STATUS_OBJECT_PATH_INVALID or STATUS_OBJECT_PATH_NOT_FOUND.
Also creating the shared memory as "Global\\MySharedMem" does not work.

What am I doing wrong?

I tried to create the shared memory in kernel mode, I get success on ZwCreateSection and ZwMapViewOfSection but i get access violation when I access the pSharedData_ pointer to test the buffer:

NTSTATUS CModule1::MapUserSection()
{
typedef struct SHARED_SECTION {DWORD i; };
NTSTATUS status = STATUS_SUCCESS;
ULONG Attributes=OBJ_KERNEL_HANDLE | OBJ_FORCE_ACCESS_CHECK;

OBJECT_ATTRIBUTES objectAttributes;
LARGE_INTEGER MaxSize;
SIZE_T ViewSize=sizeof(SHARED_SECTION);
MaxSize.QuadPart=sizeof(SHARED_SECTION);

WCHAR stringBuffer[] =  L"\\MySm2";
UNICODE_STRING  sectionName;
RtlInitUnicodeString(&sectionName,stringBuffer);
InitializeObjectAttributes(&objectAttributes,&sectionName,Attributes,NULL,NULL);

status= ZwCreateSection(&sectionHandle_,SECTION_ALL_ACCESS,&objectAttributes,&MaxSize,PAGE_READWRITE,SEC_COMMIT,NULL);
status = ZwMapViewOfSection(sectionHandle_, ZwCurrentProcess(), (PVOID *)&pSharedData_, 0, 0, NULL, &ViewSize, ViewShare, 0, PAGE_READWRITE); 

//To test the buffer
RtlFillMemory(pSharedData_, '1',ViewSize);
return status;
}

Everything fails...

Filament answered 15/9, 2015 at 21:25 Comment(4)
May be related, Every time I do something like this my names start with either "Local\\" or "Global\\", you may need to append "Local\\" to the front of your names.Orme
You would presumably need to use Global\MySharedMem when creating the file mapping. Once you've done that, use winobj (available from the MS web site) to look through the kernel namespace and find it.Loss
I tried this creating the shared memory in user space with Global\\MySharedMemame but in this case I get the error STATUS_OBJECT_PATH_SYNTAX_BAD 0xC000003BLFilament
What did winobj find?Loss
C
5

Concerning CreateFileMapping:

Creating a file mapping object in the global namespace from a session other than session zero requires the SeCreateGlobalPrivilege privilege.

From KB191840:

[T]he object is always mapped in the user address space (below 0x80000000) of a process (regardless of whether the object is created in kernel mode or user mode) the address is valid only if it is accessed in the context of the process.

The KB continues:

This method is not recommended and is used least by low-level device drivers because, as explained earlier, the scope of the address is limited to the process in which the object is mapped, and it cannot be accessed in a DPC or ISR. [Emphasis Mine]

The fix is either:

  1. Create the file mapping in kernel mode. (Suggested by the KB article.)
  2. Use IOCTL
Convalescence answered 15/9, 2015 at 22:49 Comment(3)
I tried to create the shared memory in kernel mode, but it fails when accessing the data pointer. I wiil try IOCTL.Filament
Now I understand your comment (x64): the object obj allocated in the driver has this address 0xffffe000d44ae510, while the shared memory pointer pSM is here at 0x000000e81bf20000. pSM address can not be accessed from obj in the kernel code.Filament
I found the sample code here that I assumed it was working...Filament

© 2022 - 2024 — McMap. All rights reserved.