Author: jmorlan
Date: Fri Jun 4 08:36:12 2010
New Revision: 47562
URL:
http://svn.reactos.org/svn/reactos?rev=47562&view=rev
Log:
[KERNEL32], [WIN32CSR]
- Make Get/SetConsoleTitle more compatible with windows; in particular, transfer title via
capture buffer to allow for longer titles.
- Tighten up capture buffer validation in win32csr.
Modified:
trunk/reactos/dll/win32/kernel32/misc/console.c
trunk/reactos/include/reactos/subsys/csrss/csrss.h
trunk/reactos/subsystems/win32/csrss/win32csr/alias.c
trunk/reactos/subsystems/win32/csrss/win32csr/coninput.c
trunk/reactos/subsystems/win32/csrss/win32csr/conoutput.c
trunk/reactos/subsystems/win32/csrss/win32csr/console.c
trunk/reactos/subsystems/win32/csrss/win32csr/dllmain.c
trunk/reactos/subsystems/win32/csrss/win32csr/win32csr.h
Modified: trunk/reactos/dll/win32/kernel32/misc/console.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/kernel32/misc/co…
==============================================================================
--- trunk/reactos/dll/win32/kernel32/misc/console.c [iso-8859-1] (original)
+++ trunk/reactos/dll/win32/kernel32/misc/console.c [iso-8859-1] Fri Jun 4 08:36:12 2010
@@ -3418,6 +3418,64 @@
}
+static DWORD
+IntGetConsoleTitle(LPVOID lpConsoleTitle, DWORD nSize, BOOL bUnicode)
+{
+ CSR_API_MESSAGE Request;
+ PCSR_CAPTURE_BUFFER CaptureBuffer;
+ ULONG CsrRequest = MAKE_CSR_API(GET_TITLE, CSR_CONSOLE);
+ NTSTATUS Status;
+
+ if (nSize == 0)
+ return 0;
+
+ Request.Data.GetTitleRequest.Length = nSize * (bUnicode ? 1 : sizeof(WCHAR));
+ CaptureBuffer = CsrAllocateCaptureBuffer(1, Request.Data.GetTitleRequest.Length);
+ if (CaptureBuffer == NULL)
+ {
+ SetLastError(ERROR_NOT_ENOUGH_MEMORY);
+ return 0;
+ }
+
+ CsrAllocateMessagePointer(CaptureBuffer,
+ Request.Data.GetTitleRequest.Length,
+ (PVOID*)&Request.Data.GetTitleRequest.Title);
+
+ Status = CsrClientCallServer(&Request, CaptureBuffer, CsrRequest,
sizeof(CSR_API_MESSAGE));
+ if (!NT_SUCCESS(Status) || !(NT_SUCCESS(Status = Request.Status)))
+ {
+ CsrFreeCaptureBuffer(CaptureBuffer);
+ SetLastErrorByStatus(Status);
+ return 0;
+ }
+
+ if (bUnicode)
+ {
+ if (nSize >= sizeof(WCHAR))
+ wcscpy((LPWSTR)lpConsoleTitle, Request.Data.GetTitleRequest.Title);
+ }
+ else
+ {
+ if (nSize < Request.Data.GetTitleRequest.Length / sizeof(WCHAR) ||
+ !WideCharToMultiByte(CP_ACP, // ANSI code page
+ 0, // performance and mapping flags
+ Request.Data.GetTitleRequest.Title, // address of
wide-character string
+ -1, // number of characters in string
+ (LPSTR)lpConsoleTitle, // address of buffer for new
string
+ nSize, // size of buffer
+ NULL, // FAST
+ NULL))
+ {
+ /* Yes, if the buffer isn't big enough, it returns 0... Bad API */
+ *(LPSTR)lpConsoleTitle = '\0';
+ Request.Data.GetTitleRequest.Length = 0;
+ }
+ }
+ CsrFreeCaptureBuffer(CaptureBuffer);
+
+ return Request.Data.GetTitleRequest.Length / sizeof(WCHAR);
+}
+
/*--------------------------------------------------------------
* GetConsoleTitleW
*
@@ -3428,48 +3486,8 @@
GetConsoleTitleW(LPWSTR lpConsoleTitle,
DWORD nSize)
{
- PCSR_API_MESSAGE Request;
- ULONG CsrRequest;
- NTSTATUS Status;
-
- Request = RtlAllocateHeap(RtlGetProcessHeap(),
- 0,
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_GET_TITLE) +
CSRSS_MAX_TITLE_LENGTH * sizeof(WCHAR));
- if (Request == NULL)
- {
- SetLastError(ERROR_NOT_ENOUGH_MEMORY);
- return FALSE;
- }
-
- CsrRequest = MAKE_CSR_API(GET_TITLE, CSR_CONSOLE);
-
- Status = CsrClientCallServer(Request,
- NULL,
- CsrRequest,
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_GET_TITLE) +
CSRSS_MAX_TITLE_LENGTH * sizeof(WCHAR));
- if (!NT_SUCCESS(Status) || !(NT_SUCCESS(Status = Request->Status)))
- {
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
- SetLastErrorByStatus(Status);
- return 0;
- }
-
- if (nSize * sizeof(WCHAR) <= Request->Data.GetTitleRequest.Length)
- {
- nSize--;
- }
- else
- {
- nSize = Request->Data.GetTitleRequest.Length / sizeof (WCHAR);
- }
- memcpy(lpConsoleTitle, Request->Data.GetTitleRequest.Title, nSize *
sizeof(WCHAR));
- lpConsoleTitle[nSize] = L'\0';
-
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
-
- return nSize;
-}
-
+ return IntGetConsoleTitle(lpConsoleTitle, nSize, TRUE);
+}
/*--------------------------------------------------------------
* GetConsoleTitleA
@@ -3483,28 +3501,7 @@
GetConsoleTitleA(LPSTR lpConsoleTitle,
DWORD nSize)
{
- WCHAR WideTitle [CSRSS_MAX_TITLE_LENGTH + 1];
- DWORD nWideTitle = CSRSS_MAX_TITLE_LENGTH + 1;
- DWORD nWritten;
-
- if (!lpConsoleTitle || !nSize) return 0;
- nWideTitle = GetConsoleTitleW((LPWSTR) WideTitle, nWideTitle);
- if (!nWideTitle) return 0;
-
- if ((nWritten = WideCharToMultiByte(CP_ACP, // ANSI code page
- 0, // performance and mapping flags
- (LPWSTR) WideTitle, // address of wide-character
string
- nWideTitle, // number of characters in string
- lpConsoleTitle, // address of buffer for new
string
- nSize - 1, // size of buffer
- NULL, // FAST
- NULL))) // FAST
- {
- lpConsoleTitle[nWritten] = '\0';
- return nWritten;
- }
-
- return 0;
+ return IntGetConsoleTitle(lpConsoleTitle, nSize, FALSE);
}
@@ -3517,40 +3514,32 @@
WINAPI
SetConsoleTitleW(LPCWSTR lpConsoleTitle)
{
- PCSR_API_MESSAGE Request;
- ULONG CsrRequest;
- NTSTATUS Status;
- unsigned int c;
-
- Request = RtlAllocateHeap(RtlGetProcessHeap(), 0,
- max(sizeof(CSR_API_MESSAGE),
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) +
- min(wcslen(lpConsoleTitle), CSRSS_MAX_TITLE_LENGTH) *
sizeof(WCHAR)));
- if (Request == NULL)
+ CSR_API_MESSAGE Request;
+ PCSR_CAPTURE_BUFFER CaptureBuffer;
+ ULONG CsrRequest = MAKE_CSR_API(SET_TITLE, CSR_CONSOLE);
+ NTSTATUS Status;
+
+ Request.Data.SetTitleRequest.Length = wcslen(lpConsoleTitle) * sizeof(WCHAR);
+
+ CaptureBuffer = CsrAllocateCaptureBuffer(1, Request.Data.SetTitleRequest.Length);
+ if (CaptureBuffer == NULL)
{
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
return FALSE;
}
- CsrRequest = MAKE_CSR_API(SET_TITLE, CSR_CONSOLE);
-
- for (c = 0; lpConsoleTitle[c] && c < CSRSS_MAX_TITLE_LENGTH; c++)
- Request->Data.SetTitleRequest.Title[c] = lpConsoleTitle[c];
-
- Request->Data.SetTitleRequest.Length = c * sizeof(WCHAR);
- Status = CsrClientCallServer(Request,
- NULL,
- CsrRequest,
- max(sizeof(CSR_API_MESSAGE),
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) + c *
sizeof(WCHAR)));
- if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request->Status))
- {
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
+ CsrCaptureMessageBuffer(CaptureBuffer,
+ (PVOID)lpConsoleTitle,
+ Request.Data.SetTitleRequest.Length,
+ (PVOID*)&Request.Data.SetTitleRequest.Title);
+
+ Status = CsrClientCallServer(&Request, CaptureBuffer, CsrRequest,
sizeof(CSR_API_MESSAGE));
+ CsrFreeCaptureBuffer(CaptureBuffer);
+ if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request.Status))
+ {
SetLastErrorByStatus(Status);
- return(FALSE);
- }
-
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
+ return FALSE;
+ }
return TRUE;
}
@@ -3567,43 +3556,18 @@
WINAPI
SetConsoleTitleA(LPCSTR lpConsoleTitle)
{
- PCSR_API_MESSAGE Request;
- ULONG CsrRequest;
- NTSTATUS Status;
- unsigned int c;
-
- Request = RtlAllocateHeap(RtlGetProcessHeap(),
- 0,
- max(sizeof(CSR_API_MESSAGE),
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) +
- min(strlen(lpConsoleTitle), CSRSS_MAX_TITLE_LENGTH) *
sizeof(WCHAR)));
- if (Request == NULL)
+ ULONG Length = strlen(lpConsoleTitle) + 1;
+ LPWSTR WideTitle = HeapAlloc(GetProcessHeap(), 0, Length * sizeof(WCHAR));
+ BOOL Ret;
+ if (!WideTitle)
{
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
return FALSE;
}
-
- CsrRequest = MAKE_CSR_API(SET_TITLE, CSR_CONSOLE);
-
- for (c = 0; lpConsoleTitle[c] && c < CSRSS_MAX_TITLE_LENGTH; c++)
- Request->Data.SetTitleRequest.Title[c] = lpConsoleTitle[c];
-
- Request->Data.SetTitleRequest.Length = c * sizeof(WCHAR);
- Status = CsrClientCallServer(Request,
- NULL,
- CsrRequest,
- max(sizeof(CSR_API_MESSAGE),
- CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) + c *
sizeof(WCHAR)));
- if (!NT_SUCCESS(Status) || !NT_SUCCESS(Status = Request->Status))
- {
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
- SetLastErrorByStatus(Status);
- return(FALSE);
- }
-
- RtlFreeHeap(RtlGetProcessHeap(), 0, Request);
-
- return TRUE;
+ MultiByteToWideChar(CP_ACP, 0, lpConsoleTitle, -1, WideTitle, Length);
+ Ret = SetConsoleTitleW(WideTitle);
+ HeapFree(GetProcessHeap(), 0, WideTitle);
+ return Ret;
}
Modified: trunk/reactos/include/reactos/subsys/csrss/csrss.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/include/reactos/subsys/csr…
==============================================================================
--- trunk/reactos/include/reactos/subsys/csrss/csrss.h [iso-8859-1] (original)
+++ trunk/reactos/include/reactos/subsys/csrss/csrss.h [iso-8859-1] Fri Jun 4 08:36:12
2010
@@ -207,13 +207,13 @@
typedef struct
{
DWORD Length;
- WCHAR Title[0];
+ PWCHAR Title;
} CSRSS_SET_TITLE, *PCSRSS_SET_TITLE;
typedef struct
{
DWORD Length;
- WCHAR Title[0];
+ PWCHAR Title;
} CSRSS_GET_TITLE, *PCSRSS_GET_TITLE;
typedef struct
@@ -487,11 +487,6 @@
#define CSRSS_MAX_READ_CONSOLE (LPC_MAX_DATA_LENGTH -
CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE))
#define CSRSS_MAX_READ_CONSOLE_OUTPUT_CHAR (LPC_MAX_DATA_LENGTH -
CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_CHAR))
#define CSRSS_MAX_READ_CONSOLE_OUTPUT_ATTRIB (LPC_MAX_DATA_LENGTH -
CSR_API_MESSAGE_HEADER_SIZE(CSRSS_READ_CONSOLE_OUTPUT_ATTRIB))
-#define CSRSS_MAX_GET_PROCESS_LIST (LPC_MAX_DATA_LENGTH -
CSR_API_MESSAGE_HEADER_SIZE(CSRSS_GET_PROCESS_LIST))
-
-/* WCHARs, not bytes! */
-#define CSRSS_MAX_TITLE_LENGTH 80
-#define CSRSS_MAX_ALIAS_TARGET_LENGTH 80
#define CREATE_PROCESS (0x0)
#define TERMINATE_PROCESS (0x1)
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/alias.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/alias.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/alias.c [iso-8859-1] Fri Jun 4 08:36:12
2010
@@ -31,21 +31,6 @@
} ALIAS_HEADER, *PALIAS_HEADER;
-/* Ensure that a buffer is contained within the process's shared memory section. */
-static BOOL
-ValidateBuffer(PCSRSS_PROCESS_DATA ProcessData, PVOID Buffer, ULONG Size)
-{
- ULONG Offset = (BYTE *)Buffer - (BYTE *)ProcessData->CsrSectionViewBase;
- if (Offset >= ProcessData->CsrSectionViewSize
- || Size > (ProcessData->CsrSectionViewSize - Offset))
- {
- DPRINT1("Invalid buffer %p %d; not within %p %d\n",
- Buffer, Size, ProcessData->CsrSectionViewBase,
ProcessData->CsrSectionViewSize);
- return FALSE;
- }
- return TRUE;
-}
-
static
PALIAS_HEADER
IntFindAliasHeader(PALIAS_HEADER RootHeader, LPCWSTR lpExeName)
@@ -415,7 +400,8 @@
return STATUS_BUFFER_TOO_SMALL;
}
- if (!ValidateBuffer(ProcessData, lpTarget,
Request->Data.GetConsoleAlias.TargetBufferLength))
+ if (!Win32CsrValidateBuffer(ProcessData, lpTarget,
+ Request->Data.GetConsoleAlias.TargetBufferLength, 1))
{
ConioUnlockConsole(Console);
return STATUS_ACCESS_VIOLATION;
@@ -457,9 +443,10 @@
return STATUS_BUFFER_OVERFLOW;
}
- if (!ValidateBuffer(ProcessData,
- Request->Data.GetAllConsoleAlias.AliasBuffer,
- Request->Data.GetAllConsoleAlias.AliasBufferLength))
+ if (!Win32CsrValidateBuffer(ProcessData,
+ Request->Data.GetAllConsoleAlias.AliasBuffer,
+ Request->Data.GetAllConsoleAlias.AliasBufferLength,
+ 1))
{
ConioUnlockConsole(Console);
return STATUS_ACCESS_VIOLATION;
@@ -532,9 +519,10 @@
return STATUS_INVALID_PARAMETER;
}
- if (!ValidateBuffer(ProcessData,
- Request->Data.GetConsoleAliasesExes.ExeNames,
- Request->Data.GetConsoleAliasesExes.Length))
+ if (!Win32CsrValidateBuffer(ProcessData,
+ Request->Data.GetConsoleAliasesExes.ExeNames,
+ Request->Data.GetConsoleAliasesExes.Length,
+ 1))
{
ConioUnlockConsole(Console);
return STATUS_ACCESS_VIOLATION;
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/coninput.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/coninput.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/coninput.c [iso-8859-1] Fri Jun 4
08:36:12 2010
@@ -678,7 +678,6 @@
{
NTSTATUS Status;
PCSRSS_CONSOLE Console;
- DWORD Size;
DWORD Length;
PLIST_ENTRY CurrentItem;
PINPUT_RECORD InputRecord;
@@ -698,10 +697,8 @@
InputRecord = Request->Data.PeekConsoleInputRequest.InputRecord;
Length = Request->Data.PeekConsoleInputRequest.Length;
- Size = Length * sizeof(INPUT_RECORD);
-
- if (((PVOID)InputRecord < ProcessData->CsrSectionViewBase)
- || (((ULONG_PTR)InputRecord + Size) >
((ULONG_PTR)ProcessData->CsrSectionViewBase + ProcessData->CsrSectionViewSize)))
+
+ if (!Win32CsrValidateBuffer(ProcessData, InputRecord, Length, sizeof(INPUT_RECORD)))
{
ConioUnlockConsole(Console);
return STATUS_ACCESS_VIOLATION;
@@ -749,7 +746,6 @@
PCSRSS_CONSOLE Console;
NTSTATUS Status;
DWORD Length;
- DWORD Size;
DWORD i;
ConsoleInput* Record;
@@ -766,10 +762,8 @@
InputRecord = Request->Data.WriteConsoleInputRequest.InputRecord;
Length = Request->Data.WriteConsoleInputRequest.Length;
- Size = Length * sizeof(INPUT_RECORD);
-
- if (((PVOID)InputRecord < ProcessData->CsrSectionViewBase)
- || (((ULONG_PTR)InputRecord + Size) >
((ULONG_PTR)ProcessData->CsrSectionViewBase + ProcessData->CsrSectionViewSize)))
+
+ if (!Win32CsrValidateBuffer(ProcessData, InputRecord, Length, sizeof(INPUT_RECORD)))
{
ConioUnlockConsole(Console);
return STATUS_ACCESS_VIOLATION;
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/conoutput.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/conoutput.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/conoutput.c [iso-8859-1] Fri Jun 4
08:36:12 2010
@@ -1084,7 +1084,6 @@
COORD BufferSize;
NTSTATUS Status;
PBYTE Ptr;
- DWORD PSize;
DPRINT("CsrWriteConsoleOutput\n");
@@ -1101,12 +1100,10 @@
Console = Buff->Header.Console;
BufferSize = Request->Data.WriteConsoleOutputRequest.BufferSize;
- PSize = BufferSize.X * BufferSize.Y * sizeof(CHAR_INFO);
BufferCoord = Request->Data.WriteConsoleOutputRequest.BufferCoord;
CharInfo = Request->Data.WriteConsoleOutputRequest.CharInfo;
- if (((PVOID)CharInfo < ProcessData->CsrSectionViewBase) ||
- (((ULONG_PTR)CharInfo + PSize) >
- ((ULONG_PTR)ProcessData->CsrSectionViewBase +
ProcessData->CsrSectionViewSize)))
+ if (!Win32CsrValidateBuffer(ProcessData, CharInfo,
+ BufferSize.X * BufferSize.Y, sizeof(CHAR_INFO)))
{
ConioUnlockScreenBuffer(Buff);
return STATUS_ACCESS_VIOLATION;
@@ -1395,8 +1392,6 @@
PCHAR_INFO CharInfo;
PCHAR_INFO CurCharInfo;
PCSRSS_SCREEN_BUFFER Buff;
- DWORD Size;
- DWORD Length;
DWORD SizeX, SizeY;
NTSTATUS Status;
COORD BufferSize;
@@ -1423,14 +1418,12 @@
ReadRegion = Request->Data.ReadConsoleOutputRequest.ReadRegion;
BufferSize = Request->Data.ReadConsoleOutputRequest.BufferSize;
BufferCoord = Request->Data.ReadConsoleOutputRequest.BufferCoord;
- Length = BufferSize.X * BufferSize.Y;
- Size = Length * sizeof(CHAR_INFO);
/* FIXME: Is this correct? */
CodePage = ProcessData->Console->OutputCodePage;
- if (((PVOID)CharInfo < ProcessData->CsrSectionViewBase)
- || (((ULONG_PTR)CharInfo + Size) >
((ULONG_PTR)ProcessData->CsrSectionViewBase + ProcessData->CsrSectionViewSize)))
+ if (!Win32CsrValidateBuffer(ProcessData, CharInfo,
+ BufferSize.X * BufferSize.Y, sizeof(CHAR_INFO)))
{
ConioUnlockScreenBuffer(Buff);
return STATUS_ACCESS_VIOLATION;
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/console.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/console.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/console.c [iso-8859-1] Fri Jun 4
08:36:12 2010
@@ -455,19 +455,15 @@
DPRINT("CsrSetTitle\n");
- if (Request->Header.u1.s1.TotalLength
- < CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE)
- + Request->Data.SetTitleRequest.Length)
- {
- DPRINT1("Invalid request size\n");
- Request->Header.u1.s1.TotalLength = sizeof(CSR_API_MESSAGE);
- Request->Header.u1.s1.DataLength = sizeof(CSR_API_MESSAGE) -
sizeof(PORT_MESSAGE);
- return STATUS_INVALID_PARAMETER;
- }
-
- Status = ConioConsoleFromProcessData(ProcessData, &Console);
- Request->Header.u1.s1.TotalLength = sizeof(CSR_API_MESSAGE);
- Request->Header.u1.s1.DataLength = sizeof(CSR_API_MESSAGE) -
sizeof(PORT_MESSAGE);
+ Request->Header.u1.s1.TotalLength = sizeof(CSR_API_MESSAGE);
+ Request->Header.u1.s1.DataLength = sizeof(CSR_API_MESSAGE) -
sizeof(PORT_MESSAGE);
+ if (!Win32CsrValidateBuffer(ProcessData, Request->Data.SetTitleRequest.Title,
+ Request->Data.SetTitleRequest.Length, 1))
+ {
+ return STATUS_ACCESS_VIOLATION;
+ }
+
+ Status = ConioConsoleFromProcessData(ProcessData, &Console);
if(NT_SUCCESS(Status))
{
Buffer = RtlAllocateHeap(RtlGetProcessHeap(), 0,
Request->Data.SetTitleRequest.Length);
@@ -507,6 +503,13 @@
Request->Header.u1.s1.TotalLength = sizeof(CSR_API_MESSAGE);
Request->Header.u1.s1.DataLength = sizeof(CSR_API_MESSAGE) -
sizeof(PORT_MESSAGE);
+
+ if (!Win32CsrValidateBuffer(ProcessData, Request->Data.GetTitleRequest.Title,
+ Request->Data.GetTitleRequest.Length, 1))
+ {
+ return STATUS_ACCESS_VIOLATION;
+ }
+
Status = ConioConsoleFromProcessData(ProcessData, &Console);
if (! NT_SUCCESS(Status))
{
@@ -515,19 +518,16 @@
}
/* Copy title of the console to the user title buffer */
- RtlZeroMemory(&Request->Data.GetTitleRequest, sizeof(CSRSS_GET_TITLE));
+ if (Request->Data.GetTitleRequest.Length >= sizeof(WCHAR))
+ {
+ Length = min(Request->Data.GetTitleRequest.Length - sizeof(WCHAR),
Console->Title.Length);
+ memcpy(Request->Data.GetTitleRequest.Title, Console->Title.Buffer,
Length);
+ Request->Data.GetTitleRequest.Title[Length / sizeof(WCHAR)] = L'\0';
+ }
+
Request->Data.GetTitleRequest.Length = Console->Title.Length;
- memcpy (Request->Data.GetTitleRequest.Title, Console->Title.Buffer,
- Console->Title.Length);
- Length = CSR_API_MESSAGE_HEADER_SIZE(CSRSS_SET_TITLE) + Console->Title.Length;
-
- ConioUnlockConsole(Console);
-
- if (Length > sizeof(CSR_API_MESSAGE))
- {
- Request->Header.u1.s1.TotalLength = Length;
- Request->Header.u1.s1.DataLength = Length - sizeof(PORT_MESSAGE);
- }
+
+ ConioUnlockConsole(Console);
return STATUS_SUCCESS;
}
@@ -754,7 +754,6 @@
PLIST_ENTRY current_entry;
ULONG nItems = 0;
NTSTATUS Status;
- ULONG_PTR Offset;
DPRINT("CsrGetProcessList\n");
@@ -762,13 +761,8 @@
Request->Header.u1.s1.DataLength = sizeof(CSR_API_MESSAGE) -
sizeof(PORT_MESSAGE);
Buffer = Request->Data.GetProcessListRequest.ProcessId;
- Offset = (PBYTE)Buffer - (PBYTE)ProcessData->CsrSectionViewBase;
- if (Offset >= ProcessData->CsrSectionViewSize
- || (Request->Data.GetProcessListRequest.nMaxIds * sizeof(DWORD)) >
(ProcessData->CsrSectionViewSize - Offset)
- || Offset & (sizeof(DWORD) - 1))
- {
+ if (!Win32CsrValidateBuffer(ProcessData, Buffer,
Request->Data.GetProcessListRequest.nMaxIds, sizeof(DWORD)))
return STATUS_ACCESS_VIOLATION;
- }
Status = ConioConsoleFromProcessData(ProcessData, &Console);
if (! NT_SUCCESS(Status))
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/dllmain.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/dllmain.c [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/dllmain.c [iso-8859-1] Fri Jun 4
08:36:12 2010
@@ -100,6 +100,32 @@
return TRUE;
}
+/* Ensure that a captured buffer is safe to access */
+BOOL FASTCALL
+Win32CsrValidateBuffer(PCSRSS_PROCESS_DATA ProcessData, PVOID Buffer,
+ SIZE_T NumElements, SIZE_T ElementSize)
+{
+ /* Check that the following conditions are true:
+ * 1. The start of the buffer is somewhere within the process's
+ * shared memory section view.
+ * 2. The remaining space in the view is at least as large as the buffer.
+ * (NB: Please don't try to "optimize" this by using multiplication
+ * instead of division; remember that 2147483648 * 2 = 0.)
+ * 3. The buffer is DWORD-aligned.
+ */
+ ULONG_PTR Offset = (BYTE *)Buffer - (BYTE *)ProcessData->CsrSectionViewBase;
+ if (Offset >= ProcessData->CsrSectionViewSize
+ || NumElements > (ProcessData->CsrSectionViewSize - Offset) /
ElementSize
+ || (Offset & (sizeof(DWORD) - 1)) != 0)
+ {
+ DPRINT1("Invalid buffer %p(%u*%u); section view is %p(%u)\n",
+ Buffer, NumElements, ElementSize,
+ ProcessData->CsrSectionViewBase, ProcessData->CsrSectionViewSize);
+ return FALSE;
+ }
+ return TRUE;
+}
+
NTSTATUS FASTCALL
Win32CsrEnumProcesses(CSRSS_ENUM_PROCESS_PROC EnumProc,
PVOID Context)
Modified: trunk/reactos/subsystems/win32/csrss/win32csr/win32csr.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/subsystems/win32/csrss/win…
==============================================================================
--- trunk/reactos/subsystems/win32/csrss/win32csr/win32csr.h [iso-8859-1] (original)
+++ trunk/reactos/subsystems/win32/csrss/win32csr/win32csr.h [iso-8859-1] Fri Jun 4
08:36:12 2010
@@ -63,6 +63,10 @@
CSR_API(CsrDuplicateHandle);
CSR_API(CsrGetInputWaitHandle);
+BOOL FASTCALL Win32CsrValidateBuffer(PCSRSS_PROCESS_DATA ProcessData,
+ PVOID Buffer,
+ SIZE_T NumElements,
+ SIZE_T ElementSize);
NTSTATUS FASTCALL Win32CsrEnumProcesses(CSRSS_ENUM_PROCESS_PROC EnumProc,
PVOID Context);