Modified: trunk/reactos/lib/kernel32/file/file.c
Modified: trunk/reactos/lib/kernel32/include/kernel32.h
Modified: trunk/reactos/lib/kernel32/kernel32.xml
Added: trunk/reactos/lib/kernel32/misc/utils.c
Added: trunk/reactos/lib/kernel32/thread/i386/thread.S
--- trunk/reactos/lib/kernel32/file/file.c 2005-07-12 04:41:41 UTC (rev 16542)
+++ trunk/reactos/lib/kernel32/file/file.c 2005-07-12 05:00:33 UTC (rev 16543)
@@ -22,7 +22,6 @@
BOOL bIsFileApiAnsi = TRUE; // set the file api to ansi or oem
-
/* FUNCTIONS ****************************************************************/
@@ -178,20 +177,30 @@
/*
* @implemented
*/
-VOID STDCALL
+VOID
+STDCALL
SetFileApisToOEM(VOID)
{
- bIsFileApiAnsi = FALSE;
+ /* Set the correct Base Api */
+ Basep8BitStringToUnicodeString = RtlOemStringToUnicodeString;
+
+ /* FIXME: Old, deprecated way */
+ bIsFileApiAnsi = FALSE;
}
/*
* @implemented
*/
-VOID STDCALL
+VOID
+STDCALL
SetFileApisToANSI(VOID)
{
- bIsFileApiAnsi = TRUE;
+ /* Set the correct Base Api */
+ Basep8BitStringToUnicodeString = RtlAnsiStringToUnicodeString;
+
+ /* FIXME: Old, deprecated way */
+ bIsFileApiAnsi = TRUE;
}
--- trunk/reactos/lib/kernel32/include/kernel32.h 2005-07-12 04:41:41 UTC (rev 16542)
+++ trunk/reactos/lib/kernel32/include/kernel32.h 2005-07-12 05:00:33 UTC (rev 16543)
@@ -26,6 +26,13 @@
#define IsConsoleHandle(h) \
((((ULONG)h) & 0x10000003) == 0x3) ? TRUE : FALSE
+#define HANDLE_DETACHED_PROCESS (HANDLE)-1
+#define HANDLE_CREATE_NEW_CONSOLE (HANDLE)-2
+#define HANDLE_CREATE_NO_WINDOW (HANDLE)-3
+
+/* Undocumented CreateProcess flag */
+#define STARTF_SHELLPRIVATE 0x400
+
#define SetLastErrorByStatus(__S__) \
((void)SetLastError(RtlNtStatusToDosError(__S__)))
@@ -69,5 +76,86 @@
#define HeapAlloc RtlAllocateHeap
#define HeapFree RtlFreeHeap
+POBJECT_ATTRIBUTES
+STDCALL
+BasepConvertObjectAttributes(OUT POBJECT_ATTRIBUTES ObjectAttributes,
+ IN PSECURITY_ATTRIBUTES SecurityAttributes OPTIONAL,
+ IN PUNICODE_STRING ObjectName);
+
+NTSTATUS
+STDCALL
+BasepCreateStack(HANDLE hProcess,
+ ULONG StackReserve,
+ ULONG StackCommit,
+ PINITIAL_TEB InitialTeb);
+
+VOID
+STDCALL
+BasepInitializeContext(IN PCONTEXT Context,
+ IN PVOID Parameter,
+ IN PVOID StartAddress,
+ IN PVOID StackAddress,
+ IN ULONG ContextType);
+
+VOID
+STDCALL
+BaseThreadStartupThunk();
+
+VOID
+STDCALL
+BaseProcessStartThunk();
+
+__declspec(noreturn)
+VOID
+STDCALL
+BaseThreadStartup(LPTHREAD_START_ROUTINE lpStartAddress,
+ LPVOID lpParameter);
+
+VOID
+STDCALL
+BasepFreeStack(HANDLE hProcess,
+ PINITIAL_TEB InitialTeb);
+
+__declspec(noreturn)
+VOID
+WINAPI
+BaseFiberStartup(VOID);
+
+typedef UINT (STDCALL *PPROCESS_START_ROUTINE)(VOID);
+
+VOID
+STDCALL
+BaseProcessStartup(PPROCESS_START_ROUTINE lpStartAddress);
+
+BOOLEAN
+STDCALL
+BasepCheckRealTimePrivilege(VOID);
+
+VOID
+STDCALL
+BasepAnsiStringToHeapUnicodeString(IN LPCSTR AnsiString,
+ IN PVOID UnicodeString);
+
+PUNICODE_STRING
+STDCALL
+Basep8BitStringToCachedUnicodeString(IN LPCSTR String);
+
+NTSTATUS
+STDCALL
+Basep8BitStringToLiveUnicodeString(OUT PUNICODE_STRING UnicodeString,
+ IN LPCSTR String);
+
+typedef NTSTATUS (STDCALL *PRTL_CONVERT_STRING)(IN PUNICODE_STRING UnicodeString,
+ IN PANSI_STRING AnsiString,
+ IN BOOLEAN AllocateMemory);
+
+PRTL_CONVERT_STRING Basep8BitStringToUnicodeString;
+
+NTSTATUS
+STDCALL
+BasepMapFile(IN LPCWSTR lpApplicationName,
+ OUT PHANDLE hSection,
+ IN PUNICODE_STRING ApplicationName);
+
#endif /* ndef _KERNEL32_INCLUDE_KERNEL32_H */
--- trunk/reactos/lib/kernel32/kernel32.xml 2005-07-12 04:41:41 UTC (rev 16542)
+++ trunk/reactos/lib/kernel32/kernel32.xml 2005-07-12 05:00:33 UTC (rev 16543)
@@ -76,6 +76,7 @@
<file>time.c</file>
<file>timerqueue.c</file>
<file>toolhelp.c</file>
+ <file>utils.c</file>
<file>version.c</file>
</directory>
<directory name="process">
@@ -99,6 +100,7 @@
<directory name="thread">
<directory name="i386">
<file>fiber.S</file>
+ <file>thread.S</file>
</directory>
<file>fiber.c</file>
<file>fls.c</file>
--- trunk/reactos/lib/kernel32/misc/utils.c 2005-07-12 04:41:41 UTC (rev 16542)
+++ trunk/reactos/lib/kernel32/misc/utils.c 2005-07-12 05:00:33 UTC (rev 16543)
@@ -0,0 +1,425 @@
+/*
+ * COPYRIGHT: See COPYING in the top level directory
+ * PROJECT: ReactOS system libraries
+ * FILE: lib/kernel32/misc/utils.c
+ * PURPOSE: Utility and Support Functions
+ * PROGRAMMER: Alex Ionescu (alex@relsoft.net)
+ */
+
+/* INCLUDES ****************************************************************/
+
+#include <k32.h>
+
+#define NDEBUG
+#include <debug.h>
+
+/* FUNCTIONS ****************************************************************/
+
+/*
+ * Converts an ANSI or OEM String to the specified Unicode String
+ */
+NTSTATUS
+STDCALL
+Basep8BitStringToLiveUnicodeString(OUT PUNICODE_STRING UnicodeString,
+ IN LPCSTR String)
+{
+ ANSI_STRING AnsiString;
+ NTSTATUS Status;
+
+ DPRINT("Basep8BitStringToLiveUnicodeString\n");
+
+ /* Create the ANSI String */
+ RtlInitAnsiString(&AnsiString, String);
+
+ /* Convert from OEM or ANSI */
+ Status = Basep8BitStringToUnicodeString(UnicodeString, &AnsiString, FALSE);
+
+ /* Return Status */
+ if (!NT_SUCCESS(Status))
+ {
+ SetLastErrorByStatus(Status);
+ }
+ return Status;
+}
+
+
+/*
+ * Converts an ANSI or OEM String to the TEB StaticUnicodeString
+ */
+PUNICODE_STRING
+STDCALL
+Basep8BitStringToCachedUnicodeString(IN LPCSTR String)
+{
+ PUNICODE_STRING StaticString = &NtCurrentTeb()->StaticUnicodeString;
+ ANSI_STRING AnsiString;
+ NTSTATUS Status;
+
+ DPRINT("Basep8BitStringToCachedUnicodeString\n");
+
+ /* Initialize an ANSI String */
+ RtlInitAnsiString(&AnsiString, String);
+
+ /* Convert it */
+ Status = Basep8BitStringToUnicodeString(StaticString, &AnsiString, FALSE);
+
+ /* Handle failure */
+ if (!NT_SUCCESS(Status))
+ {
+ SetLastErrorByStatus(Status);
+ return NULL;
+ }
+
+ /* Return pointer to the string */
+ return StaticString;
+}
+
+/*
+ * Allocates space from the Heap and converts an Ansi String into it
+ */
+VOID
+STDCALL
+BasepAnsiStringToHeapUnicodeString(IN LPCSTR AnsiString,
+ IN PVOID UnicodeString)
+{
+ ANSI_STRING AnsiTemp;
+ UNICODE_STRING UnicodeTemp;
+
+ DPRINT("BasepAnsiStringToHeapUnicodeString\n");
+
+ /* First create the ANSI_STRING */
+ RtlInitAnsiString(&AnsiTemp, AnsiString);
+
+ /* Now get the size needed */
+ UnicodeTemp.MaximumLength = RtlAnsiStringToUnicodeSize(&AnsiTemp);
+
+ /* Allocate space from the Heap for the string */
+ UnicodeString = RtlAllocateHeap(GetProcessHeap(),
+ 0,
+ UnicodeTemp.MaximumLength);
+
+ /* Save the buffer and convert */
+ UnicodeTemp.Buffer = UnicodeString;
+ RtlAnsiStringToUnicodeString(&UnicodeTemp, &AnsiTemp, FALSE);
+}
+
+/*
+ * Converts lpSecurityAttributes + Object Name into ObjectAttributes.
+ */
+POBJECT_ATTRIBUTES
+STDCALL
+BasepConvertObjectAttributes(OUT POBJECT_ATTRIBUTES ObjectAttributes,
+ IN PSECURITY_ATTRIBUTES SecurityAttributes OPTIONAL,
+ IN PUNICODE_STRING ObjectName)
+{
+ ULONG Attributes = 0;
+ HANDLE RootDirectory = 0;
+ PVOID SecurityDescriptor = NULL;
+ BOOLEAN NeedOba = FALSE;
+
+ DPRINT("BasepConvertObjectAttributes. Security: %p, Name: %p\n",
+ SecurityAttributes, ObjectName);
+
+ /* Get the attributes if present */
+ if (SecurityAttributes)
+ {
+ Attributes = SecurityAttributes->bInheritHandle ? OBJ_INHERIT : 0;
+ SecurityDescriptor = SecurityAttributes->lpSecurityDescriptor;
+ NeedOba = TRUE;
+ }
+
+ if (ObjectName)
+ {
+ Attributes |= OBJ_OPENIF;
+ RootDirectory = hBaseDir;
+ NeedOba = TRUE;
+ }
+
+ DPRINT("Attributes: %lx, RootDirectory: %lx, SecurityDescriptor: %p\n",
+ Attributes, RootDirectory, SecurityDescriptor);
+
+ /* Create the Object Attributes */
+ if (NeedOba)
+ {
+ InitializeObjectAttributes(ObjectAttributes,
+ ObjectName,
+ Attributes,
+ RootDirectory,
+ SecurityDescriptor);
+ return ObjectAttributes;
+ }
+
+ /* Nothing to return */
+ return NULL;
+}
+
+/*
+ * Creates a stack for a thread or fiber
+ */
+NTSTATUS
+STDCALL
+BasepCreateStack(HANDLE hProcess,
+ ULONG StackReserve,
+ ULONG StackCommit,
+ PINITIAL_TEB InitialTeb)
+{
+ NTSTATUS Status;
+ SYSTEM_BASIC_INFORMATION SystemBasicInfo;
+ PIMAGE_NT_HEADERS Headers;
+ ULONG_PTR Stack = 0;
+ BOOLEAN UseGuard = FALSE;
+
+ DPRINT("BasepCreateStack (hProcess: %lx, Max: %lx, Current: %lx)\n",
+ hProcess, StackReserve, StackCommit);
+
+ /* Get some memory information */
+ Status = NtQuerySystemInformation(SystemBasicInformation,
+ &SystemBasicInfo,
+ sizeof(SYSTEM_BASIC_INFORMATION),
+ NULL);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failure to query system info\n");
+ return Status;
+ }
+
+ /* Use the Image Settings if we are dealing with the current Process */
+ if (hProcess == NtCurrentProcess())
+ {
+ /* Get the Image Headers */
+ Headers = RtlImageNtHeader(NtCurrentPeb()->ImageBaseAddress);
+
+ /* If we didn't get the parameters, find them ourselves */
+ StackReserve = (StackReserve) ?
+ StackReserve : Headers->OptionalHeader.SizeOfStackReserve;
+ StackCommit = (StackCommit) ?
+ StackCommit : Headers->OptionalHeader.SizeOfStackCommit;
+ }
+ else
+ {
+ /* Use the System Settings if needed */
+ StackReserve = (StackReserve) ? StackReserve :
+ SystemBasicInfo.AllocationGranularity;
+ StackCommit = (StackCommit) ? StackCommit : SystemBasicInfo.PageSize;
+ }
+
+ /* Align everything to Page Size */
+ StackReserve = ROUND_UP(StackReserve, SystemBasicInfo.AllocationGranularity);
+ StackCommit = ROUND_UP(StackCommit, SystemBasicInfo.PageSize);
+ #if 1 // FIXME: Remove once Guard Page support is here
+ StackCommit = StackReserve;
+ #endif
+ DPRINT("StackReserve: %lx, StackCommit: %lx\n", StackReserve, StackCommit);
+
+ /* Reserve memory for the stack */
+ Status = ZwAllocateVirtualMemory(hProcess,
+ (PVOID*)&Stack,
+ 0,
+ &StackReserve,
+ MEM_RESERVE,
+ PAGE_READWRITE);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failure to reserve stack\n");
+ return Status;
+ }
+
+ /* Now set up some basic Initial TEB Parameters */
+ InitialTeb->AllocatedStackBase = (PVOID)Stack;
+ InitialTeb->StackBase = (PVOID)(Stack + StackReserve);
+
+ /* Update the Stack Position */
+ Stack += StackReserve - StackCommit;
+
+ /* Check if we will need a guard page */
+ if (StackReserve > StackCommit)
+ {
+ Stack -= SystemBasicInfo.PageSize;
+ StackCommit += SystemBasicInfo.PageSize;
+ UseGuard = TRUE;
+ }
+
+ /* Allocate memory for the stack */
+ Status = ZwAllocateVirtualMemory(hProcess,
+ (PVOID*)&Stack,
+ 0,
+ &StackCommit,
+ MEM_COMMIT,
+ PAGE_READWRITE);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failure to allocate stack\n");
+ return Status;
+ }
+
+ /* Now set the current Stack Limit */
+ InitialTeb->StackLimit = (PVOID)Stack;
+
+ /* Create a guard page */
+ if (UseGuard)
+ {
+ ULONG GuardPageSize = SystemBasicInfo.PageSize;
+ ULONG Dummy;
+
+ /* Attempt maximum space possible */
+ Status = ZwProtectVirtualMemory(hProcess,
+ (PVOID*)&Stack,
+ &GuardPageSize,
+ PAGE_GUARD | PAGE_READWRITE,
+ &Dummy);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failure to create guard page\n");
+ return Status;
+ }
+
+ /* Update the Stack Limit keeping in mind the Guard Page */
+ InitialTeb->StackLimit = (PVOID)((ULONG_PTR)InitialTeb->StackLimit - GuardPageSize);
+ }
+
+ /* We are done! */
+ return STATUS_SUCCESS;
+}
+
+VOID
+STDCALL
+BasepFreeStack(HANDLE hProcess,
+ PINITIAL_TEB InitialTeb)
+{
+ ULONG Dummy = 0;
+
+ /* Free the Stack */
+ NtFreeVirtualMemory(hProcess,
+ &InitialTeb->AllocatedStackBase,
+ &Dummy,
+ MEM_RELEASE);
+}
+
+/*
+ * Creates the Initial Context for a Thread or Fiber
+ */
+VOID
+STDCALL
+BasepInitializeContext(IN PCONTEXT Context,
+ IN PVOID Parameter,
+ IN PVOID StartAddress,
+ IN PVOID StackAddress,
+ IN ULONG ContextType)
+{
+ DPRINT("BasepInitializeContext: %p\n", Context);
+
+ /* Setup the Initial Win32 Thread Context */
+ Context->Eax = (ULONG)StartAddress;
+ Context->Ebx = (ULONG)Parameter;
+ Context->Esp = (ULONG)StackAddress;
+ /* The other registers are undefined */
+
+ /* Setup the Segments */
+ Context->SegCs = USER_CS;
+ Context->SegDs = USER_DS;
+ Context->SegEs = USER_DS;
+ Context->SegFs = TEB_SELECTOR;
+ Context->SegSs = USER_DS;
+ Context->SegGs = 0;
+
+ /* Set the EFLAGS */
+ Context->EFlags = 0x3000; /* IOPL 3 */
+
+ if (ContextType == 1) /* For Threads */
+ {
+ Context->Eip = (ULONG)BaseThreadStartupThunk;
+ }
+ else if (ContextType == 2) /* For Fibers */
+ {
+ //Context->Eip = (ULONG)BaseFiberStartup;
+ }
+ else /* For first thread in a Process */
+ {
+ Context->Eip = (ULONG)BaseProcessStartThunk;
+ }
+
+ /* Set the Context Flags */
+ Context->ContextFlags = CONTEXT_FULL;
+
+ /* Give it some room for the Parameter */
+ Context->Esp -= sizeof(PVOID);
+}
+
+/*
+ * Checks if the privilege for Real-Time Priority is there
+ */
+BOOLEAN
+STDCALL
+BasepCheckRealTimePrivilege(VOID)
+{
+ return TRUE;
+}
+
+/*
+ * Maps an image file into a section
+ */
+NTSTATUS
+STDCALL
+BasepMapFile(IN LPCWSTR lpApplicationName,
+ OUT PHANDLE hSection,
+ IN PUNICODE_STRING ApplicationName)
+{
+ CURDIR RelativeName;
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ NTSTATUS Status;
+ HANDLE hFile = NULL;
+ IO_STATUS_BLOCK IoStatusBlock;
+
+ DPRINT("BasepMapFile\n");
+
+ /* Zero out the Relative Directory */
+ RelativeName.Handle = NULL;
+
+ /* Find the application name */
+ RtlDosPathNameToNtPathName_U((LPWSTR)lpApplicationName,
+ ApplicationName,
+ NULL,
+ &RelativeName);
+ DPRINT("ApplicationName %wZ\n", ApplicationName);
+ DPRINT("RelativeName %wZ\n", &RelativeName.DosPath);
+
+ /* Did we get a relative name? */
+ if (RelativeName.DosPath.Length)
+ {
+ ApplicationName = &RelativeName.DosPath;
+ }
+
+ /* Initialize the Object Attributes */
+ InitializeObjectAttributes(&ObjectAttributes,
+ ApplicationName,
+ OBJ_CASE_INSENSITIVE,
+ RelativeName.Handle,
+ NULL);
+
+ /* Try to open the executable */
+ Status = NtOpenFile(&hFile,
+ SYNCHRONIZE | FILE_EXECUTE | FILE_READ_DATA,
+ &ObjectAttributes,
+ &IoStatusBlock,
+ FILE_SHARE_DELETE | FILE_SHARE_READ,
+ FILE_SYNCHRONOUS_IO_NONALERT | FILE_NON_DIRECTORY_FILE);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to open file\n");
+ SetLastErrorByStatus (Status);
+ return Status;
+ }
+
+ /* Create a section for this file */
+ Status = NtCreateSection(hSection,
+ SECTION_ALL_ACCESS,
+ NULL,
+ NULL,
+ PAGE_EXECUTE,
+ SEC_IMAGE,
+ hFile);
+ NtClose(hFile);
+
+ /* Return status */
+ DPRINT("Section: %lx for file: %lx\n", *hSection, hFile);
+ return Status;
+}
--- trunk/reactos/lib/kernel32/thread/i386/thread.S 2005-07-12 04:41:41 UTC (rev 16542)
+++ trunk/reactos/lib/kernel32/thread/i386/thread.S 2005-07-12 05:00:33 UTC (rev 16543)
@@ -0,0 +1,32 @@
+/*
+ * COPYRIGHT: See COPYING in the top level directory
+ * PROJECT: ReactOS system libraries
+ * FILE: lib/kernel32/thread/i386/thread.S
+ * PURPOSE: Thread Start Thunks
+ * PROGRAMMER: Alex Ionescu (alex@relsoft.net)
+ */
+
+.globl _BaseThreadStartupThunk@0
+.globl _BaseProcessStartThunk@0
+.intel_syntax noprefix
+
+_BaseThreadStartupThunk@0:
+
+ /* Start out fresh */
+ xor ebp, ebp
+
+ push ebx /* lpParameter */
+ push eax /* lpStartAddress */
+ push 0 /* Return EIP */
+ //jmp _BaseThreadStartup@8
+
+_BaseProcessStartThunk@0:
+
+ /* Start out fresh */
+ xor ebp, ebp
+
+ push eax /* lpStartAddress */
+ push 0 /* Return EIP */
+ //jmp _BaseProcessStartup@4
+
+/* EOF */