mirror of
https://github.com/reactos/reactos.git
synced 2025-07-31 11:31:40 +00:00
Git conversion: Make reactos the root directory, move rosapps, rostests, wallpapers into modules, and delete rossubsys.
This commit is contained in:
parent
b94e2d8ca0
commit
c2c66aff7d
24198 changed files with 0 additions and 37285 deletions
492
sdk/lib/rtl/memstream.c
Normal file
492
sdk/lib/rtl/memstream.c
Normal file
|
@ -0,0 +1,492 @@
|
|||
/*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS system libraries
|
||||
* FILE: lib/rtl/memstream.c
|
||||
* PURPOSE: MemoryStream functions
|
||||
* PROGRAMMER: David Quintana (gigaherz@gmail.com)
|
||||
*/
|
||||
|
||||
/* INCLUDES *******************************************************************/
|
||||
|
||||
#include <rtl.h>
|
||||
|
||||
#define NDEBUG
|
||||
#include <debug.h>
|
||||
|
||||
/* VIRTUAL METHOD TABLES ******************************************************/
|
||||
|
||||
const struct IStreamVtbl RtlMemoryStreamVtbl =
|
||||
{
|
||||
RtlQueryInterfaceMemoryStream,
|
||||
RtlAddRefMemoryStream,
|
||||
RtlReleaseMemoryStream,
|
||||
RtlReadMemoryStream,
|
||||
RtlWriteMemoryStream,
|
||||
RtlSeekMemoryStream,
|
||||
RtlSetMemoryStreamSize,
|
||||
RtlCopyMemoryStreamTo,
|
||||
RtlCommitMemoryStream,
|
||||
RtlRevertMemoryStream,
|
||||
RtlLockMemoryStreamRegion,
|
||||
RtlUnlockMemoryStreamRegion,
|
||||
RtlStatMemoryStream,
|
||||
RtlCloneMemoryStream,
|
||||
};
|
||||
|
||||
const struct IStreamVtbl RtlOutOfProcessMemoryStreamVtbl =
|
||||
{
|
||||
RtlQueryInterfaceMemoryStream,
|
||||
RtlAddRefMemoryStream,
|
||||
RtlReleaseMemoryStream,
|
||||
RtlReadOutOfProcessMemoryStream,
|
||||
RtlWriteMemoryStream,
|
||||
RtlSeekMemoryStream,
|
||||
RtlSetMemoryStreamSize,
|
||||
RtlCopyMemoryStreamTo,
|
||||
RtlCommitMemoryStream,
|
||||
RtlRevertMemoryStream,
|
||||
RtlLockMemoryStreamRegion,
|
||||
RtlUnlockMemoryStreamRegion,
|
||||
RtlStatMemoryStream,
|
||||
RtlCloneMemoryStream,
|
||||
};
|
||||
|
||||
/* FUNCTIONS ******************************************************************/
|
||||
|
||||
static
|
||||
PRTL_MEMORY_STREAM
|
||||
IStream_To_RTL_MEMORY_STREAM(
|
||||
_In_ IStream *Interface)
|
||||
{
|
||||
if (Interface == NULL)
|
||||
return NULL;
|
||||
|
||||
return CONTAINING_RECORD(Interface, RTL_MEMORY_STREAM, Vtbl);
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
VOID
|
||||
NTAPI
|
||||
RtlInitMemoryStream(
|
||||
_Out_ PRTL_MEMORY_STREAM Stream)
|
||||
{
|
||||
RtlZeroMemory(Stream, sizeof(RTL_MEMORY_STREAM));
|
||||
Stream->Vtbl = &RtlMemoryStreamVtbl;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
VOID
|
||||
NTAPI
|
||||
RtlInitOutOfProcessMemoryStream(
|
||||
_Out_ PRTL_MEMORY_STREAM Stream)
|
||||
{
|
||||
RtlZeroMemory(Stream, sizeof(RTL_MEMORY_STREAM));
|
||||
Stream->Vtbl = &RtlOutOfProcessMemoryStreamVtbl;
|
||||
Stream->FinalRelease = RtlFinalReleaseOutOfProcessMemoryStream;
|
||||
}
|
||||
|
||||
/*
|
||||
* @unimplemented
|
||||
*/
|
||||
VOID
|
||||
NTAPI
|
||||
RtlFinalReleaseOutOfProcessMemoryStream(
|
||||
_In_ PRTL_MEMORY_STREAM Stream)
|
||||
{
|
||||
UNIMPLEMENTED;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlQueryInterfaceMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_In_ REFIID RequestedIid,
|
||||
_Outptr_ PVOID *ResultObject)
|
||||
{
|
||||
if (IsEqualGUID(RequestedIid, &IID_IUnknown) ||
|
||||
IsEqualGUID(RequestedIid, &IID_ISequentialStream) ||
|
||||
IsEqualGUID(RequestedIid, &IID_IStream))
|
||||
{
|
||||
IStream_AddRef(This);
|
||||
*ResultObject = This;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
*ResultObject = NULL;
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
ULONG
|
||||
NTAPI
|
||||
RtlAddRefMemoryStream(
|
||||
_In_ IStream *This)
|
||||
{
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
|
||||
return InterlockedIncrement(&Stream->RefCount);
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
ULONG
|
||||
NTAPI
|
||||
RtlReleaseMemoryStream(
|
||||
_In_ IStream *This)
|
||||
{
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
LONG Result;
|
||||
|
||||
Result = InterlockedDecrement(&Stream->RefCount);
|
||||
|
||||
if (Result == 0)
|
||||
{
|
||||
if (Stream->FinalRelease)
|
||||
Stream->FinalRelease(Stream);
|
||||
}
|
||||
|
||||
return Result;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlReadMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_Out_writes_bytes_(Length) PVOID Buffer,
|
||||
_In_ ULONG Length,
|
||||
_Out_opt_ PULONG BytesRead)
|
||||
{
|
||||
ULONG CopyLength;
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
SIZE_T Available = (PUCHAR)Stream->End - (PUCHAR)Stream->Current;
|
||||
|
||||
if (BytesRead)
|
||||
*BytesRead = 0;
|
||||
|
||||
if (!Length)
|
||||
return S_OK;
|
||||
|
||||
CopyLength = min(Available, Length);
|
||||
|
||||
RtlMoveMemory(Buffer, Stream->Current, CopyLength);
|
||||
|
||||
Stream->Current = (PUCHAR)Stream->Current + CopyLength;
|
||||
|
||||
*BytesRead = CopyLength;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlReadOutOfProcessMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_Out_writes_bytes_(Length) PVOID Buffer,
|
||||
_In_ ULONG Length,
|
||||
_Out_opt_ PULONG BytesRead)
|
||||
{
|
||||
NTSTATUS Status;
|
||||
ULONG CopyLength;
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
SIZE_T Available = (PUCHAR)Stream->End - (PUCHAR)Stream->Current;
|
||||
|
||||
if (BytesRead)
|
||||
*BytesRead = 0;
|
||||
|
||||
if (!Length)
|
||||
return S_OK;
|
||||
|
||||
CopyLength = min(Available, Length);
|
||||
|
||||
Status = NtReadVirtualMemory(Stream->ProcessHandle,
|
||||
Stream->Current,
|
||||
Buffer,
|
||||
CopyLength,
|
||||
BytesRead);
|
||||
|
||||
if (NT_SUCCESS(Status))
|
||||
Stream->Current = (PUCHAR)Stream->Current + *BytesRead;
|
||||
|
||||
return HRESULT_FROM_WIN32(RtlNtStatusToDosError(Status));
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlSeekMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_In_ LARGE_INTEGER RelativeOffset,
|
||||
_In_ ULONG Origin,
|
||||
_Out_opt_ PULARGE_INTEGER ResultOffset)
|
||||
{
|
||||
PVOID NewPosition;
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
|
||||
switch (Origin)
|
||||
{
|
||||
case STREAM_SEEK_SET:
|
||||
NewPosition = (PUCHAR)Stream->Start + RelativeOffset.QuadPart;
|
||||
break;
|
||||
|
||||
case STREAM_SEEK_CUR:
|
||||
NewPosition = (PUCHAR)Stream->Current + RelativeOffset.QuadPart;
|
||||
break;
|
||||
|
||||
case STREAM_SEEK_END:
|
||||
NewPosition = (PUCHAR)Stream->End - RelativeOffset.QuadPart;
|
||||
break;
|
||||
|
||||
default:
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (NewPosition < Stream->Start || NewPosition > Stream->End)
|
||||
return STG_E_INVALIDPOINTER;
|
||||
|
||||
Stream->Current = NewPosition;
|
||||
|
||||
if (ResultOffset)
|
||||
ResultOffset->QuadPart = (PUCHAR)Stream->Current - (PUCHAR)Stream->Start;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlCopyMemoryStreamTo(
|
||||
_In_ IStream *This,
|
||||
_In_ IStream *Target,
|
||||
_In_ ULARGE_INTEGER Length,
|
||||
_Out_opt_ PULARGE_INTEGER BytesRead,
|
||||
_Out_opt_ PULARGE_INTEGER BytesWritten)
|
||||
{
|
||||
CHAR Buffer[1024];
|
||||
ULONGLONG TotalSize;
|
||||
ULONG Left, Amount;
|
||||
HRESULT Result;
|
||||
|
||||
if (BytesRead)
|
||||
BytesRead->QuadPart = 0;
|
||||
if (BytesWritten)
|
||||
BytesWritten->QuadPart = 0;
|
||||
|
||||
if (!Target)
|
||||
return S_OK;
|
||||
|
||||
if (!Length.QuadPart)
|
||||
return S_OK;
|
||||
|
||||
/* Copy data */
|
||||
TotalSize = Length.QuadPart;
|
||||
while (TotalSize)
|
||||
{
|
||||
Left = (ULONG)min(TotalSize, sizeof(Buffer));
|
||||
|
||||
/* Read */
|
||||
Result = IStream_Read(This, Buffer, Left, &Amount);
|
||||
if (BytesRead)
|
||||
BytesRead->QuadPart += Amount;
|
||||
if (FAILED(Result) || Amount == 0)
|
||||
break;
|
||||
|
||||
Left = Amount;
|
||||
|
||||
/* Write */
|
||||
Result = IStream_Write(Target, Buffer, Left, &Amount);
|
||||
if (BytesWritten)
|
||||
BytesWritten->QuadPart += Amount;
|
||||
if (FAILED(Result) || Amount != Left)
|
||||
break;
|
||||
|
||||
TotalSize -= Left;
|
||||
}
|
||||
return Result;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlStatMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_Out_ STATSTG *Stats,
|
||||
_In_ ULONG Flags)
|
||||
{
|
||||
PRTL_MEMORY_STREAM Stream = IStream_To_RTL_MEMORY_STREAM(This);
|
||||
|
||||
if (!Stats)
|
||||
return STG_E_INVALIDPOINTER;
|
||||
|
||||
RtlZeroMemory(Stats, sizeof(STATSTG));
|
||||
Stats->type = STGTY_STREAM;
|
||||
Stats->cbSize.QuadPart = (PUCHAR)Stream->End - (PUCHAR)Stream->Start;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
/* DUMMY FUNCTIONS ************************************************************/
|
||||
/*
|
||||
* The following functions return E_NOTIMPL in Windows Server 2003.
|
||||
*/
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlWriteMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_In_reads_bytes_(Length) CONST VOID *Buffer,
|
||||
_In_ ULONG Length,
|
||||
_Out_opt_ PULONG BytesWritten)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(Buffer);
|
||||
UNREFERENCED_PARAMETER(Length);
|
||||
UNREFERENCED_PARAMETER(BytesWritten);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlSetMemoryStreamSize(
|
||||
_In_ IStream *This,
|
||||
_In_ ULARGE_INTEGER NewSize)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(NewSize);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlCommitMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_In_ ULONG CommitFlags)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(CommitFlags);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlRevertMemoryStream(
|
||||
_In_ IStream *This)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlLockMemoryStreamRegion(
|
||||
_In_ IStream *This,
|
||||
_In_ ULARGE_INTEGER Offset,
|
||||
_In_ ULARGE_INTEGER Length,
|
||||
_In_ ULONG LockType)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(Offset);
|
||||
UNREFERENCED_PARAMETER(Length);
|
||||
UNREFERENCED_PARAMETER(LockType);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlUnlockMemoryStreamRegion(
|
||||
_In_ IStream *This,
|
||||
_In_ ULARGE_INTEGER Offset,
|
||||
_In_ ULARGE_INTEGER Length,
|
||||
_In_ ULONG LockType)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(Offset);
|
||||
UNREFERENCED_PARAMETER(Length);
|
||||
UNREFERENCED_PARAMETER(LockType);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
HRESULT
|
||||
NTAPI
|
||||
RtlCloneMemoryStream(
|
||||
_In_ IStream *This,
|
||||
_Outptr_ IStream **ResultStream)
|
||||
{
|
||||
UNREFERENCED_PARAMETER(This);
|
||||
UNREFERENCED_PARAMETER(ResultStream);
|
||||
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
/*
|
||||
* @implemented
|
||||
*/
|
||||
NTSTATUS
|
||||
NTAPI
|
||||
RtlCopyMappedMemory(
|
||||
_Out_writes_bytes_all_(Size) PVOID Destination,
|
||||
_In_reads_bytes_(Size) const VOID *Source,
|
||||
_In_ SIZE_T Size)
|
||||
{
|
||||
NTSTATUS Status = STATUS_SUCCESS;
|
||||
_SEH2_TRY
|
||||
{
|
||||
RtlCopyMemory(Destination, Source, Size);
|
||||
}
|
||||
_SEH2_EXCEPT(_SEH2_GetExceptionCode() == STATUS_IN_PAGE_ERROR
|
||||
? EXCEPTION_EXECUTE_HANDLER
|
||||
: EXCEPTION_CONTINUE_SEARCH)
|
||||
{
|
||||
Status = _SEH2_GetExceptionCode();
|
||||
}
|
||||
_SEH2_END;
|
||||
return Status;
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue