2 * PROJECT: ReactOS Win32 Base API
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: dll/win32/kernel32/mem/section.c
5 * PURPOSE: Handles virtual memory APIs
6 * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org)
9 /* INCLUDES ******************************************************************/
16 /* FUNCTIONS *****************************************************************/
23 CreateFileMappingA(IN HANDLE hFile
,
24 IN LPSECURITY_ATTRIBUTES lpFileMappingAttributes
,
26 IN DWORD dwMaximumSizeHigh
,
27 IN DWORD dwMaximumSizeLow
,
32 PUNICODE_STRING UnicodeCache
;
33 LPCWSTR UnicodeName
= NULL
;
35 /* Check for a name */
39 UnicodeCache
= &NtCurrentTeb()->StaticUnicodeString
;
41 /* Convert to unicode */
42 RtlInitAnsiString(&AnsiName
, lpName
);
43 Status
= RtlAnsiStringToUnicodeString(UnicodeCache
, &AnsiName
, FALSE
);
44 if (!NT_SUCCESS(Status
))
46 /* Conversion failed */
47 SetLastErrorByStatus(Status
);
51 /* Otherwise, save the buffer */
52 UnicodeName
= (LPCWSTR
)UnicodeCache
->Buffer
;
55 /* Call the Unicode version */
56 return CreateFileMappingW(hFile
,
57 lpFileMappingAttributes
,
69 CreateFileMappingW(HANDLE hFile
,
70 LPSECURITY_ATTRIBUTES lpFileMappingAttributes
,
72 DWORD dwMaximumSizeHigh
,
73 DWORD dwMaximumSizeLow
,
78 OBJECT_ATTRIBUTES LocalAttributes
;
79 POBJECT_ATTRIBUTES ObjectAttributes
;
80 UNICODE_STRING SectionName
;
81 ACCESS_MASK DesiredAccess
;
82 LARGE_INTEGER LocalSize
;
83 PLARGE_INTEGER SectionSize
= NULL
;
86 /* Set default access */
87 DesiredAccess
= STANDARD_RIGHTS_REQUIRED
| SECTION_QUERY
| SECTION_MAP_READ
;
89 /* Get the attributes for the actual allocation and cleanup flProtect */
90 Attributes
= flProtect
& (SEC_FILE
| SEC_IMAGE
| SEC_RESERVE
| SEC_NOCACHE
| SEC_COMMIT
);
91 flProtect
^= Attributes
;
93 /* If the caller didn't say anything, assume SEC_COMMIT */
94 if (!Attributes
) Attributes
= SEC_COMMIT
;
96 /* Now check if the caller wanted write access */
97 if (flProtect
== PAGE_READWRITE
)
100 DesiredAccess
|= (SECTION_MAP_WRITE
| SECTION_MAP_READ
);
103 /* Now check if we got a name */
104 if (lpName
) RtlInitUnicodeString(&SectionName
, lpName
);
106 /* Now convert the object attributes */
107 ObjectAttributes
= BasepConvertObjectAttributes(&LocalAttributes
,
108 lpFileMappingAttributes
,
109 lpName
? &SectionName
: NULL
);
111 /* Check if we got a size */
112 if (dwMaximumSizeLow
|| dwMaximumSizeHigh
)
114 /* Use a LARGE_INTEGER and convert */
115 SectionSize
= &LocalSize
;
116 SectionSize
->LowPart
= dwMaximumSizeLow
;
117 SectionSize
->HighPart
= dwMaximumSizeHigh
;
120 /* Make sure the handle is valid */
121 if (hFile
== INVALID_HANDLE_VALUE
)
123 /* It's not, we'll only go on if we have a size */
127 /* No size, so this isn't a valid non-mapped section */
128 SetLastError(ERROR_INVALID_PARAMETER
);
133 /* Now create the actual section */
134 Status
= NtCreateSection(&SectionHandle
,
141 if (!NT_SUCCESS(Status
))
144 SetLastErrorByStatus(Status
);
148 /* Return the section */
149 return SectionHandle
;
157 MapViewOfFileEx(HANDLE hFileMappingObject
,
158 DWORD dwDesiredAccess
,
159 DWORD dwFileOffsetHigh
,
160 DWORD dwFileOffsetLow
,
161 SIZE_T dwNumberOfBytesToMap
,
162 LPVOID lpBaseAddress
)
165 LARGE_INTEGER SectionOffset
;
170 /* Convert the offset */
171 SectionOffset
.LowPart
= dwFileOffsetLow
;
172 SectionOffset
.HighPart
= dwFileOffsetHigh
;
174 /* Save the size and base */
175 ViewBase
= lpBaseAddress
;
176 ViewSize
= dwNumberOfBytesToMap
;
178 /* Convert flags to NT Protection Attributes */
179 if (dwDesiredAccess
& FILE_MAP_WRITE
)
181 Protect
= PAGE_READWRITE
;
183 else if (dwDesiredAccess
& FILE_MAP_READ
)
185 Protect
= PAGE_READONLY
;
187 else if (dwDesiredAccess
& FILE_MAP_COPY
)
189 Protect
= PAGE_WRITECOPY
;
193 Protect
= PAGE_NOACCESS
;
196 /* Map the section */
197 Status
= ZwMapViewOfSection(hFileMappingObject
,
207 if (!NT_SUCCESS(Status
))
210 SetLastErrorByStatus(Status
);
214 /* Return the base */
223 MapViewOfFile(HANDLE hFileMappingObject
,
224 DWORD dwDesiredAccess
,
225 DWORD dwFileOffsetHigh
,
226 DWORD dwFileOffsetLow
,
227 SIZE_T dwNumberOfBytesToMap
)
229 /* Call the extended API */
230 return MapViewOfFileEx(hFileMappingObject
,
234 dwNumberOfBytesToMap
,
243 UnmapViewOfFile(LPCVOID lpBaseAddress
)
247 /* Unmap the section */
248 Status
= NtUnmapViewOfSection(NtCurrentProcess(), (PVOID
)lpBaseAddress
);
249 if (!NT_SUCCESS(Status
))
252 SetLastErrorByStatus(Status
);
256 /* Otherwise, return sucess */
265 OpenFileMappingA(DWORD dwDesiredAccess
,
270 ANSI_STRING AnsiName
;
271 PUNICODE_STRING UnicodeCache
;
273 /* Check for a name */
277 UnicodeCache
= &NtCurrentTeb()->StaticUnicodeString
;
279 /* Convert to unicode */
280 RtlInitAnsiString(&AnsiName
, lpName
);
281 Status
= RtlAnsiStringToUnicodeString(UnicodeCache
, &AnsiName
, FALSE
);
282 if (!NT_SUCCESS(Status
))
284 /* Conversion failed */
285 SetLastErrorByStatus(Status
);
292 SetLastError(ERROR_INVALID_PARAMETER
);
296 /* Call the Unicode version */
297 return OpenFileMappingW(dwDesiredAccess
,
299 (LPCWSTR
)UnicodeCache
->Buffer
);
307 OpenFileMappingW(DWORD dwDesiredAccess
,
312 HANDLE SectionHandle
;
313 OBJECT_ATTRIBUTES ObjectAttributes
;
314 UNICODE_STRING UnicodeName
;
319 /* Otherwise, fail */
320 SetLastError(ERROR_INVALID_PARAMETER
);
324 /* Convert attributes */
325 RtlInitUnicodeString(&UnicodeName
, lpName
);
326 InitializeObjectAttributes(&ObjectAttributes
,
328 (bInheritHandle
? OBJ_INHERIT
: 0),
332 /* Convert COPY to READ */
333 if (dwDesiredAccess
== FILE_MAP_COPY
) dwDesiredAccess
= FILE_MAP_READ
;
335 /* Open the section */
336 Status
= ZwOpenSection(&SectionHandle
,
339 if (!NT_SUCCESS(Status
))
342 SetLastErrorByStatus(Status
);
346 /* Otherwise, return the handle */
347 return SectionHandle
;
355 FlushViewOfFile(LPCVOID lpBaseAddress
,
356 SIZE_T dwNumberOfBytesToFlush
)
358 SIZE_T NumberOfBytesToFlush
;
360 IO_STATUS_BLOCK IoStatusBlock
;
362 /* Save amount of bytes to flush to a local var */
363 NumberOfBytesToFlush
= dwNumberOfBytesToFlush
;
366 Status
= NtFlushVirtualMemory(NtCurrentProcess(),
367 (LPVOID
)lpBaseAddress
,
368 &NumberOfBytesToFlush
,
370 if (!NT_SUCCESS(Status
))
373 SetLastErrorByStatus(Status
);