mirror of
https://github.com/reactos/reactos.git
synced 2024-12-28 10:04:49 +00:00
Fixed environment implementation
Fixed current directory implementation svn path=/trunk/; revision=987
This commit is contained in:
parent
f0175145d6
commit
6708f0b87e
18 changed files with 1413 additions and 1462 deletions
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: rtl.h,v 1.25 2000/02/05 16:04:52 ekohl Exp $
|
/* $Id: rtl.h,v 1.26 2000/02/18 00:47:28 ekohl Exp $
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
@ -537,16 +537,6 @@ RtlInitAnsiString (
|
||||||
PCSZ SourceString
|
PCSZ SourceString
|
||||||
);
|
);
|
||||||
|
|
||||||
NTSTATUS
|
|
||||||
STDCALL
|
|
||||||
RtlInitializeContext (
|
|
||||||
IN HANDLE ProcessHandle,
|
|
||||||
IN PCONTEXT Context,
|
|
||||||
IN PVOID Parameter,
|
|
||||||
IN PTHREAD_START_ROUTINE StartAddress,
|
|
||||||
IN OUT PINITIAL_TEB InitialTeb
|
|
||||||
);
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlInitString (
|
RtlInitString (
|
||||||
|
@ -561,6 +551,16 @@ RtlInitUnicodeString (
|
||||||
PCWSTR SourceString
|
PCWSTR SourceString
|
||||||
);
|
);
|
||||||
|
|
||||||
|
NTSTATUS
|
||||||
|
STDCALL
|
||||||
|
RtlInitializeContext (
|
||||||
|
IN HANDLE ProcessHandle,
|
||||||
|
IN PCONTEXT Context,
|
||||||
|
IN PVOID Parameter,
|
||||||
|
IN PTHREAD_START_ROUTINE StartAddress,
|
||||||
|
IN OUT PINITIAL_TEB InitialTeb
|
||||||
|
);
|
||||||
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlIntegerToChar (
|
RtlIntegerToChar (
|
||||||
|
@ -578,6 +578,14 @@ RtlIntegerToUnicodeString (
|
||||||
IN OUT PUNICODE_STRING String
|
IN OUT PUNICODE_STRING String
|
||||||
);
|
);
|
||||||
|
|
||||||
|
BOOLEAN
|
||||||
|
STDCALL
|
||||||
|
RtlIsNameLegalDOS8Dot3 (
|
||||||
|
IN PUNICODE_STRING UnicodeName,
|
||||||
|
IN OUT PANSI_STRING AnsiName,
|
||||||
|
IN OUT PBOOLEAN SpacesFound
|
||||||
|
);
|
||||||
|
|
||||||
LARGE_INTEGER
|
LARGE_INTEGER
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlLargeIntegerAdd (
|
RtlLargeIntegerAdd (
|
||||||
|
|
|
@ -33,6 +33,7 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define DPRINT1(args...) do { DbgPrint("(%s:%d) ",__FILE__,__LINE__); DbgPrint(args); ExAllocatePool(NonPagedPool,0); } while(0);
|
#define DPRINT1(args...) do { DbgPrint("(%s:%d) ",__FILE__,__LINE__); DbgPrint(args); ExAllocatePool(NonPagedPool,0); } while(0);
|
||||||
|
#define CHECKPOINT1 do { DbgPrint("%s:%d\n",__FILE__,__LINE__); ExAllocatePool(NonPagedPool,0); } while(0);
|
||||||
|
|
||||||
extern unsigned int old_idt[256][2];
|
extern unsigned int old_idt[256][2];
|
||||||
//extern unsigned int idt;
|
//extern unsigned int idt;
|
||||||
|
|
|
@ -28,6 +28,9 @@ typedef struct _PEB_FREE_BLOCK
|
||||||
ULONG Size;
|
ULONG Size;
|
||||||
} PEB_FREE_BLOCK, *PPEB_FREE_BLOCK;
|
} PEB_FREE_BLOCK, *PPEB_FREE_BLOCK;
|
||||||
|
|
||||||
|
/* RTL_USER_PROCESS_PARAMETERS.Flags */
|
||||||
|
#define PPF_NORMALIZED (1)
|
||||||
|
|
||||||
typedef struct _RTL_USER_PROCESS_PARAMETERS
|
typedef struct _RTL_USER_PROCESS_PARAMETERS
|
||||||
{
|
{
|
||||||
ULONG TotalSize; // 00h
|
ULONG TotalSize; // 00h
|
||||||
|
|
|
@ -23,6 +23,14 @@
|
||||||
#define FIELD_OFFSET(type,fld) ((LONG)&(((type *)0)->fld))
|
#define FIELD_OFFSET(type,fld) ((LONG)&(((type *)0)->fld))
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
/* GLOBAL VARIABLES ***********************************************************/
|
||||||
|
|
||||||
|
extern WINBOOL bIsFileApiAnsi;
|
||||||
|
|
||||||
|
|
||||||
|
/* FUNCTION PROTOTYPES ********************************************************/
|
||||||
|
|
||||||
BOOL __ErrorReturnFalse(ULONG ErrorCode);
|
BOOL __ErrorReturnFalse(ULONG ErrorCode);
|
||||||
PVOID __ErrorReturnNull(ULONG ErrorCode);
|
PVOID __ErrorReturnNull(ULONG ErrorCode);
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: rtl.h,v 1.8 2000/02/05 16:06:09 ekohl Exp $
|
/* $Id: rtl.h,v 1.9 2000/02/18 00:48:25 ekohl Exp $
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
@ -89,14 +89,6 @@ RtlIsDosDeviceName_U (
|
||||||
PWSTR DeviceName
|
PWSTR DeviceName
|
||||||
);
|
);
|
||||||
|
|
||||||
BOOLEAN
|
|
||||||
STDCALL
|
|
||||||
RtlIsNameLegalDOS8Dot3 (
|
|
||||||
PUNICODE_STRING us,
|
|
||||||
PANSI_STRING as,
|
|
||||||
PBOOLEAN pb
|
|
||||||
);
|
|
||||||
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlSetCurrentDirectory_U (
|
RtlSetCurrentDirectory_U (
|
||||||
|
@ -208,10 +200,10 @@ RtlCreateProcessParameters (
|
||||||
IN PUNICODE_STRING Title,
|
IN PUNICODE_STRING Title,
|
||||||
IN PUNICODE_STRING Desktop,
|
IN PUNICODE_STRING Desktop,
|
||||||
IN PUNICODE_STRING Reserved,
|
IN PUNICODE_STRING Reserved,
|
||||||
IN PVOID Reserved2
|
IN PUNICODE_STRING Reserved2
|
||||||
);
|
);
|
||||||
|
|
||||||
VOID
|
PRTL_USER_PROCESS_PARAMETERS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlDeNormalizeProcessParams (
|
RtlDeNormalizeProcessParams (
|
||||||
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
||||||
|
@ -223,7 +215,7 @@ RtlDestroyProcessParameters (
|
||||||
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
||||||
);
|
);
|
||||||
|
|
||||||
VOID
|
PRTL_USER_PROCESS_PARAMETERS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlNormalizeProcessParams (
|
RtlNormalizeProcessParams (
|
||||||
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
IN OUT PRTL_USER_PROCESS_PARAMETERS ProcessParameters
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: curdir.c,v 1.19 2000/01/11 17:30:16 ekohl Exp $
|
/* $Id: curdir.c,v 1.20 2000/02/18 00:49:39 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -11,176 +11,146 @@
|
||||||
|
|
||||||
/* INCLUDES ******************************************************************/
|
/* INCLUDES ******************************************************************/
|
||||||
|
|
||||||
|
#include <ddk/ntddk.h>
|
||||||
|
#include <ntdll/rtl.h>
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <wchar.h>
|
|
||||||
#include <ctype.h>
|
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
#define NDEBUG
|
#define NDEBUG
|
||||||
#include <kernel32/kernel32.h>
|
#include <kernel32/kernel32.h>
|
||||||
|
|
||||||
/* GLOBALS *******************************************************************/
|
|
||||||
|
|
||||||
static HANDLE hCurrentDirectory = NULL;
|
/* GLOBAL VARIABLES **********************************************************/
|
||||||
static WCHAR CurrentDirectoryW[MAX_PATH];
|
|
||||||
|
|
||||||
static WCHAR SystemDirectoryW[MAX_PATH];
|
static WCHAR SystemDirectoryW[MAX_PATH];
|
||||||
static WCHAR WindowsDirectoryW[MAX_PATH];
|
static WCHAR WindowsDirectoryW[MAX_PATH];
|
||||||
|
|
||||||
WINBOOL STDCALL SetCurrentDirectoryW(LPCWSTR lpPathName);
|
|
||||||
|
|
||||||
/* FUNCTIONS *****************************************************************/
|
/* FUNCTIONS *****************************************************************/
|
||||||
|
|
||||||
DWORD STDCALL GetCurrentDirectoryA(DWORD nBufferLength, LPSTR lpBuffer)
|
DWORD
|
||||||
|
STDCALL
|
||||||
|
GetCurrentDirectoryA (
|
||||||
|
DWORD nBufferLength,
|
||||||
|
LPSTR lpBuffer
|
||||||
|
)
|
||||||
{
|
{
|
||||||
UINT uSize,i;
|
ANSI_STRING AnsiString;
|
||||||
WCHAR TempDir[MAX_PATH];
|
UNICODE_STRING UnicodeString;
|
||||||
|
|
||||||
if ( lpBuffer == NULL )
|
/* initialize ansi string */
|
||||||
return 0;
|
AnsiString.Length = 0;
|
||||||
|
AnsiString.MaximumLength = nBufferLength;
|
||||||
|
AnsiString.Buffer = lpBuffer;
|
||||||
|
|
||||||
GetCurrentDirectoryW(MAX_PATH, TempDir);
|
/* allocate buffer for unicode string */
|
||||||
uSize = lstrlenW(TempDir);
|
UnicodeString.Length = 0;
|
||||||
if (nBufferLength > uSize)
|
UnicodeString.MaximumLength = nBufferLength * sizeof(WCHAR);
|
||||||
{
|
UnicodeString.Buffer = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
i = 0;
|
0,
|
||||||
while (TempDir[i] != 0)
|
UnicodeString.MaximumLength);
|
||||||
{
|
|
||||||
lpBuffer[i] = (unsigned char)TempDir[i];
|
/* get current directory */
|
||||||
i++;
|
UnicodeString.Length = RtlGetCurrentDirectory_U (UnicodeString.MaximumLength,
|
||||||
}
|
UnicodeString.Buffer);
|
||||||
lpBuffer[i] = 0;
|
DPRINT("UnicodeString.Buffer %S\n", UnicodeString.Buffer);
|
||||||
}
|
|
||||||
return uSize;
|
/* convert unicode string to ansi (or oem) */
|
||||||
|
if (bIsFileApiAnsi)
|
||||||
|
RtlUnicodeStringToAnsiString (&AnsiString,
|
||||||
|
&UnicodeString,
|
||||||
|
FALSE);
|
||||||
|
else
|
||||||
|
RtlUnicodeStringToOemString (&AnsiString,
|
||||||
|
&UnicodeString,
|
||||||
|
FALSE);
|
||||||
|
DPRINT("AnsiString.Buffer %s\n", AnsiString.Buffer);
|
||||||
|
|
||||||
|
/* free unicode string */
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
UnicodeString.Buffer);
|
||||||
|
|
||||||
|
return AnsiString.Length;
|
||||||
}
|
}
|
||||||
|
|
||||||
DWORD STDCALL GetCurrentDirectoryW(DWORD nBufferLength, LPWSTR lpBuffer)
|
|
||||||
|
DWORD
|
||||||
|
STDCALL
|
||||||
|
GetCurrentDirectoryW (
|
||||||
|
DWORD nBufferLength,
|
||||||
|
LPWSTR lpBuffer
|
||||||
|
)
|
||||||
{
|
{
|
||||||
UINT uSize;
|
ULONG Length;
|
||||||
|
|
||||||
DPRINT("GetCurrentDirectoryW()\n");
|
Length = RtlGetCurrentDirectory_U (nBufferLength,
|
||||||
|
lpBuffer);
|
||||||
|
|
||||||
if ( lpBuffer == NULL )
|
return (Length / sizeof (WCHAR));
|
||||||
return 0;
|
|
||||||
|
|
||||||
uSize = lstrlenW(CurrentDirectoryW);
|
|
||||||
if (nBufferLength > uSize)
|
|
||||||
{
|
|
||||||
lstrcpyW(lpBuffer, CurrentDirectoryW);
|
|
||||||
}
|
|
||||||
if (uSize > 3 && lpBuffer[uSize - 1] == L'\\')
|
|
||||||
{
|
|
||||||
lpBuffer[uSize - 1] = 0;
|
|
||||||
uSize--;
|
|
||||||
}
|
|
||||||
DPRINT("GetCurrentDirectoryW() = '%S'\n",lpBuffer);
|
|
||||||
|
|
||||||
return uSize;
|
|
||||||
#if 0
|
|
||||||
return (RtlGetCurrentDirectory_U (nBufferLength, lpBuffer) / sizeof (WCHAR));
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
WINBOOL STDCALL SetCurrentDirectoryA(LPCSTR lpPathName)
|
|
||||||
|
WINBOOL
|
||||||
|
STDCALL
|
||||||
|
SetCurrentDirectoryA (
|
||||||
|
LPCSTR lpPathName
|
||||||
|
)
|
||||||
{
|
{
|
||||||
UINT i;
|
ANSI_STRING AnsiString;
|
||||||
WCHAR PathNameW[MAX_PATH];
|
UNICODE_STRING UnicodeString;
|
||||||
|
NTSTATUS Status;
|
||||||
|
|
||||||
if ( lpPathName == NULL )
|
RtlInitAnsiString (&AnsiString,
|
||||||
|
(LPSTR)lpPathName);
|
||||||
|
|
||||||
|
/* convert ansi (or oem) to unicode */
|
||||||
|
if (bIsFileApiAnsi)
|
||||||
|
RtlAnsiStringToUnicodeString (&UnicodeString,
|
||||||
|
&AnsiString,
|
||||||
|
TRUE);
|
||||||
|
else
|
||||||
|
RtlOemStringToUnicodeString (&UnicodeString,
|
||||||
|
&AnsiString,
|
||||||
|
TRUE);
|
||||||
|
|
||||||
|
Status = RtlSetCurrentDirectory_U (&UnicodeString);
|
||||||
|
|
||||||
|
RtlFreeUnicodeString (&UnicodeString);
|
||||||
|
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
SetLastError(ERROR_INVALID_PARAMETER);
|
SetLastError (RtlNtStatusToDosError (Status));
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( lstrlen(lpPathName) > MAX_PATH )
|
|
||||||
{
|
|
||||||
SetLastError(ERROR_BUFFER_OVERFLOW);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
i = 0;
|
|
||||||
while ((lpPathName[i])!=0 && i < MAX_PATH)
|
|
||||||
{
|
|
||||||
PathNameW[i] = (WCHAR)lpPathName[i];
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
PathNameW[i] = 0;
|
|
||||||
|
|
||||||
return SetCurrentDirectoryW(PathNameW);
|
|
||||||
}
|
|
||||||
|
|
||||||
WINBOOL STDCALL SetCurrentDirectoryW(LPCWSTR lpPathName)
|
|
||||||
{
|
|
||||||
ULONG len;
|
|
||||||
WCHAR PathName[MAX_PATH];
|
|
||||||
HANDLE hDir;
|
|
||||||
|
|
||||||
DPRINT("SetCurrentDirectoryW(lpPathName %S)\n",lpPathName);
|
|
||||||
|
|
||||||
if (lpPathName == NULL)
|
|
||||||
{
|
|
||||||
SetLastError(ERROR_INVALID_PARAMETER);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
len = lstrlenW(lpPathName);
|
|
||||||
if (len > MAX_PATH)
|
|
||||||
{
|
|
||||||
SetLastError(ERROR_BUFFER_OVERFLOW);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!GetFullPathNameW (lpPathName, MAX_PATH, PathName, NULL))
|
|
||||||
{
|
|
||||||
SetLastError(ERROR_BAD_PATHNAME);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
DPRINT("PathName %S\n",PathName);
|
|
||||||
|
|
||||||
hDir = CreateFileW(PathName,
|
|
||||||
GENERIC_READ,
|
|
||||||
FILE_SHARE_READ,
|
|
||||||
NULL,
|
|
||||||
OPEN_EXISTING,
|
|
||||||
FILE_ATTRIBUTE_DIRECTORY,
|
|
||||||
NULL);
|
|
||||||
if (hDir == INVALID_HANDLE_VALUE)
|
|
||||||
{
|
|
||||||
DPRINT("Failed to open directory\n");
|
|
||||||
SetLastError(ERROR_BAD_PATHNAME);
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (hCurrentDirectory != NULL)
|
|
||||||
{
|
|
||||||
CloseHandle(hCurrentDirectory);
|
|
||||||
}
|
|
||||||
|
|
||||||
hCurrentDirectory = hDir;
|
|
||||||
|
|
||||||
DPRINT("PathName %S\n",PathName);
|
|
||||||
|
|
||||||
wcscpy(CurrentDirectoryW,PathName);
|
|
||||||
len = lstrlenW(CurrentDirectoryW);
|
|
||||||
if (CurrentDirectoryW[len-1] != '\\')
|
|
||||||
{
|
|
||||||
CurrentDirectoryW[len] = '\\';
|
|
||||||
CurrentDirectoryW[len+1] = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
#if 0
|
|
||||||
UNICODE_STRING PathName_U;
|
|
||||||
|
|
||||||
RtlInitUnicodeString (&PathName_U,
|
|
||||||
lpPathName);
|
|
||||||
|
|
||||||
return RtlSetCurrentDirectory_U (&PathName_U);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
DWORD STDCALL GetTempPathA(DWORD nBufferLength, LPSTR lpBuffer)
|
|
||||||
|
WINBOOL
|
||||||
|
STDCALL
|
||||||
|
SetCurrentDirectoryW (
|
||||||
|
LPCWSTR lpPathName
|
||||||
|
)
|
||||||
|
{
|
||||||
|
UNICODE_STRING UnicodeString;
|
||||||
|
NTSTATUS Status;
|
||||||
|
|
||||||
|
RtlInitUnicodeString (&UnicodeString,
|
||||||
|
lpPathName);
|
||||||
|
|
||||||
|
Status = RtlSetCurrentDirectory_U (&UnicodeString);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
SetLastError (RtlNtStatusToDosError (Status));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
DWORD STDCALL GetTempPathA (DWORD nBufferLength, LPSTR lpBuffer)
|
||||||
{
|
{
|
||||||
WCHAR BufferW[MAX_PATH];
|
WCHAR BufferW[MAX_PATH];
|
||||||
DWORD retCode;
|
DWORD retCode;
|
||||||
|
@ -214,6 +184,7 @@ DWORD STDCALL GetTempPathW(DWORD nBufferLength, LPWSTR lpBuffer)
|
||||||
UINT STDCALL GetSystemDirectoryA(LPSTR lpBuffer, UINT uSize)
|
UINT STDCALL GetSystemDirectoryA(LPSTR lpBuffer, UINT uSize)
|
||||||
{
|
{
|
||||||
UINT uPathSize,i;
|
UINT uPathSize,i;
|
||||||
|
|
||||||
if ( lpBuffer == NULL )
|
if ( lpBuffer == NULL )
|
||||||
return 0;
|
return 0;
|
||||||
uPathSize = lstrlenW(SystemDirectoryW);
|
uPathSize = lstrlenW(SystemDirectoryW);
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: dir.c,v 1.23 2000/01/20 22:55:37 ekohl Exp $
|
/* $Id: dir.c,v 1.24 2000/02/18 00:49:39 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -16,6 +16,7 @@
|
||||||
/* INCLUDES ******************************************************************/
|
/* INCLUDES ******************************************************************/
|
||||||
|
|
||||||
#include <ddk/ntddk.h>
|
#include <ddk/ntddk.h>
|
||||||
|
#include <ntdll/rtl.h>
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <wchar.h>
|
#include <wchar.h>
|
||||||
|
@ -317,276 +318,107 @@ WINBOOL STDCALL RemoveDirectoryW(LPCWSTR lpPathName)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static DWORD GetDotSequenceLengthA (PSTR p)
|
DWORD
|
||||||
{
|
STDCALL
|
||||||
DWORD dwCount = 0;
|
GetFullPathNameA (
|
||||||
|
LPCSTR lpFileName,
|
||||||
for (;;)
|
|
||||||
{
|
|
||||||
if (*p == '.')
|
|
||||||
dwCount++;
|
|
||||||
else if ((*p == '\\' || *p == '\0') && dwCount)
|
|
||||||
return dwCount;
|
|
||||||
else
|
|
||||||
return 0;
|
|
||||||
p++;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
DWORD STDCALL GetFullPathNameA(LPCSTR lpFileName,
|
|
||||||
DWORD nBufferLength,
|
DWORD nBufferLength,
|
||||||
LPSTR lpBuffer,
|
LPSTR lpBuffer,
|
||||||
LPSTR *lpFilePart)
|
LPSTR *lpFilePart
|
||||||
|
)
|
||||||
{
|
{
|
||||||
PSTR p;
|
UNICODE_STRING FileNameU;
|
||||||
PSTR prev = NULL;
|
UNICODE_STRING FullNameU;
|
||||||
|
ANSI_STRING FileName;
|
||||||
|
ANSI_STRING FullName;
|
||||||
|
PWSTR FilePartU;
|
||||||
|
ULONG BufferLength;
|
||||||
|
ULONG Offset;
|
||||||
|
|
||||||
DPRINT("GetFullPathNameA(lpFileName %s, nBufferLength %d, lpBuffer %p, "
|
DPRINT("GetFullPathNameA(lpFileName %s, nBufferLength %d, lpBuffer %p, "
|
||||||
"lpFilePart %p)\n",lpFileName,nBufferLength,lpBuffer,lpFilePart);
|
"lpFilePart %p)\n",lpFileName,nBufferLength,lpBuffer,lpFilePart);
|
||||||
|
|
||||||
if (!lpFileName || !lpBuffer)
|
RtlInitAnsiString (&FileName,
|
||||||
return 0;
|
(LPSTR)lpFileName);
|
||||||
|
|
||||||
if (isalpha(lpFileName[0]) && lpFileName[1] == ':')
|
if (bIsFileApiAnsi)
|
||||||
{
|
RtlAnsiStringToUnicodeString (&FileNameU,
|
||||||
if (lpFileName[2] == '\\')
|
&FileName,
|
||||||
{
|
TRUE);
|
||||||
lstrcpyA(lpBuffer, lpFileName);
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
RtlOemStringToUnicodeString (&FileNameU,
|
||||||
CHAR szRoot[4] = "A:\\";
|
&FileName,
|
||||||
DWORD len;
|
TRUE);
|
||||||
|
|
||||||
szRoot[0] = lpFileName[0];
|
BufferLength = nBufferLength * sizeof(WCHAR);
|
||||||
len = GetCurrentDirectoryA(nBufferLength, lpBuffer);
|
|
||||||
if (lpBuffer[len - 1] != '\\')
|
FullNameU.MaximumLength = BufferLength;
|
||||||
{
|
FullNameU.Length = 0;
|
||||||
lpBuffer[len] = '\\';
|
FullNameU.Buffer = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
lpBuffer[len + 1] = 0;
|
0,
|
||||||
}
|
BufferLength);
|
||||||
lstrcatA(lpBuffer, &lpFileName[2]);
|
|
||||||
}
|
FullNameU.Length = RtlGetFullPathName_U (FileNameU.Buffer,
|
||||||
}
|
BufferLength,
|
||||||
else if (lpFileName[0] == '\\')
|
FullNameU.Buffer,
|
||||||
{
|
&FilePartU);
|
||||||
GetCurrentDirectoryA(nBufferLength, lpBuffer);
|
|
||||||
lstrcpyA(&lpBuffer[2], lpFileName);
|
RtlFreeUnicodeString (&FileNameU);
|
||||||
}
|
|
||||||
|
FullName.MaximumLength = nBufferLength;
|
||||||
|
FullName.Length = 0;
|
||||||
|
FullName.Buffer = lpBuffer;
|
||||||
|
|
||||||
|
/* convert unicode to ansi (or oem) */
|
||||||
|
if (bIsFileApiAnsi)
|
||||||
|
RtlUnicodeStringToAnsiString (&FullName,
|
||||||
|
&FullNameU,
|
||||||
|
FALSE);
|
||||||
else
|
else
|
||||||
{
|
RtlUnicodeStringToOemString (&FullName,
|
||||||
DWORD len;
|
&FullNameU,
|
||||||
len = GetCurrentDirectoryA(nBufferLength, lpBuffer);
|
FALSE);
|
||||||
if (lpBuffer[len - 1] != '\\')
|
|
||||||
{
|
|
||||||
lpBuffer[len] = '\\';
|
|
||||||
lpBuffer[len + 1] = 0;
|
|
||||||
}
|
|
||||||
lstrcatA(lpBuffer, lpFileName);
|
|
||||||
}
|
|
||||||
|
|
||||||
DPRINT("lpBuffer %s\n",lpBuffer);
|
|
||||||
|
|
||||||
p = lpBuffer + 2;
|
|
||||||
prev = p;
|
|
||||||
|
|
||||||
while ((*p) != 0 || ((*p) == '\\' && (*(p+1)) == 0))
|
|
||||||
{
|
|
||||||
DWORD dwDotLen;
|
|
||||||
|
|
||||||
dwDotLen = GetDotSequenceLengthA (p+1);
|
|
||||||
DPRINT("DotSequenceLength %u\n", dwDotLen);
|
|
||||||
DPRINT("prev %s p %s\n",prev,p);
|
|
||||||
|
|
||||||
if (dwDotLen == 0)
|
|
||||||
{
|
|
||||||
prev = p;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
p++;
|
|
||||||
}
|
|
||||||
while ((*p) != 0 && (*p) != '\\');
|
|
||||||
}
|
|
||||||
else if (dwDotLen == 1)
|
|
||||||
{
|
|
||||||
lstrcpyA(p, p+2);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (dwDotLen > 2)
|
|
||||||
{
|
|
||||||
int n = dwDotLen - 2;
|
|
||||||
|
|
||||||
while (n > 0 && prev > (lpBuffer+2))
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
if ((*prev) == '\\')
|
|
||||||
n--;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (*(p+dwDotLen+1) == 0)
|
|
||||||
*(prev+1) = 0;
|
|
||||||
else
|
|
||||||
lstrcpyA (prev, p+dwDotLen+1);
|
|
||||||
p = prev;
|
|
||||||
if (prev > (lpBuffer+2))
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
while ((*prev) != '\\')
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lpFilePart != NULL)
|
if (lpFilePart != NULL)
|
||||||
{
|
{
|
||||||
(*lpFilePart) = prev + 1;
|
Offset = (ULONG)(FilePartU - FullNameU.Buffer);
|
||||||
|
*lpFilePart = FullName.Buffer + Offset;
|
||||||
}
|
}
|
||||||
|
|
||||||
DPRINT("lpBuffer %s\n",lpBuffer);
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
FullNameU.Buffer);
|
||||||
|
|
||||||
return strlen(lpBuffer);
|
DPRINT("lpBuffer %s lpFilePart %s Length %ld\n",
|
||||||
|
lpBuffer, lpFilePart, FullName.Length);
|
||||||
|
|
||||||
|
return FullName.Length;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static DWORD GetDotSequenceLengthW (PWSTR p)
|
DWORD
|
||||||
{
|
STDCALL
|
||||||
DWORD dwCount = 0;
|
GetFullPathNameW (
|
||||||
|
LPCWSTR lpFileName,
|
||||||
for (;;)
|
|
||||||
{
|
|
||||||
if (*p == '.')
|
|
||||||
dwCount++;
|
|
||||||
else if ((*p == '\\' || *p == '\0') && dwCount)
|
|
||||||
return dwCount;
|
|
||||||
else
|
|
||||||
return 0;
|
|
||||||
p++;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
DWORD STDCALL GetFullPathNameW(LPCWSTR lpFileName,
|
|
||||||
DWORD nBufferLength,
|
DWORD nBufferLength,
|
||||||
LPWSTR lpBuffer,
|
LPWSTR lpBuffer,
|
||||||
LPWSTR *lpFilePart)
|
LPWSTR *lpFilePart
|
||||||
|
)
|
||||||
{
|
{
|
||||||
PWSTR p;
|
ULONG Length;
|
||||||
PWSTR prev = NULL;
|
|
||||||
|
|
||||||
DPRINT("GetFullPathNameW(lpFileName %S, nBufferLength %d, lpBuffer %p, "
|
DPRINT("GetFullPathNameW(lpFileName %S, nBufferLength %d, lpBuffer %p, "
|
||||||
"lpFilePart %p)\n",lpFileName,nBufferLength,lpBuffer,lpFilePart);
|
"lpFilePart %p)\n",lpFileName,nBufferLength,lpBuffer,lpFilePart);
|
||||||
|
|
||||||
if (!lpFileName || !lpBuffer)
|
Length = RtlGetFullPathName_U ((LPWSTR)lpFileName,
|
||||||
return 0;
|
nBufferLength * sizeof(WCHAR),
|
||||||
|
lpBuffer,
|
||||||
|
lpFilePart);
|
||||||
|
|
||||||
if (isalpha(lpFileName[0]) && lpFileName[1] == L':')
|
DPRINT("lpBuffer %S lpFilePart %S Length %ld\n",
|
||||||
{
|
lpBuffer, lpFilePart, Length / sizeof(WCHAR));
|
||||||
if (lpFileName[2] == L'\\')
|
|
||||||
{
|
|
||||||
lstrcpyW(lpBuffer, lpFileName);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
WCHAR szRoot[4] = L"A:\\";
|
|
||||||
DWORD len;
|
|
||||||
|
|
||||||
szRoot[0] = lpFileName[0];
|
return (Length / sizeof(WCHAR));
|
||||||
len = GetCurrentDirectoryW(nBufferLength, lpBuffer);
|
|
||||||
if (lpBuffer[len - 1] != L'\\')
|
|
||||||
{
|
|
||||||
lpBuffer[len] = L'\\';
|
|
||||||
lpBuffer[len + 1] = 0;
|
|
||||||
}
|
|
||||||
lstrcatW(lpBuffer, &lpFileName[2]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (lpFileName[0] == L'\\')
|
|
||||||
{
|
|
||||||
GetCurrentDirectoryW(nBufferLength, lpBuffer);
|
|
||||||
lstrcpyW(&lpBuffer[2], lpFileName);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
DWORD len;
|
|
||||||
len = GetCurrentDirectoryW(nBufferLength, lpBuffer);
|
|
||||||
if (lpBuffer[len - 1] != L'\\')
|
|
||||||
{
|
|
||||||
lpBuffer[len] = L'\\';
|
|
||||||
lpBuffer[len + 1] = 0;
|
|
||||||
}
|
|
||||||
lstrcatW(lpBuffer, lpFileName);
|
|
||||||
}
|
|
||||||
|
|
||||||
DPRINT("lpBuffer %S\n",lpBuffer);
|
|
||||||
|
|
||||||
p = lpBuffer + 2;
|
|
||||||
prev = p;
|
|
||||||
|
|
||||||
while ((*p) != 0 || ((*p) == L'\\' && (*(p+1)) == 0))
|
|
||||||
{
|
|
||||||
DWORD dwDotLen;
|
|
||||||
|
|
||||||
dwDotLen = GetDotSequenceLengthW (p+1);
|
|
||||||
DPRINT("DotSequenceLength %u\n", dwDotLen);
|
|
||||||
DPRINT("prev %S p %S\n",prev,p);
|
|
||||||
|
|
||||||
if (dwDotLen == 0)
|
|
||||||
{
|
|
||||||
prev = p;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
p++;
|
|
||||||
}
|
|
||||||
while ((*p) != 0 && (*p) != L'\\');
|
|
||||||
}
|
|
||||||
else if (dwDotLen == 1)
|
|
||||||
{
|
|
||||||
lstrcpyW(p, p+2);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (dwDotLen > 2)
|
|
||||||
{
|
|
||||||
int n = dwDotLen - 2;
|
|
||||||
|
|
||||||
while (n > 0 && prev > (lpBuffer+2))
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
if ((*prev) == L'\\')
|
|
||||||
n--;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (*(p+dwDotLen+1) == 0)
|
|
||||||
*(prev+1) = 0;
|
|
||||||
else
|
|
||||||
lstrcpyW (prev, p+dwDotLen+1);
|
|
||||||
p = prev;
|
|
||||||
if (prev > (lpBuffer+2))
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
while ((*prev) != L'\\')
|
|
||||||
{
|
|
||||||
prev--;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (lpFilePart != NULL)
|
|
||||||
{
|
|
||||||
(*lpFilePart) = prev + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
DPRINT("lpBuffer %S\n",lpBuffer);
|
|
||||||
|
|
||||||
return wcslen(lpBuffer);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -734,7 +566,8 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
|
|
||||||
DPRINT("SearchPath\n");
|
DPRINT("SearchPath\n");
|
||||||
|
|
||||||
if ( lpPath == NULL ) {
|
if ( lpPath == NULL )
|
||||||
|
{
|
||||||
// check the directory from which the application loaded
|
// check the directory from which the application loaded
|
||||||
|
|
||||||
if ( GetCurrentDirectoryW( MAX_PATH, BufferW ) > 0 ) {
|
if ( GetCurrentDirectoryW( MAX_PATH, BufferW ) > 0 ) {
|
||||||
|
@ -772,62 +605,10 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
|
|
||||||
HeapFree(GetProcessHeap(),0,EnvironmentBufferW);
|
HeapFree(GetProcessHeap(),0,EnvironmentBufferW);
|
||||||
|
|
||||||
// WCHAR BufferW[MAX_PATH];
|
|
||||||
// WCHAR FileAndExtensionW[MAX_PATH];
|
|
||||||
// WCHAR *EnvironmentBufferW = NULL;
|
|
||||||
|
|
||||||
// UNICODE_STRING PathString;
|
|
||||||
// OBJECT_ATTRIBUTES ObjectAttributes;
|
|
||||||
// IO_STATUS_BLOCK IoStatusBlock;
|
|
||||||
|
|
||||||
DPRINT("SearchPath\n");
|
|
||||||
|
|
||||||
if (lpPath == NULL)
|
|
||||||
{
|
|
||||||
// check the directory from which the application loaded
|
|
||||||
|
|
||||||
if (GetCurrentDirectoryW(MAX_PATH, BufferW) > 0)
|
|
||||||
{
|
|
||||||
retCode = SearchPathW(BufferW,lpFileName, lpExtension, nBufferLength, lpBuffer, lpFilePart );
|
|
||||||
if ( retCode != 0 )
|
|
||||||
return retCode;
|
return retCode;
|
||||||
}
|
}
|
||||||
if ( GetSystemDirectoryW(BufferW, MAX_PATH) > 0 )
|
else
|
||||||
{
|
{
|
||||||
retCode = SearchPathW(BufferW,lpFileName, lpExtension, nBufferLength, lpBuffer, lpFilePart );
|
|
||||||
if ( retCode != 0 )
|
|
||||||
return retCode;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( GetWindowsDirectoryW(BufferW, MAX_PATH) > 0 )
|
|
||||||
{
|
|
||||||
retCode = SearchPathW(BufferW,lpFileName, lpExtension, nBufferLength, lpBuffer, lpFilePart );
|
|
||||||
if ( retCode != 0 )
|
|
||||||
return retCode;
|
|
||||||
}
|
|
||||||
|
|
||||||
j = GetEnvironmentVariableW(L"Path",EnvironmentBufferW,0);
|
|
||||||
EnvironmentBufferW = (WCHAR *) HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,(j+1)*sizeof(WCHAR));
|
|
||||||
|
|
||||||
j = GetEnvironmentVariableW(L"Path",EnvironmentBufferW,j+1);
|
|
||||||
|
|
||||||
for(i=0;i<j;i++) {
|
|
||||||
if ( EnvironmentBufferW[i] == L';' )
|
|
||||||
EnvironmentBufferW[i] = 0;
|
|
||||||
}
|
|
||||||
i = 0;
|
|
||||||
while ( retCode == 0 && i < j ) {
|
|
||||||
if ( EnvironmentBufferW[i] != 0 )
|
|
||||||
retCode = SearchPathW(&EnvironmentBufferW[i],lpFileName, lpExtension, nBufferLength, lpBuffer, lpFilePart );
|
|
||||||
i += lstrlenW(&EnvironmentBufferW[i]) + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
HeapFree(GetProcessHeap(),0,EnvironmentBufferW);
|
|
||||||
|
|
||||||
return retCode;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
|
|
||||||
FileAndExtensionW[0] = 0;
|
FileAndExtensionW[0] = 0;
|
||||||
lpBuffer[0] = 0;
|
lpBuffer[0] = 0;
|
||||||
i = lstrlenW(lpFileName);
|
i = lstrlenW(lpFileName);
|
||||||
|
@ -836,7 +617,8 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
if ( i + j + 8 < nBufferLength )
|
if ( i + j + 8 < nBufferLength )
|
||||||
return i + j + 9;
|
return i + j + 9;
|
||||||
|
|
||||||
if ( lpExtension != NULL ) {
|
if ( lpExtension != NULL )
|
||||||
|
{
|
||||||
if ( lpFileName[i-4] != L'.' ) {
|
if ( lpFileName[i-4] != L'.' ) {
|
||||||
wcscpy(FileAndExtensionW,lpFileName);
|
wcscpy(FileAndExtensionW,lpFileName);
|
||||||
wcscat(FileAndExtensionW,lpExtension);
|
wcscat(FileAndExtensionW,lpExtension);
|
||||||
|
@ -847,18 +629,14 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
else
|
else
|
||||||
wcscpy(FileAndExtensionW,lpFileName);
|
wcscpy(FileAndExtensionW,lpFileName);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
lstrcatW(BufferW,L"\\??\\");
|
lstrcatW(BufferW,L"\\??\\");
|
||||||
lstrcatW(BufferW,lpPath);
|
lstrcatW(BufferW,lpPath);
|
||||||
|
|
||||||
|
|
||||||
//printf("%S\n",FileAndExtensionW);
|
//printf("%S\n",FileAndExtensionW);
|
||||||
|
|
||||||
|
|
||||||
i = wcslen(BufferW);
|
i = wcslen(BufferW);
|
||||||
if ( BufferW[i-1] != L'\\' ) {
|
if ( BufferW[i-1] != L'\\' )
|
||||||
|
{
|
||||||
BufferW[i] = L'\\';
|
BufferW[i] = L'\\';
|
||||||
BufferW[i+1] = 0;
|
BufferW[i+1] = 0;
|
||||||
}
|
}
|
||||||
|
@ -883,6 +661,7 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
if ( lpFilePart != NULL )
|
if ( lpFilePart != NULL )
|
||||||
*lpFilePart = &BufferW[wcslen(BufferW)+1];
|
*lpFilePart = &BufferW[wcslen(BufferW)+1];
|
||||||
wcscat(BufferW,FileAndExtensionW);
|
wcscat(BufferW,FileAndExtensionW);
|
||||||
|
|
||||||
//printf("%S\n",lpBuffer);
|
//printf("%S\n",lpBuffer);
|
||||||
|
|
||||||
PathString.Buffer = BufferW;
|
PathString.Buffer = BufferW;
|
||||||
|
@ -916,6 +695,6 @@ DWORD STDCALL SearchPathW(LPCWSTR lpPath,
|
||||||
|
|
||||||
return lstrlenW(lpBuffer);
|
return lstrlenW(lpBuffer);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* EOF */
|
||||||
|
|
|
@ -21,9 +21,11 @@
|
||||||
|
|
||||||
#define LPPROGRESS_ROUTINE void*
|
#define LPPROGRESS_ROUTINE void*
|
||||||
|
|
||||||
|
|
||||||
/* GLOBALS ******************************************************************/
|
/* GLOBALS ******************************************************************/
|
||||||
|
|
||||||
static BOOLEAN bIsFileApiAnsi; // set the file api to ansi or oem
|
WINBOOL bIsFileApiAnsi = TRUE; // set the file api to ansi or oem
|
||||||
|
|
||||||
|
|
||||||
/* FUNCTIONS ****************************************************************/
|
/* FUNCTIONS ****************************************************************/
|
||||||
|
|
||||||
|
@ -41,7 +43,7 @@ VOID STDCALL SetFileApisToANSI(VOID)
|
||||||
|
|
||||||
WINBOOL STDCALL AreFileApisANSI(VOID)
|
WINBOOL STDCALL AreFileApisANSI(VOID)
|
||||||
{
|
{
|
||||||
return(bIsFileApiAnsi);
|
return (bIsFileApiAnsi);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -42,7 +42,6 @@ WINBOOL STDCALL DllMain(HANDLE hInst,
|
||||||
{
|
{
|
||||||
DPRINT("DLL_PROCESS_ATTACH\n");
|
DPRINT("DLL_PROCESS_ATTACH\n");
|
||||||
AllocConsole();
|
AllocConsole();
|
||||||
SetCurrentDirectoryA("C:\\");
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case DLL_THREAD_ATTACH:
|
case DLL_THREAD_ATTACH:
|
||||||
|
@ -70,6 +69,3 @@ WINBOOL STDCALL DllMain(HANDLE hInst,
|
||||||
}
|
}
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
/*
|
/* $Id: env.c,v 1.10 2000/02/18 00:49:56 ekohl Exp $
|
||||||
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
* FILE: lib/kernel32/misc/env.c
|
* FILE: lib/kernel32/misc/env.c
|
||||||
|
@ -9,172 +10,189 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <ddk/ntddk.h>
|
#include <ddk/ntddk.h>
|
||||||
|
#include <ntdll/rtl.h>
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
#include <wchar.h>
|
#include <wchar.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
|
#define NDEBUG
|
||||||
#include <kernel32/kernel32.h>
|
#include <kernel32/kernel32.h>
|
||||||
|
|
||||||
#define MAX_ENVIRONMENT_VARS 255
|
|
||||||
#define MAX_VALUE 1024
|
|
||||||
|
|
||||||
typedef struct _ENV_ELEMENT
|
/* FUNCTIONS ******************************************************************/
|
||||||
{
|
|
||||||
UNICODE_STRING Name;
|
|
||||||
UNICODE_STRING Value;
|
|
||||||
WINBOOL Valid;
|
|
||||||
} ENV_ELEMENT;
|
|
||||||
|
|
||||||
ENV_ELEMENT Environment[MAX_ENVIRONMENT_VARS+1];
|
|
||||||
UINT nEnvVar = 0;
|
|
||||||
|
|
||||||
DWORD STDCALL GetEnvironmentVariableA(LPCSTR lpName,
|
|
||||||
LPSTR lpBuffer,
|
|
||||||
DWORD nSize)
|
|
||||||
{
|
|
||||||
WCHAR BufferW[MAX_VALUE];
|
|
||||||
WCHAR NameW[MAX_PATH];
|
|
||||||
DWORD RetValue;
|
|
||||||
int i=0;
|
|
||||||
|
|
||||||
while ((*lpName)!=0 && i < MAX_PATH)
|
|
||||||
{
|
|
||||||
NameW[i] = *lpName;
|
|
||||||
lpName++;
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
NameW[i] = 0;
|
|
||||||
|
|
||||||
RetValue = GetEnvironmentVariableW(NameW,BufferW,nSize);
|
|
||||||
for(i=0;i<nSize;i++)
|
|
||||||
lpBuffer[i] = (char)BufferW[i];
|
|
||||||
return RetValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
DWORD
|
DWORD
|
||||||
STDCALL
|
STDCALL
|
||||||
GetEnvironmentVariableW(
|
GetEnvironmentVariableA (
|
||||||
|
LPCSTR lpName,
|
||||||
|
LPSTR lpBuffer,
|
||||||
|
DWORD nSize
|
||||||
|
)
|
||||||
|
{
|
||||||
|
ANSI_STRING VarName;
|
||||||
|
ANSI_STRING VarValue;
|
||||||
|
UNICODE_STRING VarNameU;
|
||||||
|
UNICODE_STRING VarValueU;
|
||||||
|
NTSTATUS Status;
|
||||||
|
|
||||||
|
/* initialize unicode variable name string */
|
||||||
|
RtlInitAnsiString (&VarName,
|
||||||
|
(LPSTR)lpName);
|
||||||
|
RtlAnsiStringToUnicodeString (&VarNameU,
|
||||||
|
&VarName,
|
||||||
|
TRUE);
|
||||||
|
|
||||||
|
/* initialize ansi variable value string */
|
||||||
|
VarValue.Length = 0;
|
||||||
|
VarValue.MaximumLength = nSize;
|
||||||
|
VarValue.Buffer = lpBuffer;
|
||||||
|
|
||||||
|
/* initialize unicode variable value string and allocate buffer */
|
||||||
|
VarValueU.Length = 0;
|
||||||
|
VarValueU.MaximumLength = nSize * sizeof(WCHAR);
|
||||||
|
VarValueU.Buffer = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
VarValueU.MaximumLength);
|
||||||
|
|
||||||
|
/* get unicode environment variable */
|
||||||
|
Status = RtlQueryEnvironmentVariable_U (NULL,
|
||||||
|
&VarNameU,
|
||||||
|
&VarValueU);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
/* free unicode buffer */
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
VarValueU.Buffer);
|
||||||
|
|
||||||
|
/* free unicode variable name string */
|
||||||
|
RtlFreeUnicodeString (&VarNameU);
|
||||||
|
|
||||||
|
SetLastError (RtlNtStatusToDosError(Status));
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* convert unicode value string to ansi */
|
||||||
|
RtlUnicodeStringToAnsiString (&VarValue,
|
||||||
|
&VarValueU,
|
||||||
|
FALSE);
|
||||||
|
|
||||||
|
/* free unicode buffer */
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
VarValueU.Buffer);
|
||||||
|
|
||||||
|
/* free unicode variable name string */
|
||||||
|
RtlFreeUnicodeString (&VarNameU);
|
||||||
|
|
||||||
|
return (VarValueU.Length / sizeof(WCHAR));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
DWORD
|
||||||
|
STDCALL
|
||||||
|
GetEnvironmentVariableW (
|
||||||
LPCWSTR lpName,
|
LPCWSTR lpName,
|
||||||
LPWSTR lpBuffer,
|
LPWSTR lpBuffer,
|
||||||
DWORD nSize
|
DWORD nSize
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UINT NameLen;
|
UNICODE_STRING VarName;
|
||||||
UINT i;
|
UNICODE_STRING VarValue;
|
||||||
NameLen = lstrlenW(lpName);
|
NTSTATUS Status;
|
||||||
i = 0;
|
|
||||||
|
|
||||||
while (i < nEnvVar)
|
RtlInitUnicodeString (&VarName,
|
||||||
|
lpName);
|
||||||
|
|
||||||
|
VarValue.Length = 0;
|
||||||
|
VarValue.MaximumLength = nSize * sizeof(WCHAR);
|
||||||
|
VarValue.Buffer = lpBuffer;
|
||||||
|
|
||||||
|
Status = RtlQueryEnvironmentVariable_U (NULL,
|
||||||
|
&VarName,
|
||||||
|
&VarValue);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
if ( _wcsnicmp(Environment[i].Name.Buffer,lpName,min(NameLen,Environment[i].Name.Length/sizeof(WCHAR))) != 0 ) {
|
SetLastError (RtlNtStatusToDosError(Status));
|
||||||
lstrcpynW(lpBuffer,Environment[i].Value.Buffer,min(nSize,Environment[i].Value.Length/sizeof(WCHAR)));
|
|
||||||
|
|
||||||
return lstrlenW(Environment[i].Value.Buffer);
|
|
||||||
|
|
||||||
}
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (VarValue.Length / sizeof(WCHAR));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
SetEnvironmentVariableA(
|
SetEnvironmentVariableA (
|
||||||
LPCSTR lpName,
|
LPCSTR lpName,
|
||||||
LPCSTR lpValue
|
LPCSTR lpValue
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
WCHAR NameW[MAX_PATH];
|
ANSI_STRING VarName;
|
||||||
WCHAR ValueW[MAX_VALUE];
|
ANSI_STRING VarValue;
|
||||||
|
UNICODE_STRING VarNameU;
|
||||||
|
UNICODE_STRING VarValueU;
|
||||||
|
NTSTATUS Status;
|
||||||
|
|
||||||
int i=0;
|
RtlInitAnsiString (&VarName,
|
||||||
while ((*lpName)!=0 && i < MAX_PATH)
|
(LPSTR)lpName);
|
||||||
|
RtlAnsiStringToUnicodeString (&VarNameU,
|
||||||
|
&VarName,
|
||||||
|
TRUE);
|
||||||
|
|
||||||
|
RtlInitAnsiString (&VarValue,
|
||||||
|
(LPSTR)lpValue);
|
||||||
|
RtlAnsiStringToUnicodeString (&VarValueU,
|
||||||
|
&VarValue,
|
||||||
|
TRUE);
|
||||||
|
|
||||||
|
Status = RtlSetEnvironmentVariable (NULL,
|
||||||
|
&VarNameU,
|
||||||
|
&VarValueU);
|
||||||
|
|
||||||
|
RtlFreeUnicodeString (&VarNameU);
|
||||||
|
RtlFreeUnicodeString (&VarValueU);
|
||||||
|
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
NameW[i] = *lpName;
|
SetLastError (RtlNtStatusToDosError(Status));
|
||||||
lpName++;
|
return FALSE;
|
||||||
i++;
|
|
||||||
}
|
}
|
||||||
NameW[i] = 0;
|
|
||||||
|
|
||||||
i = 0;
|
return TRUE;
|
||||||
|
|
||||||
while ((*lpValue)!=0 && i < MAX_PATH)
|
|
||||||
{
|
|
||||||
ValueW[i] = *lpValue;
|
|
||||||
lpValue++;
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
ValueW[i] = 0;
|
|
||||||
return SetEnvironmentVariableW(NameW,ValueW);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
SetEnvironmentVariableW(
|
SetEnvironmentVariableW (
|
||||||
LPCWSTR lpName,
|
LPCWSTR lpName,
|
||||||
LPCWSTR lpValue
|
LPCWSTR lpValue
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UINT NameLen, ValueLen;
|
UNICODE_STRING VarName;
|
||||||
UINT i;
|
UNICODE_STRING VarValue;
|
||||||
WCHAR *NameBuffer;
|
NTSTATUS Status;
|
||||||
WCHAR *ValueBuffer;
|
|
||||||
NameLen = lstrlenW(lpName);
|
|
||||||
ValueLen = lstrlenW(lpValue);
|
|
||||||
i = 0;
|
|
||||||
|
|
||||||
while (i < nEnvVar)
|
RtlInitUnicodeString (&VarName,
|
||||||
|
lpName);
|
||||||
|
|
||||||
|
RtlInitUnicodeString (&VarValue,
|
||||||
|
lpValue);
|
||||||
|
|
||||||
|
Status = RtlSetEnvironmentVariable (NULL,
|
||||||
|
&VarName,
|
||||||
|
&VarValue);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
if ( _wcsnicmp(Environment[i].Name.Buffer,lpName,min(NameLen,Environment[i].Name.Length/sizeof(WCHAR))) != 0 ) {
|
SetLastError (RtlNtStatusToDosError(Status));
|
||||||
if ( lpValue != NULL ) {
|
|
||||||
lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,Environment[i].Value.MaximumLength/sizeof(WCHAR)));
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
Environment[i].Valid = FALSE;
|
|
||||||
Environment[i].Value.Length = 0;
|
|
||||||
Environment[i].Name.Length = 0;
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
|
|
||||||
if ( nEnvVar >= MAX_ENVIRONMENT_VARS )
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
while (i < nEnvVar)
|
|
||||||
{
|
|
||||||
if ( Environment[i].Valid == FALSE )
|
|
||||||
break;
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
if ( i == nEnvVar ) {
|
|
||||||
NameBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,MAX_PATH*sizeof(WCHAR) );
|
|
||||||
ValueBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,MAX_VALUE*sizeof(WCHAR) );
|
|
||||||
|
|
||||||
Environment[i].Name.Buffer = NameBuffer;
|
|
||||||
Environment[i].Name.MaximumLength = MAX_PATH*sizeof(WCHAR);
|
|
||||||
|
|
||||||
Environment[i].Value.Buffer = ValueBuffer;
|
|
||||||
Environment[i].Value.MaximumLength = MAX_VALUE*sizeof(WCHAR);
|
|
||||||
nEnvVar++;
|
|
||||||
}
|
|
||||||
Environment[i].Valid = TRUE;
|
|
||||||
|
|
||||||
lstrcpynW(Environment[i].Name.Buffer,lpValue,min(NameLen,(Environment[i].Name.MaximumLength-sizeof(WCHAR))/sizeof(WCHAR)));
|
|
||||||
Environment[i].Name.Length = NameLen*sizeof(WCHAR);
|
|
||||||
|
|
||||||
lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,(Environment[i].Value.MaximumLength-sizeof(WCHAR)))/sizeof(WCHAR));
|
|
||||||
Environment[i].Value.Length = ValueLen*sizeof(WCHAR);
|
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
DWORD
|
DWORD
|
||||||
STDCALL
|
STDCALL
|
||||||
GetVersion(VOID)
|
GetVersion(VOID)
|
||||||
|
@ -192,7 +210,6 @@ GetVersion(VOID)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
GetVersionExW(
|
GetVersionExW(
|
||||||
|
@ -208,6 +225,7 @@ GetVersionExW(
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
GetVersionExA(
|
GetVersionExA(
|
||||||
|
@ -226,265 +244,202 @@ GetVersionExA(
|
||||||
|
|
||||||
LPSTR
|
LPSTR
|
||||||
STDCALL
|
STDCALL
|
||||||
GetEnvironmentStringsA(VOID)
|
GetEnvironmentStringsA (
|
||||||
|
VOID
|
||||||
|
)
|
||||||
{
|
{
|
||||||
#if 0
|
UNICODE_STRING UnicodeString;
|
||||||
WCHAR *EnvironmentStringsW;
|
ANSI_STRING AnsiString;
|
||||||
char *EnvironmentStringsA;
|
PWCHAR EnvU;
|
||||||
int size = 0;
|
PWCHAR PtrU;
|
||||||
int i;
|
ULONG Length;
|
||||||
#endif
|
PCHAR EnvPtr = NULL;
|
||||||
|
|
||||||
return(NULL);
|
EnvU = (PWCHAR)(NtCurrentPeb ()->ProcessParameters->Environment);
|
||||||
|
|
||||||
/* FIXME: This doesn't work */
|
if (EnvU == NULL)
|
||||||
#if 0
|
return NULL;
|
||||||
EnvironmentStringsW = GetEnvironmentStringsW();
|
|
||||||
EnvironmentStringsA = (char *)EnvironmentStringsW;
|
|
||||||
|
|
||||||
for(i=0;i<nEnvVar;i++)
|
if (*EnvU == 0)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
/* get environment size */
|
||||||
|
PtrU = EnvU;
|
||||||
|
while (*PtrU)
|
||||||
{
|
{
|
||||||
if ( Environment[i].Valid )
|
while (*PtrU)
|
||||||
|
PtrU++;
|
||||||
|
PtrU++;
|
||||||
|
}
|
||||||
|
Length = (ULONG)(PtrU - EnvU);
|
||||||
|
DPRINT("Length %lu\n", Length);
|
||||||
|
|
||||||
|
/* allocate environment buffer */
|
||||||
|
EnvPtr = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
Length + 1);
|
||||||
|
DPRINT("EnvPtr %p\n", EnvPtr);
|
||||||
|
|
||||||
|
/* convert unicode environment to ansi */
|
||||||
|
UnicodeString.MaximumLength = Length + sizeof(WCHAR);
|
||||||
|
UnicodeString.Buffer = EnvU;
|
||||||
|
|
||||||
|
AnsiString.MaximumLength = Length + 1;
|
||||||
|
AnsiString.Length = 0;
|
||||||
|
AnsiString.Buffer = EnvPtr;
|
||||||
|
|
||||||
|
DPRINT ("UnicodeString.Buffer \'%S\'\n", UnicodeString.Buffer);
|
||||||
|
|
||||||
|
while (*(UnicodeString.Buffer))
|
||||||
{
|
{
|
||||||
size += Environment[i].Name.Length;
|
UnicodeString.Length = wcslen (UnicodeString.Buffer) * sizeof(WCHAR);
|
||||||
size += sizeof(WCHAR); // =
|
if (UnicodeString.Length > 0)
|
||||||
size += Environment[i].Value.Length;
|
{
|
||||||
size += sizeof(WCHAR); // zero
|
DPRINT("UnicodeString.Buffer \'%S\'\n", UnicodeString.Buffer);
|
||||||
|
|
||||||
|
RtlUnicodeStringToAnsiString (&AnsiString,
|
||||||
|
&UnicodeString,
|
||||||
|
FALSE);
|
||||||
|
|
||||||
|
DPRINT("AnsiString.Buffer \'%s\'\n", AnsiString.Buffer);
|
||||||
|
|
||||||
|
AnsiString.Buffer += (AnsiString.Length + 1);
|
||||||
|
UnicodeString.Buffer += ((UnicodeString.Length / sizeof(WCHAR)) + 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
size += sizeof(WCHAR);
|
*(AnsiString.Buffer) = 0;
|
||||||
size /= sizeof(WCHAR);
|
|
||||||
for(i=0;i<size;i++)
|
return EnvPtr;
|
||||||
EnvironmentStringsA[i] = (char)EnvironmentStringsW[i];
|
|
||||||
return EnvironmentStringsA;
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
LPWSTR
|
LPWSTR
|
||||||
STDCALL
|
STDCALL
|
||||||
GetEnvironmentStringsW(VOID)
|
GetEnvironmentStringsW (
|
||||||
|
VOID
|
||||||
|
)
|
||||||
{
|
{
|
||||||
#if 0
|
return (LPWSTR)(NtCurrentPeb ()->ProcessParameters->Environment);
|
||||||
int size = 0;
|
|
||||||
int i;
|
|
||||||
WCHAR *EnvironmentString;
|
|
||||||
WCHAR *EnvironmentStringSave;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
return(NULL);
|
|
||||||
|
|
||||||
/* FIXME: This doesn't work, why not? */
|
|
||||||
#if 0
|
|
||||||
for(i=0;i<nEnvVar;i++)
|
|
||||||
{
|
|
||||||
if ( Environment[i].Valid )
|
|
||||||
{
|
|
||||||
size += Environment[i].Name.Length;
|
|
||||||
size += sizeof(WCHAR); // =
|
|
||||||
size += Environment[i].Value.Length;
|
|
||||||
size += sizeof(WCHAR); // zero
|
|
||||||
}
|
|
||||||
}
|
|
||||||
size += sizeof(WCHAR); // extra zero
|
|
||||||
DPRINT("size %d\n",size);
|
|
||||||
EnvironmentString = (WCHAR *)HeapAlloc(GetProcessHeap(),
|
|
||||||
HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,
|
|
||||||
size);
|
|
||||||
DPRINT("EnvironmentString %x\n",EnvironmentString);
|
|
||||||
EnvironmentStringSave = EnvironmentString;
|
|
||||||
for(i=0;i<nEnvVar;i++)
|
|
||||||
{
|
|
||||||
if ( Environment[i].Valid )
|
|
||||||
{
|
|
||||||
wcscpy(EnvironmentString,Environment[i].Name.Buffer);
|
|
||||||
wcscat(EnvironmentString,L"=");
|
|
||||||
wcscat(EnvironmentString,Environment[i].Value.Buffer);
|
|
||||||
|
|
||||||
size = Environment[i].Name.Length;
|
|
||||||
size += sizeof(WCHAR); // =
|
|
||||||
size += Environment[i].Value.Length;
|
|
||||||
size += sizeof(WCHAR); // zero
|
|
||||||
EnvironmentString += (size/sizeof(WCHAR));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
*EnvironmentString = 0;
|
|
||||||
return EnvironmentStringSave;
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
FreeEnvironmentStringsA(
|
FreeEnvironmentStringsA (
|
||||||
LPSTR EnvironmentStrings
|
LPSTR EnvironmentStrings
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
if ( EnvironmentStrings == NULL )
|
if (EnvironmentStrings == NULL)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
HeapFree(GetProcessHeap(),0,EnvironmentStrings);
|
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
EnvironmentStrings);
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
WINBOOL
|
WINBOOL
|
||||||
STDCALL
|
STDCALL
|
||||||
FreeEnvironmentStringsW(
|
FreeEnvironmentStringsW (
|
||||||
LPWSTR EnvironmentStrings
|
LPWSTR EnvironmentStrings
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
if ( EnvironmentStrings == NULL )
|
|
||||||
return FALSE;
|
|
||||||
HeapFree(GetProcessHeap(),0,EnvironmentStrings);
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int ExpandVariableA(
|
DWORD
|
||||||
LPCSTR lpSrc, LPSTR lpDst, DWORD nSize , DWORD *nWritten)
|
STDCALL
|
||||||
|
ExpandEnvironmentStringsA (
|
||||||
|
LPCSTR lpSrc,
|
||||||
|
LPSTR lpDst,
|
||||||
|
DWORD nSize
|
||||||
|
)
|
||||||
{
|
{
|
||||||
int nVar = 0;
|
ANSI_STRING Source;
|
||||||
LPSTR lpVar;
|
ANSI_STRING Destination;
|
||||||
LPSTR lpEnd;
|
UNICODE_STRING SourceU;
|
||||||
|
UNICODE_STRING DestinationU;
|
||||||
|
NTSTATUS Status;
|
||||||
|
ULONG Length = 0;
|
||||||
|
|
||||||
if ( nWritten == NULL )
|
RtlInitAnsiString (&Source,
|
||||||
return -1;
|
(LPSTR)lpSrc);
|
||||||
|
RtlAnsiStringToUnicodeString (&SourceU,
|
||||||
|
&Source,
|
||||||
|
TRUE);
|
||||||
|
|
||||||
if ( *lpSrc != '%' ) {
|
Destination.Length = 0;
|
||||||
return -1;
|
Destination.MaximumLength = nSize;
|
||||||
}
|
Destination.Buffer = lpDst,
|
||||||
|
|
||||||
|
DestinationU.Length = 0;
|
||||||
|
DestinationU.MaximumLength = nSize * sizeof(WCHAR);
|
||||||
|
DestinationU.Buffer = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
DestinationU.MaximumLength);
|
||||||
|
|
||||||
lpVar = (LPSTR)lpSrc;
|
Status = RtlExpandEnvironmentStrings_U (NULL,
|
||||||
lpVar++;
|
&SourceU,
|
||||||
|
&DestinationU,
|
||||||
|
&Length);
|
||||||
|
|
||||||
|
RtlFreeUnicodeString (&SourceU);
|
||||||
|
|
||||||
lpEnd = strchr( lpVar, '%' );
|
if (!NT_SUCCESS(Status))
|
||||||
if ( lpEnd == NULL ) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
*lpEnd = 0;
|
|
||||||
|
|
||||||
nWritten = GetEnvironmentVariableA(lpVar,lpDst,nSize);
|
|
||||||
*lpEnd = '%';
|
|
||||||
|
|
||||||
if ( nWritten == 0 )
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if ( nWritten > nSize )
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
return (lpEnd - lpVar) -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
DWORD STDCALL ExpandEnvironmentStringsA(
|
|
||||||
LPCSTR lpSrc, LPSTR lpDst, DWORD nSize
|
|
||||||
)
|
|
||||||
{
|
|
||||||
DWORD v;
|
|
||||||
DWORD bw;
|
|
||||||
|
|
||||||
while(*lpSrc != 0 && nSize > 0 )
|
|
||||||
{
|
{
|
||||||
if ( *lpSrc == '%' ) {
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
v = ExpandVariableA(lpSrc,lpDst,nSize , &bw);
|
0,
|
||||||
if ( v == -1 ) {
|
DestinationU.Buffer);
|
||||||
*lpDst = *lpSrc;
|
SetLastError (RtlNtStatusToDosError (Status));
|
||||||
lpDst++;
|
return 0;
|
||||||
lpSrc++;
|
|
||||||
nSize--;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
lpSrc+=v;
|
|
||||||
lpDst+=bw;
|
|
||||||
nSize-=bw;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
|
|
||||||
*lpDst = *lpSrc;
|
|
||||||
lpDst++;
|
|
||||||
lpSrc++;
|
|
||||||
nSize--;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
RtlUnicodeStringToAnsiString (&Destination,
|
||||||
|
&DestinationU,
|
||||||
|
FALSE);
|
||||||
|
|
||||||
}
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
DestinationU.Buffer);
|
||||||
|
|
||||||
int ExpandVariableW(
|
return (Length / sizeof(WCHAR));
|
||||||
LPCWSTR lpSrc, LPWSTR lpDst, DWORD nSize , DWORD *nWritten)
|
|
||||||
{
|
|
||||||
LPWSTR lpVar;
|
|
||||||
LPWSTR lpEnd;
|
|
||||||
|
|
||||||
if ( nWritten == NULL )
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if ( *lpSrc != L'%' ) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
lpVar = (LPWSTR)lpSrc;
|
|
||||||
lpVar++;
|
|
||||||
|
|
||||||
|
|
||||||
lpEnd = wcschr( lpVar, L'%' );
|
|
||||||
if ( lpEnd == NULL ) {
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
*lpEnd = 0;
|
|
||||||
|
|
||||||
nWritten = GetEnvironmentVariableW(lpVar,lpDst,nSize);
|
|
||||||
*lpEnd = L'%';
|
|
||||||
|
|
||||||
if ( nWritten == 0 )
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
if ( nWritten > nSize )
|
|
||||||
return -1;
|
|
||||||
|
|
||||||
return ((lpEnd - lpVar)/2) -1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
DWORD STDCALL ExpandEnvironmentStringsW(
|
DWORD
|
||||||
LPCWSTR lpSrc, LPWSTR lpDst, DWORD nSize
|
STDCALL
|
||||||
)
|
ExpandEnvironmentStringsW (
|
||||||
|
LPCWSTR lpSrc,
|
||||||
|
LPWSTR lpDst,
|
||||||
|
DWORD nSize
|
||||||
|
)
|
||||||
{
|
{
|
||||||
DWORD v;
|
UNICODE_STRING Source;
|
||||||
DWORD bw;
|
UNICODE_STRING Destination;
|
||||||
|
NTSTATUS Status;
|
||||||
|
ULONG Length = 0;
|
||||||
|
|
||||||
while(*lpSrc != 0 && nSize > 0 )
|
RtlInitUnicodeString (&Source,
|
||||||
|
(LPWSTR)lpSrc);
|
||||||
|
|
||||||
|
Destination.Length = 0;
|
||||||
|
Destination.MaximumLength = nSize * sizeof(WCHAR);
|
||||||
|
Destination.Buffer = lpDst;
|
||||||
|
|
||||||
|
Status = RtlExpandEnvironmentStrings_U (NULL,
|
||||||
|
&Source,
|
||||||
|
&Destination,
|
||||||
|
&Length);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
if ( *lpSrc == L'%' ) {
|
SetLastError (RtlNtStatusToDosError (Status));
|
||||||
v = ExpandVariableW(lpSrc,lpDst,nSize , &bw);
|
return 0;
|
||||||
if ( v == -1 ) {
|
|
||||||
*lpDst = *lpSrc;
|
|
||||||
lpDst++;
|
|
||||||
lpSrc++;
|
|
||||||
nSize--;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
lpSrc+=v;
|
|
||||||
lpDst+=bw;
|
|
||||||
nSize-=bw;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
|
|
||||||
*lpDst = *lpSrc;
|
|
||||||
lpDst++;
|
|
||||||
lpSrc++;
|
|
||||||
nSize--;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return (Length / sizeof(WCHAR));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* EOF */
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: create.c,v 1.20 2000/02/13 16:05:13 dwelch Exp $
|
/* $Id: create.c,v 1.21 2000/02/18 00:50:07 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -275,6 +275,54 @@ static NTSTATUS KlInitPeb (HANDLE ProcessHandle,
|
||||||
ULONG PpbSize;
|
ULONG PpbSize;
|
||||||
ULONG BytesWritten;
|
ULONG BytesWritten;
|
||||||
ULONG Offset;
|
ULONG Offset;
|
||||||
|
PVOID ParentEnv = NULL;
|
||||||
|
PVOID EnvPtr = NULL;
|
||||||
|
ULONG EnvSize = 0;
|
||||||
|
|
||||||
|
/* create the Environment */
|
||||||
|
if (Ppb->Environment != NULL)
|
||||||
|
ParentEnv = Ppb->Environment;
|
||||||
|
else if (NtCurrentPeb()->ProcessParameters->Environment != NULL)
|
||||||
|
ParentEnv = NtCurrentPeb()->ProcessParameters->Environment;
|
||||||
|
|
||||||
|
if (ParentEnv != NULL)
|
||||||
|
{
|
||||||
|
MEMORY_BASIC_INFORMATION MemInfo;
|
||||||
|
|
||||||
|
Status = NtQueryVirtualMemory (NtCurrentProcess (),
|
||||||
|
ParentEnv,
|
||||||
|
MemoryBasicInformation,
|
||||||
|
&MemInfo,
|
||||||
|
sizeof(MEMORY_BASIC_INFORMATION),
|
||||||
|
NULL);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
return Status;
|
||||||
|
}
|
||||||
|
EnvSize = MemInfo.RegionSize;
|
||||||
|
}
|
||||||
|
DPRINT("EnvironmentSize %ld\n", EnvSize);
|
||||||
|
|
||||||
|
/* allocate and initialize new environment block */
|
||||||
|
if (EnvSize != 0)
|
||||||
|
{
|
||||||
|
Status = NtAllocateVirtualMemory(ProcessHandle,
|
||||||
|
&EnvPtr,
|
||||||
|
0,
|
||||||
|
&EnvSize,
|
||||||
|
MEM_COMMIT,
|
||||||
|
PAGE_READWRITE);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
return(Status);
|
||||||
|
}
|
||||||
|
|
||||||
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
|
EnvPtr,
|
||||||
|
ParentEnv,
|
||||||
|
EnvSize,
|
||||||
|
&BytesWritten);
|
||||||
|
}
|
||||||
|
|
||||||
/* create the PPB */
|
/* create the PPB */
|
||||||
PpbBase = (PVOID)PEB_STARTUPINFO;
|
PpbBase = (PVOID)PEB_STARTUPINFO;
|
||||||
|
@ -297,13 +345,18 @@ static NTSTATUS KlInitPeb (HANDLE ProcessHandle,
|
||||||
Ppb->TotalSize,
|
Ppb->TotalSize,
|
||||||
&BytesWritten);
|
&BytesWritten);
|
||||||
|
|
||||||
|
/* write pointer to environment */
|
||||||
/* create the PPB */
|
Offset = FIELD_OFFSET(RTL_USER_PROCESS_PARAMETERS, Environment);
|
||||||
|
|
||||||
Offset = FIELD_OFFSET(PEB, ProcessParameters);
|
|
||||||
|
|
||||||
NtWriteVirtualMemory(ProcessHandle,
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
PEB_BASE + Offset,
|
(PVOID)(PpbBase + Offset),
|
||||||
|
&EnvPtr,
|
||||||
|
sizeof(EnvPtr),
|
||||||
|
&BytesWritten);
|
||||||
|
|
||||||
|
/* write pointer to process parameter block */
|
||||||
|
Offset = FIELD_OFFSET(PEB, ProcessParameters);
|
||||||
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
|
(PVOID)(PEB_BASE + Offset),
|
||||||
&PpbBase,
|
&PpbBase,
|
||||||
sizeof(PpbBase),
|
sizeof(PpbBase),
|
||||||
&BytesWritten);
|
&BytesWritten);
|
||||||
|
@ -327,12 +380,12 @@ WINBOOL STDCALL CreateProcessW(LPCWSTR lpApplicationName,
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
LPTHREAD_START_ROUTINE lpStartAddress = NULL;
|
LPTHREAD_START_ROUTINE lpStartAddress = NULL;
|
||||||
WCHAR TempCommandLine[256];
|
WCHAR TempCommandLine[256];
|
||||||
PVOID BaseAddress;
|
// PVOID BaseAddress;
|
||||||
LARGE_INTEGER SectionOffset;
|
// LARGE_INTEGER SectionOffset;
|
||||||
IMAGE_NT_HEADERS Headers;
|
// IMAGE_NT_HEADERS Headers;
|
||||||
IMAGE_DOS_HEADER DosHeader;
|
// IMAGE_DOS_HEADER DosHeader;
|
||||||
HANDLE NTDllSection;
|
// HANDLE NTDllSection;
|
||||||
ULONG InitialViewSize;
|
// ULONG InitialViewSize;
|
||||||
PROCESS_BASIC_INFORMATION ProcessBasicInfo;
|
PROCESS_BASIC_INFORMATION ProcessBasicInfo;
|
||||||
ULONG retlen;
|
ULONG retlen;
|
||||||
DWORD len = 0;
|
DWORD len = 0;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
; $Id: ntdll.def,v 1.39 2000/02/05 16:07:10 ekohl Exp $
|
; $Id: ntdll.def,v 1.40 2000/02/18 00:48:50 ekohl Exp $
|
||||||
;
|
;
|
||||||
; ReactOS Operating System
|
; ReactOS Operating System
|
||||||
;
|
;
|
||||||
|
@ -464,6 +464,10 @@ RtlDeNormalizeProcessParams@4
|
||||||
RtlDestroyEnvironment@4
|
RtlDestroyEnvironment@4
|
||||||
RtlDestroyHeap@4
|
RtlDestroyHeap@4
|
||||||
RtlDestroyProcessParameters@4
|
RtlDestroyProcessParameters@4
|
||||||
|
RtlDetermineDosPathNameType_U@4
|
||||||
|
RtlDoesFileExists_U@4
|
||||||
|
RtlDosPathNameToNtPathName_U@16
|
||||||
|
RtlDosSearchPath_U@24
|
||||||
RtlDowncaseUnicodeString@12
|
RtlDowncaseUnicodeString@12
|
||||||
RtlEnlargedIntegerMultiply@8
|
RtlEnlargedIntegerMultiply@8
|
||||||
RtlEnlargedUnsignedDivide@16
|
RtlEnlargedUnsignedDivide@16
|
||||||
|
@ -482,15 +486,19 @@ RtlFreeOemString@4
|
||||||
RtlFreeUnicodeString@4
|
RtlFreeUnicodeString@4
|
||||||
RtlGetCurrentDirectory_U@8
|
RtlGetCurrentDirectory_U@8
|
||||||
RtlGetDaclSecurityDescriptor@16
|
RtlGetDaclSecurityDescriptor@16
|
||||||
|
RtlGetFullPathName_U@16
|
||||||
RtlGetGroupSecurityDescriptor@12
|
RtlGetGroupSecurityDescriptor@12
|
||||||
|
RtlGetLongestNtPathLength@0
|
||||||
RtlGetOwnerSecurityDescriptor@12
|
RtlGetOwnerSecurityDescriptor@12
|
||||||
RtlGetProcessHeap@0
|
RtlGetProcessHeap@0
|
||||||
RtlInitAnsiString@8
|
RtlInitAnsiString@8
|
||||||
RtlInitializeContext@20
|
|
||||||
RtlInitString@8
|
RtlInitString@8
|
||||||
RtlInitUnicodeString@8
|
RtlInitUnicodeString@8
|
||||||
|
RtlInitializeContext@20
|
||||||
RtlIntegerToChar@16
|
RtlIntegerToChar@16
|
||||||
RtlIntegerToUnicodeString@12
|
RtlIntegerToUnicodeString@12
|
||||||
|
RtlIsDosDeviceName_U@4
|
||||||
|
RtlIsNameLegalDOS8Dot3@12
|
||||||
RtlLargeIntegerAdd@16
|
RtlLargeIntegerAdd@16
|
||||||
RtlLargeIntegerArithmeticShift@12
|
RtlLargeIntegerArithmeticShift@12
|
||||||
RtlLargeIntegerDivide@20
|
RtlLargeIntegerDivide@20
|
||||||
|
@ -521,6 +529,7 @@ RtlSizeHeap@12
|
||||||
RtlUnlockHeap@4
|
RtlUnlockHeap@4
|
||||||
RtlUnicodeStringToAnsiSize@4
|
RtlUnicodeStringToAnsiSize@4
|
||||||
RtlUnicodeStringToAnsiString@12
|
RtlUnicodeStringToAnsiString@12
|
||||||
|
RtlUnicodeStringToCountedOemString@12
|
||||||
RtlUnicodeStringToInteger@12
|
RtlUnicodeStringToInteger@12
|
||||||
RtlUnicodeStringToOemSize@4
|
RtlUnicodeStringToOemSize@4
|
||||||
RtlUnicodeStringToOemString@12
|
RtlUnicodeStringToOemString@12
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
; $Id: ntdll.edf,v 1.29 2000/02/05 16:07:10 ekohl Exp $
|
; $Id: ntdll.edf,v 1.30 2000/02/18 00:48:50 ekohl Exp $
|
||||||
;
|
;
|
||||||
; ReactOS Operating System
|
; ReactOS Operating System
|
||||||
;
|
;
|
||||||
|
@ -459,6 +459,10 @@ RtlDeNormalizeProcessParams=RtlDeNormalizeProcessParams@4
|
||||||
RtlDestroyEnvironment=RtlDestroyEnvironment@4
|
RtlDestroyEnvironment=RtlDestroyEnvironment@4
|
||||||
RtlDestroyHeap=RtlDestroyHeap@4
|
RtlDestroyHeap=RtlDestroyHeap@4
|
||||||
RtlDestroyProcessParameters=RtlDestroyProcessParameters@4
|
RtlDestroyProcessParameters=RtlDestroyProcessParameters@4
|
||||||
|
RtlDetermineDosPathNameType_U=RtlDetermineDosPathNameType_U@4
|
||||||
|
RtlDoesFileExists_U=RtlDoesFileExists_U@4
|
||||||
|
RtlDosPathNameToNtPathName_U=RtlDosPathNameToNtPathName_U@16
|
||||||
|
RtlDosSearchPath_U=RtlDosSearchPath_U@24
|
||||||
RtlDowncaseUnicodeString=RtlDowncaseUnicodeString@12
|
RtlDowncaseUnicodeString=RtlDowncaseUnicodeString@12
|
||||||
RtlEnlargedIntegerMultiply=RtlEnlargedIntegerMultiply@8
|
RtlEnlargedIntegerMultiply=RtlEnlargedIntegerMultiply@8
|
||||||
RtlEnlargedUnsignedDivide=RtlEnlargedUnsignedDivide@16
|
RtlEnlargedUnsignedDivide=RtlEnlargedUnsignedDivide@16
|
||||||
|
@ -476,15 +480,19 @@ RtlFreeHeap=RtlFreeHeap@12
|
||||||
RtlFreeUnicodeString=RtlFreeUnicodeString@4
|
RtlFreeUnicodeString=RtlFreeUnicodeString@4
|
||||||
RtlGetCurrentDirectory_U=RtlGetCurrentDirectory_U@8
|
RtlGetCurrentDirectory_U=RtlGetCurrentDirectory_U@8
|
||||||
RtlGetDaclSecurityDescriptor=RtlGetDaclSecurityDescriptor@16
|
RtlGetDaclSecurityDescriptor=RtlGetDaclSecurityDescriptor@16
|
||||||
|
RtlGetFullPathName_U=RtlGetFullPathName_U@16
|
||||||
RtlGetGroupSecurityDescriptor=RtlGetGroupSecurityDescriptor@12
|
RtlGetGroupSecurityDescriptor=RtlGetGroupSecurityDescriptor@12
|
||||||
|
RtlGetLongestNtPathLength=RtlGetLongestNtPathLength@0
|
||||||
RtlGetOwnerSecurityDescriptor=RtlGetOwnerSecurityDescriptor@12
|
RtlGetOwnerSecurityDescriptor=RtlGetOwnerSecurityDescriptor@12
|
||||||
RtlGetProcessHeap=RtlGetProcessHeap@0
|
RtlGetProcessHeap=RtlGetProcessHeap@0
|
||||||
RtlInitAnsiString=RtlInitAnsiString@8
|
RtlInitAnsiString=RtlInitAnsiString@8
|
||||||
RtlInitializeContext=RtlInitializeContext@20
|
|
||||||
RtlInitString=RtlInitString@8
|
RtlInitString=RtlInitString@8
|
||||||
RtlInitUnicodeString=RtlInitUnicodeString@8
|
RtlInitUnicodeString=RtlInitUnicodeString@8
|
||||||
|
RtlInitializeContext=RtlInitializeContext@20
|
||||||
RtlIntegerToChar=RtlIntegerToChar@16
|
RtlIntegerToChar=RtlIntegerToChar@16
|
||||||
RtlIntegerToUnicodeString=RtlIntegerToUnicodeString@12
|
RtlIntegerToUnicodeString=RtlIntegerToUnicodeString@12
|
||||||
|
RtlIsDosDeviceName_U=RtlIsDosDeviceName_U@4
|
||||||
|
RtlIsNameLegalDOS8Dot3=RtlIsNameLegalDOS8Dot3@12
|
||||||
RtlLargeIntegerAdd=RtlLargeIntegerAdd@16
|
RtlLargeIntegerAdd=RtlLargeIntegerAdd@16
|
||||||
RtlLargeIntegerArithmeticShift=RtlLargeIntegerArithmeticShift@12
|
RtlLargeIntegerArithmeticShift=RtlLargeIntegerArithmeticShift@12
|
||||||
RtlLargeIntegerDivide=RtlLargeIntegerDivide@20
|
RtlLargeIntegerDivide=RtlLargeIntegerDivide@20
|
||||||
|
@ -515,9 +523,13 @@ RtlSizeHeap=RtlSizeHeap@12
|
||||||
RtlUnlockHeap=RtlUnlockHeap@4
|
RtlUnlockHeap=RtlUnlockHeap@4
|
||||||
RtlUnicodeStringToAnsiSize=RtlUnicodeStringToAnsiSize@4
|
RtlUnicodeStringToAnsiSize=RtlUnicodeStringToAnsiSize@4
|
||||||
RtlUnicodeStringToAnsiString=RtlUnicodeStringToAnsiString@12
|
RtlUnicodeStringToAnsiString=RtlUnicodeStringToAnsiString@12
|
||||||
|
RtlUnicodeStringToCountedOemString=RtlUnicodeStringToCountedOemString@12
|
||||||
RtlUnicodeStringToInteger=RtlUnicodeStringToInteger@12
|
RtlUnicodeStringToInteger=RtlUnicodeStringToInteger@12
|
||||||
|
RtlUnicodeStringToOemSize=RtlUnicodeStringToOemSize@4
|
||||||
|
RtlUnicodeStringToOemString=RtlUnicodeStringToOemString@12
|
||||||
RtlUnicodeToMultiByteN=RtlUnicodeToMultiByteN@20
|
RtlUnicodeToMultiByteN=RtlUnicodeToMultiByteN@20
|
||||||
RtlUnicodeToMultiByteSize=RtlUnicodeToMultiByteSize@12
|
RtlUnicodeToMultiByteSize=RtlUnicodeToMultiByteSize@12
|
||||||
|
RtlUnicodeToOemN=RtlUnicodeToOemN@20
|
||||||
RtlUnwind=RtlUnwind@0
|
RtlUnwind=RtlUnwind@0
|
||||||
RtlUpcaseUnicodeChar=RtlUpcaseUnicodeChar@4
|
RtlUpcaseUnicodeChar=RtlUpcaseUnicodeChar@4
|
||||||
RtlUpcaseUnicodeString=RtlUpcaseUnicodeString@12
|
RtlUpcaseUnicodeString=RtlUpcaseUnicodeString@12
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: env.c,v 1.6 2000/02/13 16:05:16 dwelch Exp $
|
/* $Id: env.c,v 1.7 2000/02/18 00:49:11 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -16,7 +16,7 @@
|
||||||
#include <internal/teb.h>
|
#include <internal/teb.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
//#define NDEBUG
|
#define NDEBUG
|
||||||
#include <ntdll/ntdll.h>
|
#include <ntdll/ntdll.h>
|
||||||
|
|
||||||
/* FUNCTIONS *****************************************************************/
|
/* FUNCTIONS *****************************************************************/
|
||||||
|
@ -31,7 +31,7 @@ RtlCreateEnvironment (
|
||||||
MEMORY_BASIC_INFORMATION MemInfo;
|
MEMORY_BASIC_INFORMATION MemInfo;
|
||||||
PVOID EnvPtr = NULL;
|
PVOID EnvPtr = NULL;
|
||||||
NTSTATUS Status = STATUS_SUCCESS;
|
NTSTATUS Status = STATUS_SUCCESS;
|
||||||
ULONG RegionSize = 1;
|
ULONG RegionSize = PAGESIZE;
|
||||||
|
|
||||||
if (Initialize == FALSE)
|
if (Initialize == FALSE)
|
||||||
{
|
{
|
||||||
|
@ -77,7 +77,6 @@ RtlCreateEnvironment (
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
RegionSize = 1;
|
|
||||||
Status = NtAllocateVirtualMemory (NtCurrentProcess (),
|
Status = NtAllocateVirtualMemory (NtCurrentProcess (),
|
||||||
&EnvPtr,
|
&EnvPtr,
|
||||||
0,
|
0,
|
||||||
|
@ -85,8 +84,11 @@ RtlCreateEnvironment (
|
||||||
MEM_COMMIT,
|
MEM_COMMIT,
|
||||||
PAGE_READWRITE);
|
PAGE_READWRITE);
|
||||||
if (NT_SUCCESS(Status))
|
if (NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
memset (EnvPtr, 0, RegionSize);
|
||||||
*Environment = EnvPtr;
|
*Environment = EnvPtr;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
@ -112,52 +114,58 @@ NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlExpandEnvironmentStrings_U (
|
RtlExpandEnvironmentStrings_U (
|
||||||
PVOID Environment,
|
PVOID Environment,
|
||||||
PUNICODE_STRING src,
|
PUNICODE_STRING Source,
|
||||||
PUNICODE_STRING dst,
|
PUNICODE_STRING Destination,
|
||||||
PULONG Length
|
PULONG Length
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UNICODE_STRING var,val;
|
UNICODE_STRING var;
|
||||||
int src_len, dst_max, tail;
|
UNICODE_STRING val;
|
||||||
WCHAR *s,*d,*w;
|
|
||||||
BOOLEAN flag = FALSE;
|
|
||||||
NTSTATUS Status = STATUS_SUCCESS;
|
NTSTATUS Status = STATUS_SUCCESS;
|
||||||
|
BOOLEAN flag = FALSE;
|
||||||
|
PWSTR s;
|
||||||
|
PWSTR d;
|
||||||
|
PWSTR w;
|
||||||
|
int src_len;
|
||||||
|
int dst_max;
|
||||||
|
int tail;
|
||||||
|
|
||||||
src_len = src->Length / 2;
|
src_len = Source->Length / sizeof(WCHAR);
|
||||||
s = src->Buffer;
|
s = Source->Buffer;
|
||||||
dst_max = dst->MaximumLength / 2;
|
dst_max = Destination->MaximumLength / sizeof(WCHAR);
|
||||||
d = dst->Buffer;
|
d = Destination->Buffer;
|
||||||
|
|
||||||
while( src_len )
|
while (src_len)
|
||||||
{
|
{
|
||||||
if( *s == L'%' )
|
if (*s == L'%')
|
||||||
{
|
{
|
||||||
if( flag )
|
if (flag)
|
||||||
{
|
{
|
||||||
flag = FALSE;
|
flag = FALSE;
|
||||||
goto copy;
|
goto copy;
|
||||||
}
|
}
|
||||||
w = s + 1; tail = src_len - 1;
|
w = s + 1;
|
||||||
while( *w != L'%' && tail )
|
tail = src_len - 1;
|
||||||
|
while (*w != L'%' && tail)
|
||||||
{
|
{
|
||||||
w++;
|
w++;
|
||||||
tail--;
|
tail--;
|
||||||
}
|
}
|
||||||
if( !tail )
|
if (!tail)
|
||||||
goto copy;
|
goto copy;
|
||||||
|
|
||||||
var.Length = ( w - ( s + 1 ) ) * 2;
|
var.Length = (w - ( s + 1)) * sizeof(WCHAR);
|
||||||
var.MaximumLength = var.Length;
|
var.MaximumLength = var.Length;
|
||||||
var.Buffer = s + 1;
|
var.Buffer = s + 1;
|
||||||
|
|
||||||
val.Length = 0;
|
val.Length = 0;
|
||||||
val.MaximumLength = dst_max * 2;
|
val.MaximumLength = dst_max * sizeof(WCHAR);
|
||||||
val.Buffer = d;
|
val.Buffer = d;
|
||||||
Status = RtlQueryEnvironmentVariable_U (Environment, &var, &val );
|
Status = RtlQueryEnvironmentVariable_U (Environment, &var, &val);
|
||||||
if( Status >= 0 )
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
d += val.Length / 2;
|
d += val.Length / sizeof(WCHAR);
|
||||||
dst_max -= val.Length / 2;
|
dst_max -= val.Length / sizeof(WCHAR);
|
||||||
s = w + 1;
|
s = w + 1;
|
||||||
src_len = tail - 1;
|
src_len = tail - 1;
|
||||||
continue;
|
continue;
|
||||||
|
@ -165,8 +173,8 @@ RtlExpandEnvironmentStrings_U (
|
||||||
/* variable not found or buffer too small, just copy %var% */
|
/* variable not found or buffer too small, just copy %var% */
|
||||||
flag = TRUE;
|
flag = TRUE;
|
||||||
}
|
}
|
||||||
copy:;
|
copy:
|
||||||
if( !dst_max )
|
if (!dst_max)
|
||||||
{
|
{
|
||||||
Status = STATUS_BUFFER_TOO_SMALL;
|
Status = STATUS_BUFFER_TOO_SMALL;
|
||||||
break;
|
break;
|
||||||
|
@ -176,11 +184,11 @@ copy:;
|
||||||
dst_max--;
|
dst_max--;
|
||||||
src_len--;
|
src_len--;
|
||||||
}
|
}
|
||||||
dst->Length = ( d - dst->Buffer ) * 2;
|
Destination->Length = (d - Destination->Buffer) * sizeof(WCHAR);
|
||||||
if (Length)
|
if (Length != NULL)
|
||||||
*Length = dst->Length;
|
*Length = Destination->Length;
|
||||||
if( dst_max )
|
if (dst_max)
|
||||||
dst->Buffer[ dst->Length / 2 ] = 0;
|
Destination->Buffer[Destination->Length / sizeof(WCHAR)] = 0;
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
|
@ -209,71 +217,25 @@ RtlSetCurrentEnvironment (
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
}
|
}
|
||||||
|
|
||||||
#if 0
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlSetEnvironmentVariable (
|
RtlSetEnvironmentVariable (
|
||||||
PVOID *Environment,
|
PVOID *Environment,
|
||||||
PUNICODE_STRING Name,
|
PUNICODE_STRING Name,
|
||||||
PUNICODE_STRING Value
|
PUNICODE_STRING Value)
|
||||||
)
|
|
||||||
{
|
{
|
||||||
NTSTATUS Status;
|
|
||||||
PWSTR EnvPtr;
|
|
||||||
PWSTR EndPtr;
|
|
||||||
ULONG EnvLength;
|
|
||||||
|
|
||||||
Status = STATUS_VARIABLE_NOT_FOUND;
|
|
||||||
|
|
||||||
if (Environment != NULL)
|
|
||||||
{
|
|
||||||
EnvPtr = *Environment
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
RtlAcquirePebLock ();
|
|
||||||
EnvPtr = NtCurrentPeb()->ProcessParameters->Environment;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (EnvPtr != NULL)
|
|
||||||
{
|
|
||||||
/* get environment length */
|
|
||||||
EndPtr = EnvPtr;
|
|
||||||
while (*EndPtr)
|
|
||||||
{
|
|
||||||
while (*EndPtr++)
|
|
||||||
;
|
|
||||||
EndPtr++;
|
|
||||||
}
|
|
||||||
EnvLen = EndPtr - EnvPtr;
|
|
||||||
|
|
||||||
/* FIXME: add missing stuff */
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if (EnvPtr != *Environment)
|
|
||||||
RtlReleasePebLock ();
|
|
||||||
|
|
||||||
return Status;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
NTSTATUS
|
|
||||||
WINAPI
|
|
||||||
RtlSetEnvironmentVariable (
|
|
||||||
PVOID *Environment,
|
|
||||||
UNICODE_STRING *varname,
|
|
||||||
UNICODE_STRING *value)
|
|
||||||
{
|
|
||||||
UNICODE_STRING var;
|
|
||||||
MEMORY_BASIC_INFORMATION mbi;
|
MEMORY_BASIC_INFORMATION mbi;
|
||||||
|
UNICODE_STRING var;
|
||||||
int hole_len, new_len, env_len = 0;
|
int hole_len, new_len, env_len = 0;
|
||||||
WCHAR *new_env = 0, *env_end = 0, *wcs, *env, *val = 0, *tail = 0, *hole = 0;
|
WCHAR *new_env = 0, *env_end = 0, *wcs, *env, *val = 0, *tail = 0, *hole = 0;
|
||||||
ULONG size = 0, new_size;
|
ULONG size = 0, new_size;
|
||||||
LONG f = 1;
|
LONG f = 1;
|
||||||
NTSTATUS Status = STATUS_SUCCESS;
|
NTSTATUS Status = STATUS_SUCCESS;
|
||||||
|
|
||||||
|
DPRINT ("RtlSetEnvironmentVariable Environment %p Name %wZ Value %wZ\n",
|
||||||
|
Environment, Name, Value);
|
||||||
|
|
||||||
if (Environment)
|
if (Environment)
|
||||||
{
|
{
|
||||||
env = *Environment;
|
env = *Environment;
|
||||||
|
@ -284,26 +246,30 @@ RtlSetEnvironmentVariable (
|
||||||
env = NtCurrentPeb()->ProcessParameters->Environment;
|
env = NtCurrentPeb()->ProcessParameters->Environment;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( env )
|
if (env)
|
||||||
{
|
{
|
||||||
/* get environment length */
|
/* get environment length */
|
||||||
wcs = env_end = env;
|
wcs = env_end = env;
|
||||||
while( *env_end ) while( *env_end++ ); env_end++;
|
while (*env_end)
|
||||||
|
while (*env_end++)
|
||||||
|
;
|
||||||
|
env_end++;
|
||||||
env_len = env_end - env;
|
env_len = env_end - env;
|
||||||
|
DPRINT ("environment length %ld characters\n", env_len);
|
||||||
|
|
||||||
/* find where to insert */
|
/* find where to insert */
|
||||||
while( *wcs )
|
while (*wcs)
|
||||||
{
|
{
|
||||||
for (var.Buffer = wcs++; *wcs && *wcs != L'='; wcs++);
|
for (var.Buffer = wcs++; *wcs && *wcs != L'='; wcs++);
|
||||||
if( *wcs )
|
if (*wcs)
|
||||||
{
|
{
|
||||||
var.Length = ( wcs - var.Buffer ) * 2;
|
var.Length = (wcs - var.Buffer) * sizeof(WCHAR);
|
||||||
var.MaximumLength = var.Length;
|
var.MaximumLength = var.Length;
|
||||||
for ( val = ++wcs; *wcs; wcs++);
|
for ( val = ++wcs; *wcs; wcs++);
|
||||||
f = RtlCompareUnicodeString( &var, varname, TRUE );
|
f = RtlCompareUnicodeString (&var, Name, TRUE);
|
||||||
if( f >= 0 )
|
if (f >= 0)
|
||||||
{
|
{
|
||||||
if( f ) /* Insert before found */
|
if (f) /* Insert before found */
|
||||||
{
|
{
|
||||||
hole = tail = var.Buffer;
|
hole = tail = var.Buffer;
|
||||||
}
|
}
|
||||||
|
@ -320,25 +286,33 @@ RtlSetEnvironmentVariable (
|
||||||
hole = tail = wcs; /* Append to environment */
|
hole = tail = wcs; /* Append to environment */
|
||||||
}
|
}
|
||||||
|
|
||||||
found:;
|
found:
|
||||||
if( value )
|
if (Value->Length > 0)
|
||||||
{
|
{
|
||||||
hole_len = tail - hole;
|
hole_len = tail - hole;
|
||||||
/* calculate new environment size */
|
/* calculate new environment size */
|
||||||
new_size = value->Length + 2;
|
new_size = Value->Length + sizeof(WCHAR);
|
||||||
if( f )
|
/* adding new variable */
|
||||||
new_size += varname->Length + 2; /* adding new variable */
|
if (f)
|
||||||
new_len = new_size / 2;
|
new_size += Name->Length + sizeof(WCHAR);
|
||||||
|
new_len = new_size / sizeof(WCHAR);
|
||||||
if (hole_len < new_len)
|
if (hole_len < new_len)
|
||||||
{
|
{
|
||||||
/* we must enlarge environment size, let's check the size of available
|
/* we must enlarge environment size */
|
||||||
* memory */
|
/* let's check the size of available memory */
|
||||||
new_size += ( env_len - hole_len ) * 2;
|
new_size += (env_len - hole_len) * sizeof(WCHAR);
|
||||||
|
new_size = ROUNDUP(new_size, PAGESIZE);
|
||||||
mbi.RegionSize = 0;
|
mbi.RegionSize = 0;
|
||||||
|
DPRINT("new_size %lu\n", new_size);
|
||||||
|
|
||||||
if (env)
|
if (env)
|
||||||
{
|
{
|
||||||
Status = NtQueryVirtualMemory( (HANDLE)-1, env, 0, &mbi, sizeof(mbi), NULL );
|
Status = NtQueryVirtualMemory (NtCurrentProcess (),
|
||||||
|
env,
|
||||||
|
0,
|
||||||
|
&mbi,
|
||||||
|
sizeof(mbi),
|
||||||
|
NULL);
|
||||||
if (!NT_SUCCESS(Status))
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
|
@ -349,7 +323,12 @@ found:;
|
||||||
if (new_size > mbi.RegionSize)
|
if (new_size > mbi.RegionSize)
|
||||||
{
|
{
|
||||||
/* reallocate memory area */
|
/* reallocate memory area */
|
||||||
Status = NtAllocateVirtualMemory( (HANDLE)-1, (VOID**)&new_env, 0, &new_size, MEM_COMMIT, PAGE_READWRITE );
|
Status = NtAllocateVirtualMemory (NtCurrentProcess (),
|
||||||
|
(VOID**)&new_env,
|
||||||
|
0,
|
||||||
|
&new_size,
|
||||||
|
MEM_COMMIT,
|
||||||
|
PAGE_READWRITE);
|
||||||
if (!NT_SUCCESS(Status))
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
|
@ -358,8 +337,10 @@ found:;
|
||||||
|
|
||||||
if (env)
|
if (env)
|
||||||
{
|
{
|
||||||
memmove( new_env, env, ( hole - env ) * 2 );
|
memmove (new_env,
|
||||||
hole = new_env + ( hole - env );
|
env,
|
||||||
|
(hole - env) * sizeof(WCHAR));
|
||||||
|
hole = new_env + (hole - env);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -372,8 +353,9 @@ found:;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* move tail */
|
/* move tail */
|
||||||
memmove ( hole + new_len, tail, ( env_end - tail ) * 2 );
|
memmove (hole + new_len, tail, (env_end - tail) * sizeof(WCHAR));
|
||||||
if( new_env )
|
|
||||||
|
if (new_env)
|
||||||
{
|
{
|
||||||
/* we reallocated environment, let's free the old one */
|
/* we reallocated environment, let's free the old one */
|
||||||
if (Environment)
|
if (Environment)
|
||||||
|
@ -383,64 +365,79 @@ found:;
|
||||||
|
|
||||||
if (env)
|
if (env)
|
||||||
{
|
{
|
||||||
NtFreeVirtualMemory (NtCurrentProcess(),
|
size = 0;
|
||||||
|
CHECKPOINT;
|
||||||
|
DPRINT ("env %x\n", env);
|
||||||
|
DPRINT ("&env %x\n", &env);
|
||||||
|
NtFreeVirtualMemory (NtCurrentProcess (),
|
||||||
(VOID**)&env,
|
(VOID**)&env,
|
||||||
&size,
|
&size,
|
||||||
MEM_RELEASE);
|
MEM_RELEASE);
|
||||||
|
CHECKPOINT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* and now copy given stuff */
|
/* and now copy given stuff */
|
||||||
if( f )
|
if (f)
|
||||||
{
|
{
|
||||||
/* copy variable name and '=' sign */
|
/* copy variable name and '=' character */
|
||||||
memmove (hole, varname->Buffer, varname->Length);
|
memmove (hole, Name->Buffer, Name->Length);
|
||||||
hole += varname->Length / 2; *hole++ = L'=';
|
hole += Name->Length / sizeof(WCHAR);
|
||||||
|
*hole++ = L'=';
|
||||||
}
|
}
|
||||||
|
|
||||||
/* copy value */
|
/* copy value */
|
||||||
memmove( hole, value->Buffer, value->Length );
|
memmove (hole, Value->Buffer, Value->Length);
|
||||||
hole += value->Length / 2; *hole = 0;
|
hole += Value->Length / sizeof(WCHAR);
|
||||||
|
*hole = 0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (!f)
|
/* remove the environment variable */
|
||||||
memmove (hole, tail, ( env_end - tail ) * 2 ); /* remove it */
|
if (f == 0)
|
||||||
|
memmove (hole,
|
||||||
|
tail,
|
||||||
|
(env_end - tail) * sizeof(WCHAR));
|
||||||
else
|
else
|
||||||
Status = STATUS_VARIABLE_NOT_FOUND; /* notingh to remove*/
|
Status = STATUS_VARIABLE_NOT_FOUND;
|
||||||
}
|
}
|
||||||
|
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
return Status;
|
return Status;
|
||||||
}
|
}
|
||||||
//#endif
|
|
||||||
|
|
||||||
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlQueryEnvironmentVariable_U (
|
RtlQueryEnvironmentVariable_U (
|
||||||
PVOID env,
|
PVOID Environment,
|
||||||
UNICODE_STRING *varname,
|
PUNICODE_STRING Name,
|
||||||
UNICODE_STRING *value
|
PUNICODE_STRING Value
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
NTSTATUS Status = STATUS_VARIABLE_NOT_FOUND;
|
NTSTATUS Status;
|
||||||
WCHAR *wcs,*var,*val;
|
PWSTR wcs;
|
||||||
int varlen, len;
|
PWSTR var;
|
||||||
|
PWSTR val;
|
||||||
|
int varlen;
|
||||||
|
int len;
|
||||||
|
|
||||||
if (!env)
|
DPRINT("RtlQueryEnvironmentVariable_U Environment %p Variable %wZ Value %p\n",
|
||||||
env = NtCurrentPeb()->ProcessParameters->Environment;
|
Environment, varname, Value);
|
||||||
|
|
||||||
if (!env)
|
if (!Environment)
|
||||||
return Status;
|
Environment = NtCurrentPeb()->ProcessParameters->Environment;
|
||||||
|
|
||||||
value->Length = 0;
|
if (!Environment)
|
||||||
if (env == NtCurrentPeb()->ProcessParameters->Environment)
|
return STATUS_VARIABLE_NOT_FOUND;
|
||||||
|
|
||||||
|
Value->Length = 0;
|
||||||
|
if (Environment == NtCurrentPeb()->ProcessParameters->Environment)
|
||||||
RtlAcquirePebLock();
|
RtlAcquirePebLock();
|
||||||
|
|
||||||
wcs = env;
|
wcs = Environment;
|
||||||
len = varname->Length / 2;
|
len = Name->Length / sizeof(WCHAR);
|
||||||
while( *wcs )
|
while (*wcs)
|
||||||
{
|
{
|
||||||
for (var = wcs++; *wcs && *wcs != L'='; wcs++)
|
for (var = wcs++; *wcs && *wcs != L'='; wcs++)
|
||||||
;
|
;
|
||||||
|
@ -450,13 +447,15 @@ RtlQueryEnvironmentVariable_U (
|
||||||
varlen = wcs - var;
|
varlen = wcs - var;
|
||||||
for (val = ++wcs; *wcs; wcs++)
|
for (val = ++wcs; *wcs; wcs++)
|
||||||
;
|
;
|
||||||
|
|
||||||
if (varlen == len &&
|
if (varlen == len &&
|
||||||
!_wcsnicmp (var, varname->Buffer, len))
|
!_wcsnicmp (var, Name->Buffer, len))
|
||||||
{
|
{
|
||||||
value->Length = (wcs - val) * sizeof(WCHAR);
|
Value->Length = (wcs - val) * sizeof(WCHAR);
|
||||||
if (value->Length < value->MaximumLength)
|
if (Value->Length < Value->MaximumLength)
|
||||||
{
|
{
|
||||||
wcscpy (value->Buffer, val);
|
wcscpy (Value->Buffer, val);
|
||||||
|
DPRINT("Value %S\n", val);
|
||||||
Status = STATUS_SUCCESS;
|
Status = STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -464,7 +463,7 @@ RtlQueryEnvironmentVariable_U (
|
||||||
Status = STATUS_BUFFER_TOO_SMALL;
|
Status = STATUS_BUFFER_TOO_SMALL;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (env == NtCurrentPeb()->ProcessParameters->Environment)
|
if (Environment == NtCurrentPeb()->ProcessParameters->Environment)
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
|
|
||||||
return Status;
|
return Status;
|
||||||
|
@ -473,10 +472,10 @@ RtlQueryEnvironmentVariable_U (
|
||||||
wcs++;
|
wcs++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (env == NtCurrentPeb()->ProcessParameters->Environment)
|
if (Environment == NtCurrentPeb()->ProcessParameters->Environment)
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
|
|
||||||
return Status;
|
return STATUS_VARIABLE_NOT_FOUND;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* EOF */
|
/* EOF */
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: path.c,v 1.1 2000/02/05 16:08:49 ekohl Exp $
|
/* $Id: path.c,v 1.2 2000/02/18 00:49:11 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -29,6 +29,91 @@
|
||||||
|
|
||||||
/* FUNCTIONS *****************************************************************/
|
/* FUNCTIONS *****************************************************************/
|
||||||
|
|
||||||
|
|
||||||
|
static
|
||||||
|
ULONG
|
||||||
|
RtlpGetDotSequence (PWSTR p)
|
||||||
|
{
|
||||||
|
ULONG Count = 0;
|
||||||
|
|
||||||
|
for (;;)
|
||||||
|
{
|
||||||
|
if (*p == '.')
|
||||||
|
Count++;
|
||||||
|
else if ((*p == '\\' || *p == '\0') && Count)
|
||||||
|
return Count;
|
||||||
|
else
|
||||||
|
return 0;
|
||||||
|
p++;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static
|
||||||
|
VOID
|
||||||
|
RtlpEatPath (
|
||||||
|
PWSTR Path
|
||||||
|
)
|
||||||
|
{
|
||||||
|
PWSTR p, prev;
|
||||||
|
|
||||||
|
p = Path + 2;
|
||||||
|
prev = p;
|
||||||
|
|
||||||
|
while ((*p) != 0 || ((*p) == L'\\' && (*(p+1)) == 0))
|
||||||
|
{
|
||||||
|
ULONG DotLen;
|
||||||
|
|
||||||
|
DotLen = RtlpGetDotSequence (p+1);
|
||||||
|
DPRINT("DotSequenceLength %u\n", DotLen);
|
||||||
|
DPRINT("prev %S p %S\n",prev,p);
|
||||||
|
|
||||||
|
if (DotLen == 0)
|
||||||
|
{
|
||||||
|
prev = p;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
p++;
|
||||||
|
}
|
||||||
|
while ((*p) != 0 && (*p) != L'\\');
|
||||||
|
}
|
||||||
|
else if (DotLen == 1)
|
||||||
|
{
|
||||||
|
wcscpy (p, p+2);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (DotLen > 2)
|
||||||
|
{
|
||||||
|
int n = DotLen - 2;
|
||||||
|
|
||||||
|
while (n > 0 && prev > (Path + 2))
|
||||||
|
{
|
||||||
|
prev--;
|
||||||
|
if ((*prev) == L'\\')
|
||||||
|
n--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (*(p + DotLen + 1) == 0)
|
||||||
|
*(prev + 1) = 0;
|
||||||
|
else
|
||||||
|
wcscpy (prev, p + DotLen + 1);
|
||||||
|
p = prev;
|
||||||
|
if (prev > (Path + 2))
|
||||||
|
{
|
||||||
|
prev--;
|
||||||
|
while ((*prev) != L'\\')
|
||||||
|
{
|
||||||
|
prev--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
ULONG
|
ULONG
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlGetLongestNtPathLength (VOID)
|
RtlGetLongestNtPathLength (VOID)
|
||||||
|
@ -161,7 +246,7 @@ RtlGetCurrentDirectory_U (
|
||||||
PWSTR Buffer
|
PWSTR Buffer
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
DWORD Length;
|
ULONG Length;
|
||||||
PCURDIR cd;
|
PCURDIR cd;
|
||||||
|
|
||||||
DPRINT ("RtlGetCurrentDirectory %lu %p\n", MaximumLength, Buffer);
|
DPRINT ("RtlGetCurrentDirectory %lu %p\n", MaximumLength, Buffer);
|
||||||
|
@ -170,10 +255,12 @@ RtlGetCurrentDirectory_U (
|
||||||
|
|
||||||
RtlAcquirePebLock();
|
RtlAcquirePebLock();
|
||||||
Length = cd->DosPath.Length / sizeof(WCHAR);
|
Length = cd->DosPath.Length / sizeof(WCHAR);
|
||||||
if (cd->DosPath.Buffer[Length - 2] != L':')
|
if (cd->DosPath.Buffer[Length - 1] == L'\\' &&
|
||||||
|
cd->DosPath.Buffer[Length - 2] != L':')
|
||||||
Length--;
|
Length--;
|
||||||
|
|
||||||
DPRINT ("cd->DosPath.Buffer %S\n", cd->DosPath.Buffer);
|
DPRINT ("cd->DosPath.Buffer %S Length %d\n",
|
||||||
|
cd->DosPath.Buffer, Length);
|
||||||
|
|
||||||
if (MaximumLength / sizeof(WCHAR) > Length)
|
if (MaximumLength / sizeof(WCHAR) > Length)
|
||||||
{
|
{
|
||||||
|
@ -202,13 +289,14 @@ RtlSetCurrentDirectory_U (
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UNICODE_STRING full;
|
UNICODE_STRING full;
|
||||||
OBJECT_ATTRIBUTES obj;
|
OBJECT_ATTRIBUTES Attr;
|
||||||
IO_STATUS_BLOCK iosb;
|
IO_STATUS_BLOCK iosb;
|
||||||
PCURDIR cd;
|
PCURDIR cd;
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
ULONG size;
|
ULONG size;
|
||||||
HANDLE handle = NULL;
|
HANDLE handle = NULL;
|
||||||
WCHAR *wcs,*buf = 0;
|
PWSTR wcs;
|
||||||
|
PWSTR buf = 0;
|
||||||
|
|
||||||
DPRINT ("RtlSetCurrentDirectory %wZ\n", name);
|
DPRINT ("RtlSetCurrentDirectory %wZ\n", name);
|
||||||
|
|
||||||
|
@ -247,16 +335,15 @@ RtlSetCurrentDirectory_U (
|
||||||
return STATUS_OBJECT_NAME_INVALID;
|
return STATUS_OBJECT_NAME_INVALID;
|
||||||
}
|
}
|
||||||
|
|
||||||
obj.Length = sizeof(obj);
|
InitializeObjectAttributes (&Attr,
|
||||||
obj.RootDirectory = 0;
|
&full,
|
||||||
obj.ObjectName = &full;
|
OBJ_CASE_INSENSITIVE | OBJ_INHERIT,
|
||||||
obj.Attributes = OBJ_CASE_INSENSITIVE | OBJ_INHERIT;
|
NULL,
|
||||||
obj.SecurityDescriptor = 0;
|
NULL);
|
||||||
obj.SecurityQualityOfService = 0;
|
|
||||||
|
|
||||||
Status = NtOpenFile (&handle,
|
Status = NtOpenFile (&handle,
|
||||||
SYNCHRONIZE | FILE_TRAVERSE,
|
SYNCHRONIZE | FILE_TRAVERSE,
|
||||||
&obj,
|
&Attr,
|
||||||
&iosb,
|
&iosb,
|
||||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||||
FILE_DIRECTORY_FILE | FILE_SYNCHRONOUS_IO_NONALERT);
|
FILE_DIRECTORY_FILE | FILE_SYNCHRONOUS_IO_NONALERT);
|
||||||
|
@ -307,10 +394,10 @@ RtlSetCurrentDirectory_U (
|
||||||
ULONG
|
ULONG
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlGetFullPathName_U (
|
RtlGetFullPathName_U (
|
||||||
WCHAR *dosname,
|
PWSTR DosName,
|
||||||
ULONG size,
|
ULONG size,
|
||||||
WCHAR *buf,
|
PWSTR buf,
|
||||||
WCHAR **shortname
|
PWSTR *FilePart
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
WCHAR *wcs, var[4], drive;
|
WCHAR *wcs, var[4], drive;
|
||||||
|
@ -318,34 +405,34 @@ RtlGetFullPathName_U (
|
||||||
DWORD offs, sz, type;
|
DWORD offs, sz, type;
|
||||||
UNICODE_STRING usvar, pfx;
|
UNICODE_STRING usvar, pfx;
|
||||||
PCURDIR cd;
|
PCURDIR cd;
|
||||||
NTSTATUS status;
|
NTSTATUS Status;
|
||||||
|
|
||||||
DPRINT("RtlGetFullPathName_U %S %ld %p %p\n",
|
DPRINT("RtlGetFullPathName_U %S %ld %p %p\n",
|
||||||
dosname, size, buf, shortname);
|
DosName, size, buf, FilePart);
|
||||||
|
|
||||||
if (!dosname || !*dosname)
|
if (!DosName || !*DosName)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
len = wcslen (dosname);
|
len = wcslen (DosName);
|
||||||
|
|
||||||
/* strip trailing spaces */
|
/* strip trailing spaces */
|
||||||
while (len && dosname[len - 1] == L' ')
|
while (len && DosName[len - 1] == L' ')
|
||||||
len--;
|
len--;
|
||||||
if (!len)
|
if (!len)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
/* strip trailing path separator */
|
/* strip trailing path separator */
|
||||||
if (IS_PATH_SEPARATOR(dosname[len - 1]))
|
if (IS_PATH_SEPARATOR(DosName[len - 1]))
|
||||||
len--;
|
len--;
|
||||||
if (!len)
|
if (!len)
|
||||||
return 0;
|
return 0;
|
||||||
if (shortname)
|
if (FilePart)
|
||||||
*shortname = 0;
|
*FilePart = L'\0';
|
||||||
memset (buf, 0, size);
|
memset (buf, 0, size);
|
||||||
|
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
/* check for DOS device name */
|
/* check for DOS device name */
|
||||||
sz = RtlIsDosDeviceName_U (dosname);
|
sz = RtlIsDosDeviceName_U (DosName);
|
||||||
if (sz)
|
if (sz)
|
||||||
{
|
{
|
||||||
offs = sz >> 17;
|
offs = sz >> 17;
|
||||||
|
@ -353,12 +440,12 @@ CHECKPOINT;
|
||||||
if (sz + 8 >= size)
|
if (sz + 8 >= size)
|
||||||
return sz + 10;
|
return sz + 10;
|
||||||
wcscpy (buf, L"\\\\.\\");
|
wcscpy (buf, L"\\\\.\\");
|
||||||
wcsncat (buf, dosname + offs, sz / 2);
|
wcsncat (buf, DosName + offs, sz / sizeof(WCHAR));
|
||||||
return sz + 8;
|
return sz + 8;
|
||||||
}
|
}
|
||||||
|
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
type = RtlDetermineDosPathNameType_U (dosname);
|
type = RtlDetermineDosPathNameType_U (DosName);
|
||||||
|
|
||||||
RtlAcquirePebLock();
|
RtlAcquirePebLock();
|
||||||
|
|
||||||
|
@ -367,13 +454,16 @@ DPRINT("type %ld\n", type);
|
||||||
switch (type)
|
switch (type)
|
||||||
{
|
{
|
||||||
case 1: /* \\xxx or \\.xxx */
|
case 1: /* \\xxx or \\.xxx */
|
||||||
case 2: /* x:\xxx */
|
|
||||||
case 6: /* \\.\xxx */
|
case 6: /* \\.\xxx */
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 2: /* x:\xxx */
|
||||||
|
*DosName = towupper (*DosName);
|
||||||
|
break;
|
||||||
|
|
||||||
case 3: /* x:xxx */
|
case 3: /* x:xxx */
|
||||||
drive = towupper (*dosname);
|
drive = towupper (*DosName);
|
||||||
dosname += 2;
|
DosName += 2;
|
||||||
len -= 2;
|
len -= 2;
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
if (drive == towupper (cd->DosPath.Buffer[0]))
|
if (drive == towupper (cd->DosPath.Buffer[0]))
|
||||||
|
@ -384,28 +474,30 @@ CHECKPOINT;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
usvar.Length = 2 * swprintf( var, L"=%c:", drive );
|
usvar.Length = 2 * swprintf (var, L"=%c:", drive);
|
||||||
usvar.MaximumLength = 8;
|
usvar.MaximumLength = 8;
|
||||||
usvar.Buffer = var;
|
usvar.Buffer = var;
|
||||||
pfx.Length = 0;
|
pfx.Length = 0;
|
||||||
pfx.MaximumLength = size;
|
pfx.MaximumLength = size;
|
||||||
pfx.Buffer = buf;
|
pfx.Buffer = buf;
|
||||||
status = RtlQueryEnvironmentVariable_U( 0, &usvar, &pfx );
|
Status = RtlQueryEnvironmentVariable_U (NULL,
|
||||||
|
&usvar,
|
||||||
|
&pfx);
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
if (!NT_SUCCESS(status))
|
if (!NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
if (status == STATUS_BUFFER_TOO_SMALL)
|
if (Status == STATUS_BUFFER_TOO_SMALL)
|
||||||
return pfx.Length + len * 2 + 2;
|
return pfx.Length + len * 2 + 2;
|
||||||
swprintf( buf, L"%c:\\", drive );
|
swprintf (buf, L"%c:\\", drive);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
if( pfx.Length > 6 )
|
if (pfx.Length > 6)
|
||||||
{
|
{
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
buf[ pfx.Length / 2 ] = L'\\';
|
buf[pfx.Length / 2] = L'\\';
|
||||||
pfx.Length += 2;
|
pfx.Length += 2;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -418,11 +510,6 @@ CHECKPOINT;
|
||||||
|
|
||||||
case 5: /* xxx */
|
case 5: /* xxx */
|
||||||
wcscpy (buf, cd->DosPath.Buffer);
|
wcscpy (buf, cd->DosPath.Buffer);
|
||||||
if (*dosname == L'.')
|
|
||||||
{
|
|
||||||
dosname += 2;
|
|
||||||
len -= 2;
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 7: /* \\. */
|
case 7: /* \\. */
|
||||||
|
@ -434,26 +521,28 @@ CHECKPOINT;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
CHECKPOINT;
|
DPRINT("buf \'%S\' DosName \'%S\'\n", buf, DosName);
|
||||||
/* add dosname to prefix */
|
/* add dosname to prefix */
|
||||||
wcsncat (buf, dosname, len);
|
wcsncat (buf, DosName, len);
|
||||||
|
|
||||||
CHECKPOINT;
|
CHECKPOINT;
|
||||||
/* replace slashes */
|
/* replace slashes */
|
||||||
for (wcs = buf; *wcs; wcs++ )
|
for (wcs = buf; *wcs; wcs++)
|
||||||
if (*wcs == L'/')
|
if (*wcs == L'/')
|
||||||
*wcs = L'\\';
|
*wcs = L'\\';
|
||||||
|
|
||||||
|
RtlpEatPath (buf);
|
||||||
|
|
||||||
len = wcslen (buf);
|
len = wcslen (buf);
|
||||||
|
|
||||||
/* find shortname */
|
/* find file part */
|
||||||
if (shortname)
|
if (FilePart)
|
||||||
{
|
{
|
||||||
for (wcs = buf + len - 1; wcs >= buf; wcs--)
|
for (wcs = buf + len - 1; wcs >= buf; wcs--)
|
||||||
{
|
{
|
||||||
if (*wcs == L'\\')
|
if (*wcs == L'\\')
|
||||||
{
|
{
|
||||||
*shortname = wcs + 1;
|
*FilePart = wcs + 1;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -470,94 +559,109 @@ STDCALL
|
||||||
RtlDosPathNameToNtPathName_U (
|
RtlDosPathNameToNtPathName_U (
|
||||||
PWSTR dosname,
|
PWSTR dosname,
|
||||||
PUNICODE_STRING ntname,
|
PUNICODE_STRING ntname,
|
||||||
PWSTR *shortname,
|
PWSTR *FilePart,
|
||||||
PCURDIR nah
|
PCURDIR nah
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UNICODE_STRING us;
|
UNICODE_STRING us;
|
||||||
PCURDIR cd;
|
PCURDIR cd;
|
||||||
DWORD type, size;
|
ULONG Type;
|
||||||
WCHAR *buf = 0, fullname[517];
|
ULONG Size;
|
||||||
int offs, len;
|
ULONG Length;
|
||||||
|
ULONG Offset;
|
||||||
|
WCHAR fullname[2*MAX_PATH];
|
||||||
|
PWSTR Buffer = NULL;
|
||||||
|
|
||||||
RtlAcquirePebLock();
|
RtlAcquirePebLock ();
|
||||||
|
|
||||||
RtlInitUnicodeString( &us, dosname );
|
RtlInitUnicodeString (&us, dosname);
|
||||||
if( us.Length > 8 )
|
if (us.Length > 8)
|
||||||
{
|
{
|
||||||
buf = us.Buffer;
|
Buffer = us.Buffer;
|
||||||
/* check for "\\?\" - allows to use very long filenames ( up to 32k ) */
|
/* check for "\\?\" - allows to use very long filenames ( up to 32k ) */
|
||||||
if (buf[0] == L'\\' && buf[1] == L'\\' && buf[2] == L'?' && buf[3] == L'\\')
|
if (Buffer[0] == L'\\' && Buffer[1] == L'\\' &&
|
||||||
|
Buffer[2] == L'?' && Buffer[3] == L'\\')
|
||||||
{
|
{
|
||||||
// if( f_77F68606( &us, ntname, shortname, nah ) )
|
// if( f_77F68606( &us, ntname, shortname, nah ) )
|
||||||
// goto out;
|
// {
|
||||||
buf = 0;
|
// RtlReleasePebLock ();
|
||||||
goto fail;
|
// return TRUE;
|
||||||
|
// }
|
||||||
|
Buffer = NULL;
|
||||||
|
RtlReleasePebLock ();
|
||||||
|
return FALSE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
buf = RtlAllocateHeap (RtlGetProcessHeap (),
|
Buffer = RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
0,
|
0,
|
||||||
sizeof( fullname ) + MAX_PFX_SIZE );
|
sizeof( fullname ) + MAX_PFX_SIZE);
|
||||||
if (!buf)
|
if (Buffer == NULL)
|
||||||
goto fail;
|
{
|
||||||
|
RtlReleasePebLock ();
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
size = RtlGetFullPathName_U( dosname, sizeof( fullname ), fullname, shortname );
|
Size = RtlGetFullPathName_U (dosname,
|
||||||
if( !size || size > 0x208 )
|
sizeof(fullname),
|
||||||
goto fail;
|
fullname,
|
||||||
|
FilePart);
|
||||||
|
if (Size == 0 || Size > MAX_PATH * sizeof(WCHAR))
|
||||||
|
{
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
Buffer);
|
||||||
|
RtlReleasePebLock ();
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
/* Set NT prefix */
|
/* Set NT prefix */
|
||||||
offs = 0;
|
Offset = 0;
|
||||||
wcscpy (buf, L"\\??\\");
|
wcscpy (Buffer, L"\\??\\");
|
||||||
|
|
||||||
type = RtlDetermineDosPathNameType_U( fullname );
|
Type = RtlDetermineDosPathNameType_U (fullname);
|
||||||
switch (type)
|
switch (Type)
|
||||||
{
|
{
|
||||||
case 1:
|
case 1:
|
||||||
wcscat( buf, L"UNC\\" );
|
wcscat (Buffer, L"UNC\\");
|
||||||
offs = 2;
|
Offset = 2;
|
||||||
break; /* \\xxx */
|
break; /* \\xxx */
|
||||||
|
|
||||||
case 6:
|
case 6:
|
||||||
offs = 4;
|
Offset = 4;
|
||||||
break; /* \\.\xxx */
|
break; /* \\.\xxx */
|
||||||
}
|
}
|
||||||
wcscat( buf, fullname + offs );
|
wcscat (Buffer, fullname + Offset);
|
||||||
len = wcslen( buf );
|
Length = wcslen (Buffer);
|
||||||
|
|
||||||
/* Set NT filename */
|
/* set NT filename */
|
||||||
ntname->Length = len * 2;
|
ntname->Length = Length * sizeof(WCHAR);
|
||||||
ntname->MaximumLength = sizeof( fullname ) + MAX_PFX_SIZE;
|
ntname->MaximumLength = sizeof(fullname) + MAX_PFX_SIZE;
|
||||||
ntname->Buffer = buf;
|
ntname->Buffer = Buffer;
|
||||||
|
|
||||||
/* Set shortname if possible */
|
/* set pointer to file part if possible */
|
||||||
if( shortname && *shortname )
|
if (FilePart && *FilePart)
|
||||||
*shortname = buf + len - wcslen( *shortname );
|
*FilePart = Buffer + Length - wcslen (*FilePart);
|
||||||
|
|
||||||
/* Set name and handle structure if possible */
|
/* Set name and handle structure if possible */
|
||||||
if( nah )
|
if (nah)
|
||||||
{
|
{
|
||||||
memset( nah, 0, sizeof(CURDIR));
|
memset (nah, 0, sizeof(CURDIR));
|
||||||
cd = &(NtCurrentPeb ()->ProcessParameters->CurrentDirectory);
|
cd = &(NtCurrentPeb ()->ProcessParameters->CurrentDirectory);
|
||||||
if (type == 5 && cd->Handle &&
|
if (Type == 5 && cd->Handle &&
|
||||||
!_wcsnicmp (cd->DosPath.Buffer, fullname, cd->DosPath.Length / 2))
|
!_wcsnicmp (cd->DosPath.Buffer, fullname, cd->DosPath.Length / 2))
|
||||||
{
|
{
|
||||||
len = (( cd->DosPath.Length / 2 ) - offs ) + ( ( type == 1 ) ? 8 : 4 );
|
Length = ((cd->DosPath.Length / sizeof(WCHAR)) - Offset) + ((Type == 1) ? 8 : 4);
|
||||||
nah->DosPath.Buffer = buf + len;
|
nah->DosPath.Buffer = Buffer + Length;
|
||||||
nah->DosPath.Length = ntname->Length - ( len * 2 );
|
nah->DosPath.Length = ntname->Length - (Length * sizeof(WCHAR));
|
||||||
nah->DosPath.MaximumLength = nah->DosPath.Length;
|
nah->DosPath.MaximumLength = nah->DosPath.Length;
|
||||||
nah->Handle = cd->Handle;
|
nah->Handle = cd->Handle;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* out:; */
|
|
||||||
RtlReleasePebLock();
|
|
||||||
return TRUE;
|
|
||||||
|
|
||||||
fail:;
|
|
||||||
if( buf )
|
|
||||||
RtlFreeHeap (RtlGetProcessHeap (), 0, buf );
|
|
||||||
RtlReleasePebLock();
|
RtlReleasePebLock();
|
||||||
return FALSE;
|
|
||||||
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -569,115 +673,135 @@ RtlDosSearchPath_U (
|
||||||
WCHAR *ext,
|
WCHAR *ext,
|
||||||
ULONG buf_sz,
|
ULONG buf_sz,
|
||||||
WCHAR *buffer,
|
WCHAR *buffer,
|
||||||
WCHAR **shortname
|
PWSTR *FilePart
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
DWORD type;
|
ULONG Type;
|
||||||
ULONG len = 0;
|
ULONG Length = 0;
|
||||||
WCHAR *full_name,*wcs,*path;
|
PWSTR full_name;
|
||||||
|
PWSTR wcs;
|
||||||
|
PWSTR path;
|
||||||
|
|
||||||
type = RtlDetermineDosPathNameType_U( name );
|
Type = RtlDetermineDosPathNameType_U (name);
|
||||||
|
|
||||||
if( type != 5 )
|
if (Type == 5)
|
||||||
{
|
{
|
||||||
if( RtlDoesFileExists_U( name ) )
|
Length = wcslen (sp);
|
||||||
{
|
Length += wcslen (name);
|
||||||
len = RtlGetFullPathName_U( name, buf_sz, buffer, shortname );
|
if (wcschr (name, L'.'))
|
||||||
}
|
ext = NULL;
|
||||||
}
|
if (ext != NULL)
|
||||||
else
|
Length += wcslen (ext);
|
||||||
{
|
|
||||||
len = wcslen( sp );
|
|
||||||
len += wcslen( name );
|
|
||||||
if( wcschr( name, L'.' ) ) ext = 0;
|
|
||||||
if( ext ) len += wcslen( ext );
|
|
||||||
|
|
||||||
full_name = (WCHAR*)RtlAllocateHeap (RtlGetProcessHeap (), 0, ( len + 1 ) * 2 );
|
full_name = (WCHAR*)RtlAllocateHeap (RtlGetProcessHeap (),
|
||||||
len = 0;
|
0,
|
||||||
if( full_name )
|
(Length + 1) * sizeof(WCHAR));
|
||||||
|
Length = 0;
|
||||||
|
if (full_name != NULL)
|
||||||
{
|
{
|
||||||
path = sp;
|
path = sp;
|
||||||
while( *path )
|
while (*path)
|
||||||
{
|
{
|
||||||
wcs = full_name;
|
wcs = full_name;
|
||||||
while( *path && *path != L';' ) *wcs++ = *path++;
|
while (*path && *path != L';')
|
||||||
if( *path ) path++;
|
*wcs++ = *path++;
|
||||||
if( wcs != full_name && *(wcs - 1) != L'\\' ) *wcs++ = L'\\';
|
if (*path)
|
||||||
wcscpy( wcs, name );
|
path++;
|
||||||
if( ext ) wcscat( wcs, ext );
|
if (wcs != full_name && *(wcs - 1) != L'\\')
|
||||||
if( RtlDoesFileExists_U( full_name ) )
|
*wcs++ = L'\\';
|
||||||
|
wcscpy (wcs, name);
|
||||||
|
if (ext)
|
||||||
|
wcscat (wcs, ext);
|
||||||
|
if (RtlDoesFileExists_U (full_name))
|
||||||
{
|
{
|
||||||
len = RtlGetFullPathName_U( full_name, buf_sz, buffer, shortname );
|
Length = RtlGetFullPathName_U (full_name,
|
||||||
|
buf_sz,
|
||||||
|
buffer,
|
||||||
|
FilePart);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
RtlFreeHeap (RtlGetProcessHeap (), 0, full_name );
|
|
||||||
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
|
0,
|
||||||
|
full_name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return len;
|
else if (RtlDoesFileExists_U (name))
|
||||||
|
{
|
||||||
|
Length = RtlGetFullPathName_U (name,
|
||||||
|
buf_sz,
|
||||||
|
buffer,
|
||||||
|
FilePart);
|
||||||
|
}
|
||||||
|
|
||||||
|
return Length;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlIsNameLegalDOS8Dot3 (
|
RtlIsNameLegalDOS8Dot3 (
|
||||||
PUNICODE_STRING us,
|
PUNICODE_STRING UnicodeName,
|
||||||
PANSI_STRING as,
|
PANSI_STRING AnsiName,
|
||||||
PBOOLEAN pb
|
PBOOLEAN SpacesFound
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
ANSI_STRING *name = as,as1;
|
PANSI_STRING name = AnsiName;
|
||||||
char buf[12],*str;
|
ANSI_STRING DummyString;
|
||||||
|
CHAR Buffer[12];
|
||||||
|
char *str;
|
||||||
|
ULONG Length;
|
||||||
|
ULONG i;
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
BOOLEAN have_space = FALSE;
|
BOOLEAN HasSpace = FALSE;
|
||||||
BOOLEAN have_point = FALSE;
|
BOOLEAN HasDot = FALSE;
|
||||||
ULONG len,i;
|
|
||||||
|
|
||||||
if (us->Length > 24)
|
if (UnicodeName->Length > 24)
|
||||||
return FALSE; /* name too long */
|
return FALSE; /* name too long */
|
||||||
|
|
||||||
if (!name)
|
if (!name)
|
||||||
{
|
{
|
||||||
name = &as1;
|
name = &DummyString;
|
||||||
name->Length = 0;
|
name->Length = 0;
|
||||||
name->MaximumLength = 12;
|
name->MaximumLength = 12;
|
||||||
name->Buffer = buf;
|
name->Buffer = Buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
Status = RtlUpcaseUnicodeStringToCountedOemString (name,
|
Status = RtlUpcaseUnicodeStringToCountedOemString (name,
|
||||||
us,
|
UnicodeName,
|
||||||
FALSE);
|
FALSE);
|
||||||
if (!NT_SUCCESS(Status))
|
if (!NT_SUCCESS(Status))
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
len = name->Length;
|
Length = name->Length;
|
||||||
str = name->Buffer;
|
str = name->Buffer;
|
||||||
|
|
||||||
if (!(len == 1 && *str == '.') &&
|
if (!(Length == 1 && *str == '.') &&
|
||||||
!(len == 2 && *(short*)(str) == 0x2E2E))
|
!(Length == 2 && *str == '.' && *(str + 1) == '.'))
|
||||||
{
|
{
|
||||||
for (i = 0; i < len; i++, str++)
|
for (i = 0; i < Length; i++, str++)
|
||||||
{
|
{
|
||||||
switch (*str)
|
switch (*str)
|
||||||
{
|
{
|
||||||
case ' ':
|
case ' ':
|
||||||
have_space = TRUE;
|
HasSpace = TRUE;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case '.':
|
case '.':
|
||||||
if ((have_point) || /* two points */
|
if ((HasDot) || /* two points */
|
||||||
(!i) || /* point is first char */
|
(!i) || /* point is first char */
|
||||||
(i + 1 == len) || /* point is last char */
|
(i + 1 == Length) ||/* point is last char */
|
||||||
(len - i > 4)) /* more than 3 chars of extension */
|
(Length - i > 4)) /* more than 3 chars of extension */
|
||||||
return FALSE;
|
return FALSE;
|
||||||
have_point = TRUE;
|
HasDot = TRUE;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pb)
|
if (SpacesFound)
|
||||||
*pb = have_space;
|
*SpacesFound = HasSpace;
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
@ -686,11 +810,11 @@ RtlIsNameLegalDOS8Dot3 (
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlDoesFileExists_U (
|
RtlDoesFileExists_U (
|
||||||
PWSTR FileName
|
IN PWSTR FileName
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
UNICODE_STRING NtFileName;
|
UNICODE_STRING NtFileName;
|
||||||
OBJECT_ATTRIBUTES obj;
|
OBJECT_ATTRIBUTES Attr;
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
CURDIR CurDir;
|
CURDIR CurDir;
|
||||||
PWSTR Buffer;
|
PWSTR Buffer;
|
||||||
|
@ -709,16 +833,15 @@ RtlDoesFileExists_U (
|
||||||
else
|
else
|
||||||
CurDir.Handle = 0;
|
CurDir.Handle = 0;
|
||||||
|
|
||||||
obj.Length = sizeof(obj);
|
InitializeObjectAttributes (&Attr,
|
||||||
obj.RootDirectory = CurDir.Handle;
|
&NtFileName,
|
||||||
obj.ObjectName = &NtFileName;
|
OBJ_CASE_INSENSITIVE,
|
||||||
obj.Attributes = OBJ_CASE_INSENSITIVE;
|
CurDir.Handle,
|
||||||
obj.SecurityDescriptor = 0;
|
NULL);
|
||||||
obj.SecurityQualityOfService = 0;
|
|
||||||
|
|
||||||
Status = NtQueryAttributesFile (&obj, NULL);
|
Status = NtQueryAttributesFile (&Attr, NULL);
|
||||||
|
|
||||||
RtlFreeHeap (RtlGetProcessHeap(),
|
RtlFreeHeap (RtlGetProcessHeap (),
|
||||||
0,
|
0,
|
||||||
Buffer);
|
Buffer);
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
/* $Id: ppb.c,v 1.2 2000/02/14 14:13:33 dwelch Exp $
|
/* $Id: ppb.c,v 1.3 2000/02/18 00:49:11 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
* FILE: lib/ntdll/rtl/ppb.c
|
* FILE: lib/ntdll/rtl/ppb.c
|
||||||
* PURPOSE: Process functions
|
* PURPOSE: Process parameters functions
|
||||||
* PROGRAMMER: Ariadne ( ariadne@xs4all.nl)
|
* PROGRAMMER: Ariadne ( ariadne@xs4all.nl)
|
||||||
* UPDATE HISTORY:
|
* UPDATE HISTORY:
|
||||||
* Created 01/11/98
|
* Created 01/11/98
|
||||||
|
@ -25,6 +25,13 @@
|
||||||
#define NDEBUG
|
#define NDEBUG
|
||||||
#include <ntdll/ntdll.h>
|
#include <ntdll/ntdll.h>
|
||||||
|
|
||||||
|
/* MACROS ****************************************************************/
|
||||||
|
|
||||||
|
#define NORMALIZE(x,addr) {if(x) x=(VOID*)((ULONG)(x)+(ULONG)(addr));}
|
||||||
|
#define DENORMALIZE(x,addr) {if(x) x=(VOID*)((ULONG)(x)-(ULONG)(addr));}
|
||||||
|
#define ALIGN(x,align) (((ULONG)(x)+(align)-1UL)&(~((align)-1UL)))
|
||||||
|
|
||||||
|
|
||||||
/* FUNCTIONS ****************************************************************/
|
/* FUNCTIONS ****************************************************************/
|
||||||
|
|
||||||
VOID STDCALL RtlAcquirePebLock(VOID)
|
VOID STDCALL RtlAcquirePebLock(VOID)
|
||||||
|
@ -38,6 +45,26 @@ VOID STDCALL RtlReleasePebLock(VOID)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static
|
||||||
|
inline
|
||||||
|
VOID
|
||||||
|
RtlpCopyParameterString (
|
||||||
|
PWCHAR *Ptr,
|
||||||
|
PUNICODE_STRING Destination,
|
||||||
|
PUNICODE_STRING Source,
|
||||||
|
ULONG Size
|
||||||
|
)
|
||||||
|
{
|
||||||
|
Destination->Length = Source->Length;
|
||||||
|
Destination->MaximumLength = Size ? Size : Source->MaximumLength;
|
||||||
|
Destination->Buffer = (PWCHAR)(*Ptr);
|
||||||
|
if (Source->Length)
|
||||||
|
memmove (Destination->Buffer, Source->Buffer, Source->Length);
|
||||||
|
Destination->Buffer[Destination->Length / sizeof(WCHAR)] = 0;
|
||||||
|
*Ptr += Destination->MaximumLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlCreateProcessParameters (
|
RtlCreateProcessParameters (
|
||||||
|
@ -50,7 +77,7 @@ RtlCreateProcessParameters (
|
||||||
PUNICODE_STRING Title,
|
PUNICODE_STRING Title,
|
||||||
PUNICODE_STRING Desktop,
|
PUNICODE_STRING Desktop,
|
||||||
PUNICODE_STRING Reserved,
|
PUNICODE_STRING Reserved,
|
||||||
PVOID Reserved2
|
PUNICODE_STRING Reserved2
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
NTSTATUS Status = STATUS_SUCCESS;
|
NTSTATUS Status = STATUS_SUCCESS;
|
||||||
|
@ -58,38 +85,64 @@ RtlCreateProcessParameters (
|
||||||
ULONG RegionSize = 0;
|
ULONG RegionSize = 0;
|
||||||
ULONG DataSize = 0;
|
ULONG DataSize = 0;
|
||||||
PWCHAR Dest;
|
PWCHAR Dest;
|
||||||
|
UNICODE_STRING EmptyString;
|
||||||
|
HANDLE CurrentDirectoryHandle;
|
||||||
|
ULONG ConsoleFlags;
|
||||||
|
|
||||||
DPRINT ("RtlCreateProcessParameters\n");
|
DPRINT ("RtlCreateProcessParameters\n");
|
||||||
|
|
||||||
RtlAcquirePebLock ();
|
RtlAcquirePebLock ();
|
||||||
|
|
||||||
|
EmptyString.Length = 0;
|
||||||
|
EmptyString.MaximumLength = sizeof(WCHAR);
|
||||||
|
EmptyString.Buffer = L"";
|
||||||
|
|
||||||
|
if (NtCurrentPeb()->ProcessParameters)
|
||||||
|
{
|
||||||
|
if (LibraryPath == NULL)
|
||||||
|
LibraryPath = &NtCurrentPeb()->ProcessParameters->LibraryPath;
|
||||||
|
if (Environment == NULL)
|
||||||
|
Environment = NtCurrentPeb()->ProcessParameters->Environment;
|
||||||
|
if (CurrentDirectory == NULL)
|
||||||
|
CurrentDirectory = &NtCurrentPeb()->ProcessParameters->CurrentDirectory.DosPath;
|
||||||
|
CurrentDirectoryHandle = NtCurrentPeb()->ProcessParameters->CurrentDirectory.Handle;
|
||||||
|
ConsoleFlags = NtCurrentPeb()->ProcessParameters->ConsoleFlags;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (LibraryPath == NULL)
|
||||||
|
LibraryPath = &EmptyString;
|
||||||
|
if (CurrentDirectory == NULL)
|
||||||
|
CurrentDirectory = &EmptyString;
|
||||||
|
CurrentDirectoryHandle = NULL;
|
||||||
|
ConsoleFlags = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ImageName == NULL)
|
||||||
|
ImageName = CommandLine;
|
||||||
|
if (Title == NULL)
|
||||||
|
Title = &EmptyString;
|
||||||
|
if (Desktop == NULL)
|
||||||
|
Desktop = &EmptyString;
|
||||||
|
if (Reserved == NULL)
|
||||||
|
Reserved = &EmptyString;
|
||||||
|
if (Reserved2 == NULL)
|
||||||
|
Reserved2 = &EmptyString;
|
||||||
|
|
||||||
/* size of process parameter block */
|
/* size of process parameter block */
|
||||||
DataSize = sizeof (RTL_USER_PROCESS_PARAMETERS);
|
DataSize = sizeof (RTL_USER_PROCESS_PARAMETERS);
|
||||||
|
|
||||||
/* size of (reserved) buffer */
|
|
||||||
DataSize += (256 * sizeof(WCHAR));
|
|
||||||
|
|
||||||
/* size of current directory buffer */
|
/* size of current directory buffer */
|
||||||
DataSize += (MAX_PATH * sizeof(WCHAR));
|
DataSize += (MAX_PATH * sizeof(WCHAR));
|
||||||
|
|
||||||
/* add string lengths */
|
/* add string lengths */
|
||||||
if (LibraryPath != NULL)
|
DataSize += ALIGN(LibraryPath->MaximumLength, sizeof(ULONG));
|
||||||
DataSize += (LibraryPath->Length + sizeof(WCHAR));
|
DataSize += ALIGN(CommandLine->Length, sizeof(ULONG));
|
||||||
|
DataSize += ALIGN(ImageName->Length, sizeof(ULONG));
|
||||||
if (CommandLine != NULL)
|
DataSize += ALIGN(Title->MaximumLength, sizeof(ULONG));
|
||||||
DataSize += (CommandLine->Length + sizeof(WCHAR));
|
DataSize += ALIGN(Desktop->MaximumLength, sizeof(ULONG));
|
||||||
|
DataSize += ALIGN(Reserved->MaximumLength, sizeof(ULONG));
|
||||||
if (ImageName != NULL)
|
DataSize += ALIGN(Reserved2->MaximumLength, sizeof(ULONG));
|
||||||
DataSize += (ImageName->Length + sizeof(WCHAR));
|
|
||||||
|
|
||||||
if (Title != NULL)
|
|
||||||
DataSize += (Title->Length + sizeof(WCHAR));
|
|
||||||
|
|
||||||
if (Desktop != NULL)
|
|
||||||
DataSize += (Desktop->Length + sizeof(WCHAR));
|
|
||||||
|
|
||||||
if (Reserved != NULL)
|
|
||||||
DataSize += (Reserved->Length + sizeof(WCHAR));
|
|
||||||
|
|
||||||
/* Calculate the required block size */
|
/* Calculate the required block size */
|
||||||
RegionSize = ROUNDUP(DataSize, PAGESIZE);
|
RegionSize = ROUNDUP(DataSize, PAGESIZE);
|
||||||
|
@ -111,109 +164,85 @@ RtlCreateProcessParameters (
|
||||||
|
|
||||||
Param->TotalSize = RegionSize;
|
Param->TotalSize = RegionSize;
|
||||||
Param->DataSize = DataSize;
|
Param->DataSize = DataSize;
|
||||||
Param->Flags = TRUE;
|
Param->Flags = PPF_NORMALIZED;
|
||||||
Param->Environment = Environment;
|
Param->Environment = Environment;
|
||||||
// Param->Unknown1 =
|
Param->CurrentDirectory.Handle = CurrentDirectoryHandle;
|
||||||
// Param->Unknown2 =
|
Param->ConsoleFlags = ConsoleFlags;
|
||||||
// Param->Unknown3 =
|
|
||||||
// Param->Unknown4 =
|
Dest = (PWCHAR)(((PBYTE)Param) + sizeof(RTL_USER_PROCESS_PARAMETERS));
|
||||||
|
|
||||||
/* copy current directory */
|
/* copy current directory */
|
||||||
Dest = (PWCHAR)(((PBYTE)Param) +
|
RtlpCopyParameterString (&Dest,
|
||||||
sizeof(RTL_USER_PROCESS_PARAMETERS));
|
&Param->CurrentDirectory.DosPath,
|
||||||
|
CurrentDirectory,
|
||||||
|
MAX_PATH * sizeof(WCHAR));
|
||||||
|
|
||||||
Param->CurrentDirectory.DosPath.Buffer = Dest;
|
/* make sure the current directory has a trailing backslash */
|
||||||
Param->CurrentDirectory.DosPath.MaximumLength = MAX_PATH * sizeof(WCHAR);
|
if (Param->CurrentDirectory.DosPath.Length > 0)
|
||||||
if (CurrentDirectory != NULL)
|
|
||||||
{
|
{
|
||||||
Param->CurrentDirectory.DosPath.Length = CurrentDirectory->Length;
|
ULONG Length;
|
||||||
memcpy(Dest,
|
|
||||||
CurrentDirectory->Buffer,
|
|
||||||
CurrentDirectory->Length);
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + CurrentDirectory->Length);
|
|
||||||
}
|
|
||||||
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Param) + sizeof(RTL_USER_PROCESS_PARAMETERS) +
|
Length = Param->CurrentDirectory.DosPath.Length / sizeof(WCHAR);
|
||||||
/* (256 * sizeof(WCHAR)) + */ (MAX_PATH * sizeof(WCHAR)));
|
if (Param->CurrentDirectory.DosPath.Buffer[Length-1] != L'\\')
|
||||||
|
{
|
||||||
|
Param->CurrentDirectory.DosPath.Buffer[Length] = L'\\';
|
||||||
|
Param->CurrentDirectory.DosPath.Buffer[Length + 1] = 0;
|
||||||
|
Param->CurrentDirectory.DosPath.Length += sizeof(WCHAR);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* copy library path */
|
/* copy library path */
|
||||||
Param->LibraryPath.Buffer = Dest;
|
RtlpCopyParameterString (&Dest,
|
||||||
if (LibraryPath != NULL)
|
&Param->LibraryPath,
|
||||||
{
|
LibraryPath,
|
||||||
Param->LibraryPath.Length = LibraryPath->Length;
|
0);
|
||||||
memcpy (Dest,
|
|
||||||
LibraryPath->Buffer,
|
|
||||||
LibraryPath->Length);
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + LibraryPath->Length);
|
|
||||||
}
|
|
||||||
Param->LibraryPath.MaximumLength = Param->LibraryPath.Length +
|
|
||||||
sizeof(WCHAR);
|
|
||||||
*Dest = 0;
|
|
||||||
Dest++;
|
|
||||||
|
|
||||||
/* copy command line */
|
/* copy command line */
|
||||||
Param->CommandLine.Buffer = Dest;
|
RtlpCopyParameterString (&Dest,
|
||||||
if (CommandLine != NULL)
|
&Param->CommandLine,
|
||||||
{
|
CommandLine,
|
||||||
Param->CommandLine.Length = CommandLine->Length;
|
CommandLine->Length + sizeof(WCHAR));
|
||||||
memcpy (Dest,
|
|
||||||
CommandLine->Buffer,
|
|
||||||
CommandLine->Length);
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + CommandLine->Length);
|
|
||||||
}
|
|
||||||
Param->CommandLine.MaximumLength = Param->CommandLine.Length + sizeof(WCHAR);
|
|
||||||
*Dest = 0;
|
|
||||||
Dest++;
|
|
||||||
|
|
||||||
/* copy image name */
|
/* copy image name */
|
||||||
Param->ImageName.Buffer = Dest;
|
RtlpCopyParameterString (&Dest,
|
||||||
if (ImageName != NULL)
|
&Param->ImageName,
|
||||||
{
|
ImageName,
|
||||||
Param->ImageName.Length = ImageName->Length;
|
ImageName->Length + sizeof(WCHAR));
|
||||||
memcpy (Dest,
|
|
||||||
ImageName->Buffer,
|
|
||||||
ImageName->Length);
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + ImageName->Length);
|
|
||||||
}
|
|
||||||
Param->ImageName.MaximumLength = Param->ImageName.Length + sizeof(WCHAR);
|
|
||||||
*Dest = 0;
|
|
||||||
Dest++;
|
|
||||||
|
|
||||||
/* copy title */
|
/* copy title */
|
||||||
Param->Title.Buffer = Dest;
|
RtlpCopyParameterString (&Dest,
|
||||||
if (Title != NULL)
|
&Param->Title,
|
||||||
{
|
Title,
|
||||||
Param->Title.Length = Title->Length;
|
0);
|
||||||
memcpy (Dest,
|
|
||||||
Title->Buffer,
|
|
||||||
Title->Length);
|
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + Title->Length);
|
|
||||||
}
|
|
||||||
Param->Title.MaximumLength = Param->Title.Length + sizeof(WCHAR);
|
|
||||||
*Dest = 0;
|
|
||||||
Dest++;
|
|
||||||
|
|
||||||
/* copy desktop */
|
/* copy desktop */
|
||||||
Param->Desktop.Buffer = Dest;
|
RtlpCopyParameterString (&Dest,
|
||||||
if (Desktop != NULL)
|
&Param->Desktop,
|
||||||
{
|
Desktop,
|
||||||
Param->Desktop.Length = Desktop->Length;
|
0);
|
||||||
memcpy (Dest,
|
|
||||||
Desktop->Buffer,
|
RtlpCopyParameterString (&Dest,
|
||||||
Desktop->Length);
|
&Param->ShellInfo,
|
||||||
Dest = (PWCHAR)(((PBYTE)Dest) + Desktop->Length);
|
Reserved,
|
||||||
}
|
0);
|
||||||
Param->Desktop.MaximumLength = Param->Desktop.Length + sizeof(WCHAR);
|
|
||||||
*Dest = 0;
|
RtlpCopyParameterString (&Dest,
|
||||||
Dest++;
|
&Param->RuntimeData,
|
||||||
|
Reserved2,
|
||||||
|
0);
|
||||||
|
|
||||||
RtlDeNormalizeProcessParams (Param);
|
RtlDeNormalizeProcessParams (Param);
|
||||||
*Ppb = Param;
|
*Ppb = Param;
|
||||||
RtlReleasePebLock ();
|
RtlReleasePebLock ();
|
||||||
|
|
||||||
|
return STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID STDCALL RtlDestroyProcessParameters (PRTL_USER_PROCESS_PARAMETERS Ppb)
|
VOID
|
||||||
|
STDCALL
|
||||||
|
RtlDestroyProcessParameters (
|
||||||
|
PRTL_USER_PROCESS_PARAMETERS Ppb
|
||||||
|
)
|
||||||
{
|
{
|
||||||
ULONG RegionSize = 0;
|
ULONG RegionSize = 0;
|
||||||
|
|
||||||
|
@ -226,115 +255,52 @@ VOID STDCALL RtlDestroyProcessParameters (PRTL_USER_PROCESS_PARAMETERS Ppb)
|
||||||
/*
|
/*
|
||||||
* denormalize process parameters (Pointer-->Offset)
|
* denormalize process parameters (Pointer-->Offset)
|
||||||
*/
|
*/
|
||||||
VOID
|
PRTL_USER_PROCESS_PARAMETERS
|
||||||
STDCALL
|
STDCALL
|
||||||
RtlDeNormalizeProcessParams (
|
RtlDeNormalizeProcessParams (
|
||||||
PRTL_USER_PROCESS_PARAMETERS Ppb
|
PRTL_USER_PROCESS_PARAMETERS Params
|
||||||
)
|
)
|
||||||
{
|
{
|
||||||
if (Ppb == NULL)
|
if (Params && (Params->Flags & PPF_NORMALIZED))
|
||||||
return;
|
|
||||||
|
|
||||||
if (Ppb->Flags == FALSE)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (Ppb->CurrentDirectory.DosPath.Buffer != NULL)
|
|
||||||
{
|
{
|
||||||
Ppb->CurrentDirectory.DosPath.Buffer =
|
DENORMALIZE (Params->CurrentDirectory.DosPath.Buffer, Params);
|
||||||
(PWSTR)((ULONG)Ppb->CurrentDirectory.DosPath.Buffer -
|
DENORMALIZE (Params->LibraryPath.Buffer, Params);
|
||||||
(ULONG)Ppb);
|
DENORMALIZE (Params->CommandLine.Buffer, Params);
|
||||||
|
DENORMALIZE (Params->ImageName.Buffer, Params);
|
||||||
|
DENORMALIZE (Params->Title.Buffer, Params);
|
||||||
|
DENORMALIZE (Params->Desktop.Buffer, Params);
|
||||||
|
DENORMALIZE (Params->ShellInfo.Buffer, Params);
|
||||||
|
DENORMALIZE (Params->RuntimeData.Buffer, Params);
|
||||||
|
|
||||||
|
Params->Flags &= ~PPF_NORMALIZED;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Ppb->LibraryPath.Buffer != NULL)
|
return Params;
|
||||||
{
|
|
||||||
Ppb->LibraryPath.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->LibraryPath.Buffer -
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->CommandLine.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->CommandLine.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->CommandLine.Buffer -
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->ImageName.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->ImageName.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->ImageName.Buffer -
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->Title.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->Title.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->Title.Buffer -
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->Desktop.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->Desktop.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->Desktop.Buffer -
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
Ppb->Flags = FALSE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* normalize process parameters (Offset-->Pointer)
|
* normalize process parameters (Offset-->Pointer)
|
||||||
*/
|
*/
|
||||||
VOID STDCALL RtlNormalizeProcessParams (PRTL_USER_PROCESS_PARAMETERS Ppb)
|
PRTL_USER_PROCESS_PARAMETERS
|
||||||
|
STDCALL
|
||||||
|
RtlNormalizeProcessParams (
|
||||||
|
PRTL_USER_PROCESS_PARAMETERS Params)
|
||||||
{
|
{
|
||||||
if (Ppb == NULL)
|
if (Params && !(Params->Flags & PPF_NORMALIZED))
|
||||||
return;
|
|
||||||
|
|
||||||
if (Ppb->Flags == TRUE)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (Ppb->CurrentDirectory.DosPath.Buffer != NULL)
|
|
||||||
{
|
{
|
||||||
Ppb->CurrentDirectory.DosPath.Buffer =
|
NORMALIZE (Params->CurrentDirectory.DosPath.Buffer, Params);
|
||||||
(PWSTR)((ULONG)Ppb->CurrentDirectory.DosPath.Buffer +
|
NORMALIZE (Params->LibraryPath.Buffer, Params);
|
||||||
(ULONG)Ppb);
|
NORMALIZE (Params->CommandLine.Buffer, Params);
|
||||||
|
NORMALIZE (Params->ImageName.Buffer, Params);
|
||||||
|
NORMALIZE (Params->Title.Buffer, Params);
|
||||||
|
NORMALIZE (Params->Desktop.Buffer, Params);
|
||||||
|
NORMALIZE (Params->ShellInfo.Buffer, Params);
|
||||||
|
NORMALIZE (Params->RuntimeData.Buffer, Params);
|
||||||
|
|
||||||
|
Params->Flags |= PPF_NORMALIZED;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Ppb->LibraryPath.Buffer != NULL)
|
return Params;
|
||||||
{
|
|
||||||
Ppb->LibraryPath.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->LibraryPath.Buffer +
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->CommandLine.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->CommandLine.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->CommandLine.Buffer +
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->ImageName.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->ImageName.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->ImageName.Buffer +
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->Title.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->Title.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->Title.Buffer +
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (Ppb->Desktop.Buffer != NULL)
|
|
||||||
{
|
|
||||||
Ppb->Desktop.Buffer =
|
|
||||||
(PWSTR)((ULONG)Ppb->Desktop.Buffer +
|
|
||||||
(ULONG)Ppb);
|
|
||||||
}
|
|
||||||
|
|
||||||
Ppb->Flags = TRUE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* EOF */
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: process.c,v 1.13 2000/02/14 14:13:33 dwelch Exp $
|
/* $Id: process.c,v 1.14 2000/02/18 00:49:11 ekohl Exp $
|
||||||
*
|
*
|
||||||
* COPYRIGHT: See COPYING in the top level directory
|
* COPYRIGHT: See COPYING in the top level directory
|
||||||
* PROJECT: ReactOS system libraries
|
* PROJECT: ReactOS system libraries
|
||||||
|
@ -156,6 +156,54 @@ static NTSTATUS KlInitPeb (HANDLE ProcessHandle,
|
||||||
ULONG PpbSize;
|
ULONG PpbSize;
|
||||||
ULONG BytesWritten;
|
ULONG BytesWritten;
|
||||||
ULONG Offset;
|
ULONG Offset;
|
||||||
|
PVOID ParentEnv = NULL;
|
||||||
|
PVOID EnvPtr = NULL;
|
||||||
|
ULONG EnvSize = 0;
|
||||||
|
|
||||||
|
/* create the Environment */
|
||||||
|
if (Ppb->Environment != NULL)
|
||||||
|
ParentEnv = Ppb->Environment;
|
||||||
|
else if (NtCurrentPeb()->ProcessParameters->Environment != NULL)
|
||||||
|
ParentEnv = NtCurrentPeb()->ProcessParameters->Environment;
|
||||||
|
|
||||||
|
if (ParentEnv != NULL)
|
||||||
|
{
|
||||||
|
MEMORY_BASIC_INFORMATION MemInfo;
|
||||||
|
|
||||||
|
Status = NtQueryVirtualMemory (NtCurrentProcess (),
|
||||||
|
ParentEnv,
|
||||||
|
MemoryBasicInformation,
|
||||||
|
&MemInfo,
|
||||||
|
sizeof(MEMORY_BASIC_INFORMATION),
|
||||||
|
NULL);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
return Status;
|
||||||
|
}
|
||||||
|
EnvSize = MemInfo.RegionSize;
|
||||||
|
}
|
||||||
|
DPRINT("EnvironmentSize %ld\n", EnvSize);
|
||||||
|
|
||||||
|
/* allocate and initialize new environment block */
|
||||||
|
if (EnvSize != 0)
|
||||||
|
{
|
||||||
|
Status = NtAllocateVirtualMemory(ProcessHandle,
|
||||||
|
&EnvPtr,
|
||||||
|
0,
|
||||||
|
&EnvSize,
|
||||||
|
MEM_COMMIT,
|
||||||
|
PAGE_READWRITE);
|
||||||
|
if (!NT_SUCCESS(Status))
|
||||||
|
{
|
||||||
|
return(Status);
|
||||||
|
}
|
||||||
|
|
||||||
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
|
EnvPtr,
|
||||||
|
ParentEnv,
|
||||||
|
EnvSize,
|
||||||
|
&BytesWritten);
|
||||||
|
}
|
||||||
|
|
||||||
/* create the PPB */
|
/* create the PPB */
|
||||||
PpbBase = (PVOID)PEB_STARTUPINFO;
|
PpbBase = (PVOID)PEB_STARTUPINFO;
|
||||||
|
@ -172,14 +220,24 @@ static NTSTATUS KlInitPeb (HANDLE ProcessHandle,
|
||||||
}
|
}
|
||||||
|
|
||||||
DPRINT("Ppb->TotalSize %x\n", Ppb->TotalSize);
|
DPRINT("Ppb->TotalSize %x\n", Ppb->TotalSize);
|
||||||
|
|
||||||
|
/* write process parameters block*/
|
||||||
NtWriteVirtualMemory(ProcessHandle,
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
PpbBase,
|
PpbBase,
|
||||||
Ppb,
|
Ppb,
|
||||||
Ppb->TotalSize,
|
Ppb->TotalSize,
|
||||||
&BytesWritten);
|
&BytesWritten);
|
||||||
|
|
||||||
Offset = FIELD_OFFSET(PEB, ProcessParameters);
|
/* write pointer to environment */
|
||||||
|
Offset = FIELD_OFFSET(RTL_USER_PROCESS_PARAMETERS, Environment);
|
||||||
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
|
(PVOID)(PpbBase + Offset),
|
||||||
|
&EnvPtr,
|
||||||
|
sizeof(EnvPtr),
|
||||||
|
&BytesWritten);
|
||||||
|
|
||||||
|
/* write pointer to process parameter block */
|
||||||
|
Offset = FIELD_OFFSET(PEB, ProcessParameters);
|
||||||
NtWriteVirtualMemory(ProcessHandle,
|
NtWriteVirtualMemory(ProcessHandle,
|
||||||
(PVOID)(PEB_BASE + Offset),
|
(PVOID)(PEB_BASE + Offset),
|
||||||
&PpbBase,
|
&PpbBase,
|
||||||
|
@ -204,13 +262,13 @@ NTSTATUS STDCALL RtlCreateUserProcess(PUNICODE_STRING CommandLine,
|
||||||
HANDLE hThread;
|
HANDLE hThread;
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
LPTHREAD_START_ROUTINE lpStartAddress = NULL;
|
LPTHREAD_START_ROUTINE lpStartAddress = NULL;
|
||||||
WCHAR TempCommandLine[256];
|
// WCHAR TempCommandLine[256];
|
||||||
PVOID BaseAddress;
|
// PVOID BaseAddress;
|
||||||
LARGE_INTEGER SectionOffset;
|
// LARGE_INTEGER SectionOffset;
|
||||||
ULONG InitialViewSize;
|
// ULONG InitialViewSize;
|
||||||
PROCESS_BASIC_INFORMATION ProcessBasicInfo;
|
PROCESS_BASIC_INFORMATION ProcessBasicInfo;
|
||||||
ULONG retlen;
|
ULONG retlen;
|
||||||
DWORD len = 0;
|
// DWORD len = 0;
|
||||||
|
|
||||||
DPRINT("CreateProcessW(CommandLine '%w')\n", CommandLine->Buffer);
|
DPRINT("CreateProcessW(CommandLine '%w')\n", CommandLine->Buffer);
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
/* $Id: init.c,v 1.10 2000/02/13 16:05:19 dwelch Exp $
|
/* $Id: init.c,v 1.11 2000/02/18 00:51:03 ekohl Exp $
|
||||||
*
|
*
|
||||||
* init.c - Session Manager initialization
|
* init.c - Session Manager initialization
|
||||||
*
|
*
|
||||||
|
@ -74,8 +74,11 @@ InitSessionManager (
|
||||||
UNICODE_STRING UnicodeString;
|
UNICODE_STRING UnicodeString;
|
||||||
OBJECT_ATTRIBUTES ObjectAttributes;
|
OBJECT_ATTRIBUTES ObjectAttributes;
|
||||||
UNICODE_STRING CmdLineW;
|
UNICODE_STRING CmdLineW;
|
||||||
|
UNICODE_STRING CurrentDirectoryW;
|
||||||
PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
|
PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
|
||||||
|
|
||||||
|
UNICODE_STRING EnvVariable;
|
||||||
|
UNICODE_STRING EnvValue;
|
||||||
|
|
||||||
/* Create the "\SmApiPort" object (LPC) */
|
/* Create the "\SmApiPort" object (LPC) */
|
||||||
RtlInitUnicodeString (&UnicodeString,
|
RtlInitUnicodeString (&UnicodeString,
|
||||||
|
@ -133,6 +136,15 @@ InitSessionManager (
|
||||||
DisplayString (L"SM: System Environment created\n");
|
DisplayString (L"SM: System Environment created\n");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
RtlInitUnicodeString (&EnvVariable,
|
||||||
|
L"OS");
|
||||||
|
RtlInitUnicodeString (&EnvValue,
|
||||||
|
L"Reactos 0.0.15");
|
||||||
|
|
||||||
|
RtlSetEnvironmentVariable (SmSystemEnvironment,
|
||||||
|
&EnvVariable,
|
||||||
|
&EnvValue);
|
||||||
|
|
||||||
// RtlSetCurrentEnvironment (SmSystemEnvironment,
|
// RtlSetCurrentEnvironment (SmSystemEnvironment,
|
||||||
// NULL);
|
// NULL);
|
||||||
|
|
||||||
|
@ -217,12 +229,16 @@ InitSessionManager (
|
||||||
L"\\??\\C:\\reactos\\system32\\winlogon.exe");
|
L"\\??\\C:\\reactos\\system32\\winlogon.exe");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* initialize current directory (trailing backslash!!)*/
|
||||||
|
RtlInitUnicodeString (&CurrentDirectoryW,
|
||||||
|
L"C:\\reactos\\");
|
||||||
|
|
||||||
RtlCreateProcessParameters (&ProcessParameters,
|
RtlCreateProcessParameters (&ProcessParameters,
|
||||||
&UnicodeString,
|
&UnicodeString,
|
||||||
NULL,
|
NULL,
|
||||||
|
&CurrentDirectoryW,
|
||||||
NULL,
|
NULL,
|
||||||
NULL,
|
SmSystemEnvironment,
|
||||||
NULL,
|
|
||||||
NULL,
|
NULL,
|
||||||
NULL,
|
NULL,
|
||||||
NULL,
|
NULL,
|
||||||
|
|
Loading…
Reference in a new issue