Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- _When_(return == 0, _Post_satisfies_(String->Buffer != NULL))
- NTSTATUS
- RWBAllocateUnicodeString(
- _Inout_ PUNICODE_STRING String
- )
- /*++
- Routine Description:
- This routine allocates a unicode string
- Arguments:
- Size - the size in bytes needed for the string buffer
- String - supplies the size of the string to be allocated in the MaximumLength field
- return the unicode string
- Return Value:
- STATUS_SUCCESS - success
- STATUS_INSUFFICIENT_RESOURCES - failure
- --*/
- {
- PAGED_CODE();
- String->Buffer = ExAllocatePoolWithTag(NonPagedPool,
- String->MaximumLength,
- RWB_STRING_TAG);
- if (String->Buffer == NULL) {
- PT_DBG_PRINT(PTDBG_TRACE_ROUTINES,
- ("[SimRep]: Failed to allocate unicode string of size 0x%x\n",
- String->MaximumLength));
- return STATUS_INSUFFICIENT_RESOURCES;
- }
- String->Length = 0;
- return STATUS_SUCCESS;
- }
- VOID
- RWBFreeUnicodeString(
- _Inout_ PUNICODE_STRING String
- )
- /*++
- Routine Description:
- This routine frees a unicode string
- Arguments:
- String - supplies the string to be freed
- Return Value:
- None
- --*/
- {
- PAGED_CODE();
- if (String->Buffer) {
- ExFreePoolWithTag(String->Buffer,
- RWB_STRING_TAG);
- String->Buffer = NULL;
- }
- String->Length = String->MaximumLength = 0;
- String->Buffer = NULL;
- }
- NTSTATUS
- RWBRollPath(
- _In_ UNICODE_STRING Path,
- _In_ PFLT_FILTER Filter,
- _In_ PFLT_INSTANCE Instance
- )
- /*
- Routine Description:
- This routine creates the directory specified as input
- Arguments:
- Path - The path to create
- Return Value:
- STATUS_SUCCESS - success
- */
- {
- NTSTATUS status = STATUS_SUCCESS;
- HANDLE directoryHandle = NULL;
- OBJECT_ATTRIBUTES objectAttributes;
- IO_STATUS_BLOCK ioStatusBlock;
- UNICODE_STRING previousFolder;
- // Initialize object attributes to set the path
- InitializeObjectAttributes(
- &objectAttributes,
- &Path,
- OBJ_CASE_INSENSITIVE,
- NULL,
- NULL
- );
- // Tries to create the directory.
- status = FltCreateFile(
- Filter,
- Instance,
- &directoryHandle,
- FILE_LIST_DIRECTORY | FILE_TRAVERSE,
- &objectAttributes,
- &ioStatusBlock,
- NULL,
- FILE_ATTRIBUTE_NORMAL,
- FILE_SHARE_READ | FILE_SHARE_WRITE,
- FILE_OPEN_IF,
- FILE_DIRECTORY_FILE,
- NULL,
- (ULONG) 0,
- IO_IGNORE_SHARE_ACCESS_CHECK
- );
- // If the directory already exists or it have been created, returns STATUS_SUCCESS
- if (ioStatusBlock.Information == FILE_OPENED || ioStatusBlock.Information == FILE_CREATED){
- status = STATUS_SUCCESS;
- goto RWBRollPathCleanup;
- }
- // If the create failed, it means that we have to create the previous directories and then try again to create this directory
- if (!NT_SUCCESS(status)){
- UNICODE_STRING finalComponent;
- // Get the final component of the name and creates a new string without
- // it in order to create the previous folder
- FltParseFileName(&Path,
- NULL,
- NULL,
- &finalComponent
- );
- previousFolder.MaximumLength = Path.Length - finalComponent.Length - sizeof(WCHAR);
- RWBAllocateUnicodeString(&previousFolder);
- RtlCopyMemory(
- previousFolder.Buffer,
- Path.Buffer,
- previousFolder.MaximumLength
- );
- previousFolder.Length = previousFolder.MaximumLength;
- // Creates the previous folders
- RWBRollPath(
- previousFolder,
- Filter,
- Instance
- );
- // TODO: check status
- // Tries to create the directory again. This time should not fail since the previous folder have been created
- status = FltCreateFile(
- Filter,
- Instance,
- &directoryHandle,
- FILE_LIST_DIRECTORY | FILE_TRAVERSE,
- &objectAttributes,
- &ioStatusBlock,
- NULL,
- FILE_ATTRIBUTE_NORMAL,
- FILE_SHARE_READ | FILE_SHARE_WRITE,
- FILE_OPEN_IF,
- FILE_DIRECTORY_FILE,
- NULL,
- (ULONG)0,
- IO_IGNORE_SHARE_ACCESS_CHECK
- );
- RWBFreeUnicodeString(&previousFolder);
- }
- RWBRollPathCleanup:
- if (directoryHandle != NULL)
- FltClose(directoryHandle);
- return status;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement