From 9e7d29f65a005ae44d9a2f843351b822d34f96f2 Mon Sep 17 00:00:00 2001 From: Rex Jolliff Date: Tue, 25 Aug 1998 04:27:26 +0000 Subject: [PATCH] Initial revision svn path=/trunk/; revision=8 --- reactos/doc/ddkfuncs.txt | 27 + reactos/doc/debug.txt | 19 + reactos/drivers/readme | 11 + reactos/include/ddk/iodef.h | 284 ++ reactos/include/ddk/kedef.h | 41 + reactos/include/ddk/setypes.h | 10 + reactos/include/internal/wait.h | 2 + reactos/lib/kernel32/kernel32.def | 665 +++++ reactos/lib/ntdll/ntdll.def | 1053 +++++++ reactos/lib/ntdll/stubs.asm | 9 + reactos/lib/ntdll/sysfuncs.lst | 7 + reactos/ntoskrnl/ex/fmutex.c | 70 + reactos/ntoskrnl/ex/interlck.c | 45 + reactos/ntoskrnl/ex/resource.c | 133 + reactos/ntoskrnl/ex/time.c | 31 + reactos/ntoskrnl/ex/work.c | 157 ++ reactos/ntoskrnl/exports.lst | 375 +++ reactos/ntoskrnl/hal/x86/bios32.c | 140 + reactos/ntoskrnl/hal/x86/bus.c | 79 + reactos/ntoskrnl/hal/x86/dma.c | 132 + reactos/ntoskrnl/hal/x86/exp.c | 224 ++ reactos/ntoskrnl/hal/x86/halinit.c | 43 + reactos/ntoskrnl/hal/x86/head.s | 81 + reactos/ntoskrnl/hal/x86/irq.c | 369 +++ reactos/ntoskrnl/hal/x86/irqhand.asm | 106 + reactos/ntoskrnl/hal/x86/irql.c | 139 + reactos/ntoskrnl/hal/x86/irql.s | 205 ++ reactos/ntoskrnl/hal/x86/isa.c | 36 + reactos/ntoskrnl/hal/x86/mbr.c | 27 + reactos/ntoskrnl/hal/x86/mp.c | 27 + reactos/ntoskrnl/hal/x86/page.c | 205 ++ reactos/ntoskrnl/hal/x86/pci.c | 40 + reactos/ntoskrnl/hal/x86/printk.c | 247 ++ reactos/ntoskrnl/hal/x86/sources | 5 + reactos/ntoskrnl/hal/x86/spinlock.c | 104 + reactos/ntoskrnl/hal/x86/syscall.c | 9 + reactos/ntoskrnl/hal/x86/sysinfo.c | 25 + reactos/ntoskrnl/hal/x86/thread.c | 163 ++ reactos/ntoskrnl/hal/x86/usercall.asm | 46 + reactos/ntoskrnl/io/adapter.c | 60 + reactos/ntoskrnl/io/arc.c | 30 + reactos/ntoskrnl/io/cancel.c | 62 + reactos/ntoskrnl/io/cntrller.c | 145 + reactos/ntoskrnl/io/create.c | 101 + reactos/ntoskrnl/io/device.c | 186 ++ reactos/ntoskrnl/io/dpc.c | 33 + reactos/ntoskrnl/io/drvlck.c | 50 + reactos/ntoskrnl/io/errlog.c | 30 + reactos/ntoskrnl/io/error.c | 57 + reactos/ntoskrnl/io/event.c | 32 + reactos/ntoskrnl/io/fdisk.c | 44 + reactos/ntoskrnl/io/file.c | 42 + reactos/ntoskrnl/io/ioctrl.c | 24 + reactos/ntoskrnl/io/iomgr.c | 55 + reactos/ntoskrnl/io/irp.c | 295 ++ reactos/ntoskrnl/io/mdl.c | 69 + reactos/ntoskrnl/io/process.c | 29 + reactos/ntoskrnl/io/queue.c | 112 + reactos/ntoskrnl/io/resource.c | 59 + reactos/ntoskrnl/io/rw.c | 228 ++ reactos/ntoskrnl/io/share.c | 47 + reactos/ntoskrnl/io/shutdown.c | 29 + reactos/ntoskrnl/io/symlink.c | 36 + reactos/ntoskrnl/io/timer.c | 66 + reactos/ntoskrnl/ke/apc.c | 20 + reactos/ntoskrnl/ke/bug.c | 83 + reactos/ntoskrnl/ke/catch.c | 21 + reactos/ntoskrnl/ke/critical.c | 29 + reactos/ntoskrnl/ke/dispatch.c | 26 + reactos/ntoskrnl/ke/dpc.c | 114 + reactos/ntoskrnl/ke/error.c | 46 + reactos/ntoskrnl/ke/event.c | 56 + reactos/ntoskrnl/ke/exports.c | 748 +++++ reactos/ntoskrnl/ke/kqueue.c | 180 ++ reactos/ntoskrnl/ke/main.c | 175 ++ reactos/ntoskrnl/ke/module.c | 361 +++ reactos/ntoskrnl/ke/mutex.c | 49 + reactos/ntoskrnl/ke/sem.c | 40 + reactos/ntoskrnl/ke/timer.c | 407 +++ reactos/ntoskrnl/ke/wait.c | 82 + reactos/ntoskrnl/ldr/pe-bak.h | 281 ++ reactos/ntoskrnl/ldr/pe.h | 646 +++++ reactos/ntoskrnl/ldr/pedump.c | 3490 ++++++++++++++++++++++++ reactos/ntoskrnl/makefile_rex | 59 + reactos/ntoskrnl/mm/cont.c | 30 + reactos/ntoskrnl/mm/freelist.c | 205 ++ reactos/ntoskrnl/mm/iospace.c | 31 + reactos/ntoskrnl/mm/lock.c | 127 + reactos/ntoskrnl/mm/mdl.c | 224 ++ reactos/ntoskrnl/mm/mm.c | 173 ++ reactos/ntoskrnl/mm/ncache.c | 29 + reactos/ntoskrnl/mm/pageflt.asm | 24 + reactos/ntoskrnl/mm/pool.c | 652 +++++ reactos/ntoskrnl/mm/section.c | 45 + reactos/ntoskrnl/mm/virtual.c | 500 ++++ reactos/ntoskrnl/mm/zone.c | 158 ++ reactos/ntoskrnl/ntoskrnl.txt | 1084 ++++++++ reactos/ntoskrnl/ob/handle.c | 174 ++ reactos/ntoskrnl/ob/namespc.c | 363 +++ reactos/ntoskrnl/ob/object.c | 230 ++ reactos/ntoskrnl/ps/process.c | 27 + reactos/ntoskrnl/ps/psmgr.c | 21 + reactos/ntoskrnl/ps/thread.c | 324 +++ reactos/ntoskrnl/rtl/ctype.c | 37 + reactos/ntoskrnl/rtl/interlck.asm | 52 + reactos/ntoskrnl/rtl/largeint.c | 190 ++ reactos/ntoskrnl/rtl/list.c | 285 ++ reactos/ntoskrnl/rtl/lookas.c | 73 + reactos/ntoskrnl/rtl/mem.c | 72 + reactos/ntoskrnl/rtl/seqlist.c | 39 + reactos/ntoskrnl/rtl/slist.c | 92 + reactos/ntoskrnl/rtl/strtok.c | 66 + reactos/ntoskrnl/rtl/time.c | 31 + reactos/ntoskrnl/rtl/unalign.c | 43 + reactos/ntoskrnl/rtl/unicode.c | 561 ++++ reactos/ntoskrnl/rtl/unicode.c.new | 529 ++++ reactos/ntoskrnl/rtl/vsprintf.c | 326 +++ reactos/ntoskrnl/se/semgr.c | 96 + reactos/ntoskrnl/tst/test.c | 97 + reactos/ntoskrnl/utils/export/export | Bin 0 -> 33 bytes reactos/ntoskrnl/utils/export/export.c | 78 + 121 files changed, 21313 insertions(+) create mode 100644 reactos/doc/ddkfuncs.txt create mode 100644 reactos/doc/debug.txt create mode 100644 reactos/drivers/readme create mode 100644 reactos/include/ddk/iodef.h create mode 100644 reactos/include/ddk/kedef.h create mode 100644 reactos/include/ddk/setypes.h create mode 100644 reactos/include/internal/wait.h create mode 100644 reactos/lib/kernel32/kernel32.def create mode 100644 reactos/lib/ntdll/ntdll.def create mode 100644 reactos/lib/ntdll/stubs.asm create mode 100644 reactos/lib/ntdll/sysfuncs.lst create mode 100644 reactos/ntoskrnl/ex/fmutex.c create mode 100644 reactos/ntoskrnl/ex/interlck.c create mode 100644 reactos/ntoskrnl/ex/resource.c create mode 100644 reactos/ntoskrnl/ex/time.c create mode 100644 reactos/ntoskrnl/ex/work.c create mode 100644 reactos/ntoskrnl/exports.lst create mode 100644 reactos/ntoskrnl/hal/x86/bios32.c create mode 100644 reactos/ntoskrnl/hal/x86/bus.c create mode 100644 reactos/ntoskrnl/hal/x86/dma.c create mode 100644 reactos/ntoskrnl/hal/x86/exp.c create mode 100644 reactos/ntoskrnl/hal/x86/halinit.c create mode 100644 reactos/ntoskrnl/hal/x86/head.s create mode 100644 reactos/ntoskrnl/hal/x86/irq.c create mode 100644 reactos/ntoskrnl/hal/x86/irqhand.asm create mode 100644 reactos/ntoskrnl/hal/x86/irql.c create mode 100644 reactos/ntoskrnl/hal/x86/irql.s create mode 100644 reactos/ntoskrnl/hal/x86/isa.c create mode 100644 reactos/ntoskrnl/hal/x86/mbr.c create mode 100644 reactos/ntoskrnl/hal/x86/mp.c create mode 100644 reactos/ntoskrnl/hal/x86/page.c create mode 100644 reactos/ntoskrnl/hal/x86/pci.c create mode 100644 reactos/ntoskrnl/hal/x86/printk.c create mode 100644 reactos/ntoskrnl/hal/x86/sources create mode 100644 reactos/ntoskrnl/hal/x86/spinlock.c create mode 100644 reactos/ntoskrnl/hal/x86/syscall.c create mode 100644 reactos/ntoskrnl/hal/x86/sysinfo.c create mode 100644 reactos/ntoskrnl/hal/x86/thread.c create mode 100644 reactos/ntoskrnl/hal/x86/usercall.asm create mode 100644 reactos/ntoskrnl/io/adapter.c create mode 100644 reactos/ntoskrnl/io/arc.c create mode 100644 reactos/ntoskrnl/io/cancel.c create mode 100644 reactos/ntoskrnl/io/cntrller.c create mode 100644 reactos/ntoskrnl/io/create.c create mode 100644 reactos/ntoskrnl/io/device.c create mode 100644 reactos/ntoskrnl/io/dpc.c create mode 100644 reactos/ntoskrnl/io/drvlck.c create mode 100644 reactos/ntoskrnl/io/errlog.c create mode 100644 reactos/ntoskrnl/io/error.c create mode 100644 reactos/ntoskrnl/io/event.c create mode 100644 reactos/ntoskrnl/io/fdisk.c create mode 100644 reactos/ntoskrnl/io/file.c create mode 100644 reactos/ntoskrnl/io/ioctrl.c create mode 100644 reactos/ntoskrnl/io/iomgr.c create mode 100644 reactos/ntoskrnl/io/irp.c create mode 100644 reactos/ntoskrnl/io/mdl.c create mode 100644 reactos/ntoskrnl/io/process.c create mode 100644 reactos/ntoskrnl/io/queue.c create mode 100644 reactos/ntoskrnl/io/resource.c create mode 100644 reactos/ntoskrnl/io/rw.c create mode 100644 reactos/ntoskrnl/io/share.c create mode 100644 reactos/ntoskrnl/io/shutdown.c create mode 100644 reactos/ntoskrnl/io/symlink.c create mode 100644 reactos/ntoskrnl/io/timer.c create mode 100644 reactos/ntoskrnl/ke/apc.c create mode 100644 reactos/ntoskrnl/ke/bug.c create mode 100644 reactos/ntoskrnl/ke/catch.c create mode 100644 reactos/ntoskrnl/ke/critical.c create mode 100644 reactos/ntoskrnl/ke/dispatch.c create mode 100644 reactos/ntoskrnl/ke/dpc.c create mode 100644 reactos/ntoskrnl/ke/error.c create mode 100644 reactos/ntoskrnl/ke/event.c create mode 100644 reactos/ntoskrnl/ke/exports.c create mode 100644 reactos/ntoskrnl/ke/kqueue.c create mode 100644 reactos/ntoskrnl/ke/main.c create mode 100644 reactos/ntoskrnl/ke/module.c create mode 100644 reactos/ntoskrnl/ke/mutex.c create mode 100644 reactos/ntoskrnl/ke/sem.c create mode 100644 reactos/ntoskrnl/ke/timer.c create mode 100644 reactos/ntoskrnl/ke/wait.c create mode 100644 reactos/ntoskrnl/ldr/pe-bak.h create mode 100644 reactos/ntoskrnl/ldr/pe.h create mode 100644 reactos/ntoskrnl/ldr/pedump.c create mode 100644 reactos/ntoskrnl/makefile_rex create mode 100644 reactos/ntoskrnl/mm/cont.c create mode 100644 reactos/ntoskrnl/mm/freelist.c create mode 100644 reactos/ntoskrnl/mm/iospace.c create mode 100644 reactos/ntoskrnl/mm/lock.c create mode 100644 reactos/ntoskrnl/mm/mdl.c create mode 100644 reactos/ntoskrnl/mm/mm.c create mode 100644 reactos/ntoskrnl/mm/ncache.c create mode 100644 reactos/ntoskrnl/mm/pageflt.asm create mode 100644 reactos/ntoskrnl/mm/pool.c create mode 100644 reactos/ntoskrnl/mm/section.c create mode 100644 reactos/ntoskrnl/mm/virtual.c create mode 100644 reactos/ntoskrnl/mm/zone.c create mode 100644 reactos/ntoskrnl/ntoskrnl.txt create mode 100644 reactos/ntoskrnl/ob/handle.c create mode 100644 reactos/ntoskrnl/ob/namespc.c create mode 100644 reactos/ntoskrnl/ob/object.c create mode 100644 reactos/ntoskrnl/ps/process.c create mode 100644 reactos/ntoskrnl/ps/psmgr.c create mode 100644 reactos/ntoskrnl/ps/thread.c create mode 100644 reactos/ntoskrnl/rtl/ctype.c create mode 100644 reactos/ntoskrnl/rtl/interlck.asm create mode 100644 reactos/ntoskrnl/rtl/largeint.c create mode 100644 reactos/ntoskrnl/rtl/list.c create mode 100644 reactos/ntoskrnl/rtl/lookas.c create mode 100644 reactos/ntoskrnl/rtl/mem.c create mode 100644 reactos/ntoskrnl/rtl/seqlist.c create mode 100644 reactos/ntoskrnl/rtl/slist.c create mode 100644 reactos/ntoskrnl/rtl/strtok.c create mode 100644 reactos/ntoskrnl/rtl/time.c create mode 100644 reactos/ntoskrnl/rtl/unalign.c create mode 100644 reactos/ntoskrnl/rtl/unicode.c create mode 100644 reactos/ntoskrnl/rtl/unicode.c.new create mode 100644 reactos/ntoskrnl/rtl/vsprintf.c create mode 100644 reactos/ntoskrnl/se/semgr.c create mode 100644 reactos/ntoskrnl/tst/test.c create mode 100644 reactos/ntoskrnl/utils/export/export create mode 100644 reactos/ntoskrnl/utils/export/export.c diff --git a/reactos/doc/ddkfuncs.txt b/reactos/doc/ddkfuncs.txt new file mode 100644 index 00000000000..f7fbdfb1c69 --- /dev/null +++ b/reactos/doc/ddkfuncs.txt @@ -0,0 +1,27 @@ +This is a list of the functions documented in the ddk that have been +implemented + +IoAllocateController +IoFreeController +IoCreateController +IoDeleteController +IoStartNextPacket +IoStartNextPacketByKey +IoStartPacket +IoSizeOfIrp +IoMarkIrpPending +IoFreeIrp +IoConnectInterrupt +IoDisconnectInterrupt +IoGetCurrentIrpStackLocation +IoGetNextIrpStackLocation +IoRequestDpc +IoInitializeDpc +IoInitializeTimer +IoStartTimer +IoStopTimer + +Partially implemented + +IoCreateDevice +IoCallDriver diff --git a/reactos/doc/debug.txt b/reactos/doc/debug.txt new file mode 100644 index 00000000000..28467c6d883 --- /dev/null +++ b/reactos/doc/debug.txt @@ -0,0 +1,19 @@ +Some notes on debugging the ReactOS kernel +------------------------------------------ + +* Interpreting crashes + +If the kernel causes a fatal cpu fault then it will print out a message and +halt. This message contains important information for debugging the problem, +look for these lines + +Exception: xx(yy) +CS:EIP 20:zzzzzzzzzzzz + +Here xx is the type of error, usually either 14 or 13 and yy is the error +code. Generally error codes 13 and 14 both mean the kernel tried to access +some memory in an invalid way. zzzzzzzzz is the address of the erronous +instruction. + +* Debugging with bochs + diff --git a/reactos/drivers/readme b/reactos/drivers/readme new file mode 100644 index 00000000000..4f9dd7c0166 --- /dev/null +++ b/reactos/drivers/readme @@ -0,0 +1,11 @@ +These are a selection of services for the ReactOS kernel. They include + + parallel = parallel port driver + serial = serial port driver + mouse = mouse driver + null = null device driver + ide = IDE (hard disk) driver + keyboard = keyboard driver + loop = Allows accessing a file as a block device + scramdisk = Filesystem encryption driver + event = Sample driver demonstrating notifying a user thread using an event diff --git a/reactos/include/ddk/iodef.h b/reactos/include/ddk/iodef.h new file mode 100644 index 00000000000..392ffce583d --- /dev/null +++ b/reactos/include/ddk/iodef.h @@ -0,0 +1,284 @@ +typedef enum _IO_QUERY_DEVICE_DESCRIPTION +{ + IoQueryDeviceIdentifier = 0, + IoQueryDeviceConfigurationData, + IoQueryDeviceComponentInformation, + IoQueryDeviceDataFormatMaximum, +} IO_QUERY_DEVICE_DESCRIPTION, *PIO_QUERY_DEVICE_DESCRIPTION; + +typedef enum _CONFIGURATION_TYPE +{ + DiskController, + ParallelController, + MaximumType, +} CONFIGURATION_TYPE, *PCONFIGURATION_TYPE; + +typedef enum _CM_RESOURCE_TYPE +{ + CmResourceTypePort = 1, + CmResourceTypeInterrupt, + CmResourceTypeMemory, + CmResourceTypeDma, + CmResourceTypeDeviceSpecific, + CmResourceTypeMaximum, +} CM_RESOURCE_TYPE; + +typedef enum _CM_SHARE_DISPOSITION +{ + CmResourceShareDeviceExclusive = 1, + CmResourceShareDriverExclusive, + CmResourceShareShared, + CmResourceShareMaximum, +} CM_SHARE_DISPOSITION; + +enum +{ + CM_RESOURCE_INTERRUPT_LEVEL_SENSITIVE, + CM_RESOURCE_INTERRUPT_LATCHED, +}; + +enum +{ + CM_RESOURCE_PORT_MEMORY, + CM_RESOURCE_PORT_IO, +}; + +/* + * PURPOSE: Irp flags + */ +enum +{ + /* + * Read any data from the actual backing media + */ + IRP_NOCACHE, + + /* + * The I/O operation is performing paging + */ + IRP_PAGING_IO, + + /* + * The IRP is for a mount operation + */ + IRP_MOUNT_COMPLETION, + + /* + * The API expects synchronous behaviour + */ + IRP_SYNCHRONOUS_API, + + /* + * The IRP is associated with a larger operation + */ + IRP_ASSOCIATED_IRP, + + /* + * The AssociatedIrp.SystemBuffer field is valid + */ + IRP_BUFFERED_IO, + + /* + * The system buffer was allocated from pool and should be deallocated + * by the I/O manager + */ + IRP_DEALLOCATE_BUFFER, + + /* + * The IRP is for an input operation + */ + IRP_INPUT_OPERATION, + + /* + * The paging operation should complete synchronously + */ + IRP_SYNCHRONOUS_PAGING_IO, + + /* + * The IRP represents a filesystem create operation + */ + IRP_CREATE_OPERATION, + + /* + * The IRP represents a filesystem read operation + */ + IRP_READ_OPERATION, + + /* + * The IRP represents a filesystem write operation + */ + IRP_WRITE_OPERATION, + + /* + * The IRP represents a filesystem close operation + */ + IRP_CLOSE_OPERATION, + + /* + * Asynchronous behavior is advised but not required + */ + IRP_DEFER_IO_COMPLETION, +}; + +/* + * I/O operation flags + */ +enum +{ + /* + * Force an access check even if opened in kernel mode + */ + SL_FORCE_ACCESS_CHECK, + + /* + * The file being opened is a paging file + */ + SL_OPEN_PAGING_FILE, + + SL_OPEN_TARGET_DIRECTORY, + + SL_CASE_SENSITIVE, + + SL_KEY_SPECIFIED, + + SL_OVERRIDE_VERIFY_VOLUME, + + SL_WRITE_THROUGH, + + SL_FT_SEQUENTIAL_WRITE, + + SL_FAIL_IMMEDIATELY, + + SL_EXCLUSIVE_LOCK, + + SL_RESTART_SCAN, + + SL_RETURN_SINGLE_ENTRY, + + SL_INDEX_SPECIFIED, + + SL_WATCH_TREE, + + SL_ALLOW_RAW_MOUNT, + + SL_PENDING_RETURNED, + +}; + +enum +{ + SL_INVOKE_ON_SUCCESS = 1, + SL_INVOKE_ON_ERROR = 2, + SL_INVOKE_ON_CANCEL = 4, +}; + +/* + * Possible flags for the device object flags + */ +enum +{ + DO_BUFFERED_IO = 0x1, + DO_DIRECT_IO = 0x2, +}; + +/* + * Possible device types + */ +enum +{ + /* + * Standard define types + */ + FILE_DEVICE_BEEP, + FILE_DEVICE_CDROM, + FILE_DEVICE_CONTROLLER, + FILE_DEVICE_DISK, + FILE_DEVICE_INPORT_PORT, + FILE_DEVICE_KEYBOARD, + FILE_DEVICE_MIDI_IN, + FILE_DEVICE_MIDI_OUT, + FILE_DEVICE_MOUSE, + FILE_DEVICE_NULL, + FILE_DEVICE_PARALLEL_PORT, + FILE_DEVICE_PRINTER, + FILE_DEVICE_SCANNER, + FILE_DEVICE_SERIAL_MOUSE_PORT, + FILE_DEVICE_SERIAL_PORT, + FILE_DEVICE_SCREEN, + FILE_DEVICE_TAPE, + FILE_DEVICE_UNKNOWN, + FILE_DEVICE_VIDEO, + FILE_DEVICE_VIRTUAL_DISK, + FILE_DEVICE_WAVE_IN, + FILE_DEVICE_WAVE_OUT, + FILE_DEVICE_8042_PORT, + + /* + * Values beyond this are reserved for ISVs + */ + FILE_DEVICE_FIRST_FREE = 32768 +}; + + + +/* + * Possible device characteristics + */ +enum +{ + FILE_REMOVABLE_MEDIA = 0x1, + FILE_READ_ONLY_DEVICE = 0x2, + FILE_FLOPPY_DISKETTE = 0x4, + FILE_WRITE_ONCE_MEDIA = 0x8, + FILE_REMOTE_DEVICE = 0x10, +}; + +/* + * PURPOSE: Bus types + */ +enum +{ + Internal, + Isa, + MicroChannel, + TurboChannel, + PCIBus, + MaximumInterfaceType, +}; + +/* + * FIXME: These are not in the correct order + */ +enum +{ + IRP_MJ_CREATE, + IRP_MJ_CREATE_NAMED_PIPE, + IRP_MJ_CLOSE, + IRP_MJ_READ, + IRP_MJ_WRITE, + IRP_MJ_QUERY_INFORMATION, + IRP_MJ_SET_INFORMATION, + IRP_MJ_QUERY_EA, + IRP_MJ_SET_EA, + IRP_MJ_FLUSH_BUFFERS, + IRP_MJ_QUERY_VOLUME_INFORMATION, + IRP_MJ_SET_VOLUME_INFORMATION, + IRP_MJ_DIRECTORY_CONTROL, + IRP_MJ_FILE_SYSTEM_CONTROL, + IRP_MJ_DEVICE_CONTROL, + IRP_MJ_INTERNAL_DEVICE_CONTROL, + IRP_MJ_SHUTDOWN, + IRP_MJ_LOCK_CONTROL, + IRP_MJ_CLEANUP, + IRP_MJ_CREATE_MAILSLOT, + IRP_MJ_QUERY_SECURITY, + IRP_MJ_SET_SECURITY, + IRP_MJ_QUERY_POWER, + IRP_MJ_SET_POWER, + IRP_MJ_DEVICE_CHANGE, + IRP_MJ_QUERY_QUOTA, + IRP_MJ_SET_QUOTA, + IRP_MJ_PNP_POWER, + IRP_MJ_MAXIMUM_FUNCTION, +}; + diff --git a/reactos/include/ddk/kedef.h b/reactos/include/ddk/kedef.h new file mode 100644 index 00000000000..573f81e96a9 --- /dev/null +++ b/reactos/include/ddk/kedef.h @@ -0,0 +1,41 @@ +typedef enum _KINTERRUPT_MODE +{ + LevelSensitive, + Latched, +} KINTERRUPT_MODE; + +typedef enum _EVENT_TYPE +{ + NotificationEvent, + SynchronizationEvent, +} EVENT_TYPE; + +typedef enum _KWAIT_REASON +{ + Executive, + FreePage, + PageIn, + PoolAllocation, + DelayExecution, + Suspended, + UserRequest, + WrExecutive, + WrFreePage, + WrPageIn, + WrDelayExecution, + WrSuspended, + WrUserRequest, + WrQueue, + WrLpcReceive, + WrLpcReply, + WrVirtualMemory, + WrPageOut, + WrRendezvous, + Spare2, + Spare3, + Spare4, + Spare5, + Spare6, + WrKernel, + MaximumWaitReason, +} KWAIT_REASON; diff --git a/reactos/include/ddk/setypes.h b/reactos/include/ddk/setypes.h new file mode 100644 index 00000000000..d9e8b433ff1 --- /dev/null +++ b/reactos/include/ddk/setypes.h @@ -0,0 +1,10 @@ + +typedef ULONG ACCESS_MODE, *PACCESS_MODE; + +typedef struct _SECURITY_SUBJECT_CONTEXT +{ +} SECURITY_SUBJECT_CONTEXT, *PSECURITY_SUBJECT_CONTEXT; + +typedef struct _SECURITY_DESCRIPTOR_CONTEXT +{ +} SECURITY_DESCRIPTOR_CONTEXT, *PSECURITY_DESCRIPTOR_CONTEXT; diff --git a/reactos/include/internal/wait.h b/reactos/include/internal/wait.h new file mode 100644 index 00000000000..22d97cbe62d --- /dev/null +++ b/reactos/include/internal/wait.h @@ -0,0 +1,2 @@ +extern KSPIN_LOCK DispatcherDatabaseLock; +extern BOOLEAN WaitSet; diff --git a/reactos/lib/kernel32/kernel32.def b/reactos/lib/kernel32/kernel32.def new file mode 100644 index 00000000000..78ba330d391 --- /dev/null +++ b/reactos/lib/kernel32/kernel32.def @@ -0,0 +1,665 @@ +; +; kernel32.def +; +; Exports for KERNEL32 DLL +; +; Copyright (C) 1996 Free Software Foundation, Inc. +; +; Author: Scott Christley +; Date: 1996 +; +; This file is part of the Windows32 API Library. +; +; This library is free software; you can redistribute it and/or +; modify it under the terms of the GNU Library General Public +; License as published by the Free Software Foundation; either +; version 2 of the License, or (at your option) any later version. +; +; This library is distributed in the hope that it will be useful, +; but WITHOUT ANY WARRANTY; without even the implied warranty of +; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +; Library General Public License for more details. +; +; If you are interested in a warranty or support for this source code, +; contact Scott Christley for more information. +; +; You should have received a copy of the GNU Library General Public +; License along with this library; see the file COPYING.LIB. +; If not, write to the Free Software Foundation, +; 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +; +LIBRARY KERNEL32 +EXPORTS +AddAtomA@4 +AddAtomW@4 +AddConsoleAliasA@12 +AddConsoleAliasW@12 +AllocConsole@0 +AreFileApisANSI@0 +BackupRead@28 +BackupSeek@24 +BackupWrite@28 +BaseAttachCompleteThunk@0 +Beep@8 +BeginUpdateResourceA@8 +BeginUpdateResourceW@8 +BuildCommDCBA@8 +BuildCommDCBAndTimeoutsA@12 +BuildCommDCBAndTimeoutsW@12 +BuildCommDCBW@8 +CallNamedPipeA@28 +CallNamedPipeW@28 +ClearCommBreak@4 +ClearCommError@12 +CloseConsoleHandle@4 +CloseHandle@4 +CloseProfileUserMapping@0 +CmdBatNotification@4 +CommConfigDialogA@12 +CommConfigDialogW@12 +CompareFileTime@8 +CompareStringA@24 +CompareStringW@24 +ConnectNamedPipe@8 +ConsoleMenuControl@12 +ContinueDebugEvent@12 +ConvertDefaultLocale@4 +CopyFileA@12 +CopyFileW@12 +CreateConsoleScreenBuffer@20 +CreateDirectoryA@8 +CreateDirectoryExA@12 +CreateDirectoryExW@12 +CreateDirectoryW@8 +CreateEventA@16 +CreateEventW@16 +CreateFileA@28 +CreateFileMappingA@24 +CreateFileMappingW@24 +CreateFileW@28 +CreateIoCompletionPort@16 +CreateMailslotA@16 +CreateMailslotW@16 +CreateMutexA@12 +CreateMutexW@12 +CreateNamedPipeA@32 +CreateNamedPipeW@32 +CreatePipe@16 +CreateProcessA@40 +CreateProcessW@40 +CreateRemoteThread@28 +CreateSemaphoreA@16 +CreateSemaphoreW@16 +CreateTapePartition@16 +CreateThread@24 +CreateVirtualBuffer@12 +DebugActiveProcess@4 +DebugBreak@0 +DefineDosDeviceA@12 +DefineDosDeviceW@12 +DeleteAtom@4 +DeleteCriticalSection@4 +DeleteFileA@4 +DeleteFileW@4 +DeviceIoControl@32 +DisableThreadLibraryCalls@4 +DisconnectNamedPipe@4 +DosDateTimeToFileTime@12 +DuplicateConsoleHandle@16 +DuplicateHandle@28 +EndUpdateResourceA@8 +EndUpdateResourceW@8 +EnterCriticalSection@4 +EnumCalendarInfoA@16 +EnumCalendarInfoW@16 +EnumDateFormatsA@12 +EnumDateFormatsW@12 +EnumResourceLanguagesA@20 +EnumResourceLanguagesW@20 +EnumResourceNamesA@16 +EnumResourceNamesW@16 +EnumResourceTypesA@12 +EnumResourceTypesW@12 +EnumSystemCodePagesA@8 +EnumSystemCodePagesW@8 +EnumSystemLocalesA@8 +EnumSystemLocalesW@8 +EnumTimeFormatsA@12 +EnumTimeFormatsW@12 +EraseTape@12 +EscapeCommFunction@8 +ExitProcess@4 +ExitThread@4 +ExitVDM@8 +ExpandEnvironmentStringsA@12 +ExpandEnvironmentStringsW@12 +ExpungeConsoleCommandHistoryA@4 +ExpungeConsoleCommandHistoryW@4 +ExtendVirtualBuffer@8 +FatalAppExitA@8 +FatalAppExitW@8 +FatalExit@4 +FileTimeToDosDateTime@12 +FileTimeToLocalFileTime@8 +FileTimeToSystemTime@8 +FillConsoleOutputAttribute@20 +FillConsoleOutputCharacterA@20 +FillConsoleOutputCharacterW@20 +FindAtomA@4 +FindAtomW@4 +FindClose@4 +FindCloseChangeNotification@4 +FindFirstChangeNotificationA@12 +FindFirstChangeNotificationW@12 +FindFirstFileA@8 +FindFirstFileW@8 +FindNextChangeNotification@4 +FindNextFileA@8 +FindNextFileW@8 +FindResourceA@12 +FindResourceExA@16 +FindResourceExW@16 +FindResourceW@12 +FlushConsoleInputBuffer@4 +FlushFileBuffers@4 +FlushInstructionCache@12 +FlushViewOfFile@8 +FoldStringA@20 +FoldStringW@20 +FormatMessageA@28 +FormatMessageW@28 +FreeConsole@0 +FreeEnvironmentStringsA@4 +FreeEnvironmentStringsW@4 +FreeLibrary@4 +FreeLibraryAndExitThread@8 +FreeResource@4 +FreeVirtualBuffer@4 +GenerateConsoleCtrlEvent@8 +GetACP@0 +GetAtomNameA@12 +GetAtomNameW@12 +GetBinaryType@8 +GetBinaryTypeA@8 +GetBinaryTypeW@8 +GetCPInfo@8 +GetCommConfig@12 +GetCommMask@8 +GetCommModemStatus@8 +GetCommProperties@8 +GetCommState@8 +GetCommTimeouts@8 +GetCommandLineA@0 +GetCommandLineW@0 +GetCompressedFileSizeA@8 +GetCompressedFileSizeW@8 +GetComputerNameA@8 +GetComputerNameW@8 +GetConsoleAliasA@16 +GetConsoleAliasExesA@8 +GetConsoleAliasExesLengthA@0 +GetConsoleAliasExesLengthW@0 +GetConsoleAliasExesW@8 +GetConsoleAliasW@16 +GetConsoleAliasesA@12 +GetConsoleAliasesLengthA@4 +GetConsoleAliasesLengthW@4 +GetConsoleAliasesW@12 +GetConsoleCP@0 +GetConsoleCommandHistoryA@12 +GetConsoleCommandHistoryLengthA@4 +GetConsoleCommandHistoryLengthW@4 +GetConsoleCommandHistoryW@12 +GetConsoleCursorInfo@8 +GetConsoleDisplayMode@4 +GetConsoleFontInfo@16 +GetConsoleFontSize@8 +GetConsoleHardwareState@12 +GetConsoleInputWaitHandle@0 +GetConsoleMode@8 +GetConsoleOutputCP@0 +GetConsoleScreenBufferInfo@8 +GetConsoleTitleA@8 +GetConsoleTitleW@8 +GetCurrencyFormatA@24 +GetCurrencyFormatW@24 +GetCurrentConsoleFont@12 +GetCurrentDirectoryA@8 +GetCurrentDirectoryW@8 +GetCurrentProcess@0 +GetCurrentProcessId@0 +GetCurrentThread@0 +GetCurrentThreadId@0 +GetDateFormatA@24 +GetDateFormatW@24 +GetDefaultCommConfigA@12 +GetDefaultCommConfigW@12 +GetDiskFreeSpaceA@20 +GetDiskFreeSpaceW@20 +GetDriveTypeA@4 +GetDriveTypeW@4 +GetEnvironmentStrings@0 +GetEnvironmentStringsA@0 +GetEnvironmentStringsW@0 +GetEnvironmentVariableA@12 +GetEnvironmentVariableW@12 +GetExitCodeProcess@8 +GetExitCodeThread@8 +GetFileAttributesA@4 +GetFileAttributesW@4 +GetFileInformationByHandle@8 +GetFileSize@8 +GetFileTime@16 +GetFileType@4 +GetFullPathNameA@16 +GetFullPathNameW@16 +GetHandleInformation@8 +GetLargestConsoleWindowSize@4 +GetLastError@0 +GetLocalTime@4 +GetLocaleInfoA@16 +GetLocaleInfoW@16 +GetLogicalDriveStringsA@8 +GetLogicalDriveStringsW@8 +GetLogicalDrives@0 +GetMailslotInfo@20 +GetModuleFileNameA@12 +GetModuleFileNameW@12 +GetModuleHandleA@4 +GetModuleHandleW@4 +GetNamedPipeHandleStateA@28 +GetNamedPipeHandleStateW@28 +GetNamedPipeInfo@20 +GetNextVDMCommand@4 +GetNumberFormatA@24 +GetNumberFormatW@24 +GetNumberOfConsoleFonts@0 +GetNumberOfConsoleInputEvents@8 +GetNumberOfConsoleMouseButtons@4 +GetOEMCP@0 +GetOverlappedResult@16 +GetPriorityClass@4 +GetPrivateProfileIntA@16 +GetPrivateProfileIntW@16 +GetPrivateProfileSectionA@16 +GetPrivateProfileSectionNamesA@12 +GetPrivateProfileSectionNamesW@12 +GetPrivateProfileSectionW@16 +GetPrivateProfileStringA@24 +GetPrivateProfileStringW@24 +GetPrivateProfileStructA@20 +GetPrivateProfileStructW@20 +GetProcAddress@8 +GetProcessAffinityMask@12 +GetProcessHeap@0 +GetProcessHeaps@8 +GetProcessShutdownParameters@8 +GetProcessTimes@20 +GetProcessVersion@4 +GetProcessWorkingSetSize@12 +GetProfileIntA@12 +GetProfileIntW@12 +GetProfileSectionA@12 +GetProfileSectionW@12 +GetProfileStringA@20 +GetProfileStringW@20 +GetQueuedCompletionStatus@20 +GetShortPathNameA@12 +GetShortPathNameW@12 +GetStartupInfoA@4 +GetStartupInfoW@4 +GetStdHandle@4 +GetStringTypeA@20 +GetStringTypeExA@20 +GetStringTypeExW@20 +GetStringTypeW@16 +GetSystemDefaultLCID@0 +GetSystemDefaultLangID@0 +GetSystemDirectoryA@8 +GetSystemDirectoryW@8 +GetSystemInfo@4 +GetSystemPowerStatus@4 +GetSystemTime@4 +GetSystemTimeAdjustment@12 +GetSystemTimeAsFileTime@4 +GetTapeParameters@16 +GetTapePosition@20 +GetTapeStatus@4 +GetTempFileNameA@16 +GetTempFileNameW@16 +GetTempPathA@8 +GetTempPathW@8 +GetThreadContext@8 +_imp__GetThreadContext@8 +GetThreadLocale@0 +GetThreadPriority@4 +GetThreadSelectorEntry@12 +GetThreadTimes@20 +GetTickCount@0 +GetTimeFormatA@24 +GetTimeFormatW@24 +GetTimeZoneInformation@4 +GetUserDefaultLCID@0 +GetUserDefaultLangID@0 +GetVDMCurrentDirectories@8 +GetVersion@0 +GetVersionExA@4 +GetVersionExW@4 +GetVolumeInformationA@32 +GetVolumeInformationW@32 +GetWindowsDirectoryA@8 +GetWindowsDirectoryW@8 +GlobalAddAtomA@4 +GlobalAddAtomW@4 +GlobalAlloc@8 +GlobalCompact@4 +GlobalDeleteAtom@4 +GlobalFindAtomA@4 +GlobalFindAtomW@4 +GlobalFix@4 +GlobalFlags@4 +GlobalFree@4 +GlobalGetAtomNameA@12 +GlobalGetAtomNameW@12 +GlobalHandle@4 +GlobalLock@4 +GlobalMemoryStatus@4 +GlobalReAlloc@12 +GlobalSize@4 +GlobalUnWire@4 +GlobalUnfix@4 +GlobalUnlock@4 +GlobalWire@4 +HeapAlloc@12 +HeapCompact@8 +HeapCreate@12 +HeapCreateTagsW@16 +HeapDestroy@4 +HeapExtend@16 +HeapFree@12 +HeapLock@4 +HeapQueryTagW@20 +HeapReAlloc@16 +HeapSize@12 +HeapSummary@12 +HeapUnlock@4 +HeapUsage@20 +HeapValidate@12 +HeapWalk@8 +InitAtomTable@4 +InitializeCriticalSection@4 +InterlockedDecrement@4 +InterlockedExchange@8 +InterlockedIncrement@4 +InvalidateConsoleDIBits@8 +IsBadCodePtr@4 +IsBadHugeReadPtr@8 +IsBadHugeWritePtr@8 +IsBadReadPtr@8 +IsBadStringPtrA@8 +IsBadStringPtrW@8 +IsBadWritePtr@8 +IsDBCSLeadByte@4 +IsDBCSLeadByteEx@8 +IsDebuggerPresent@0 +IsValidCodePage@4 +IsValidLocale@8 +LCMapStringA@24 +LCMapStringW@24 +LeaveCriticalSection@4 +LoadLibraryA@4 +LoadLibraryExA@12 +LoadLibraryExW@12 +LoadLibraryW@4 +LoadModule@8 +LoadResource@8 +LocalAlloc@8 +LocalCompact@4 +LocalFileTimeToFileTime@8 +LocalFlags@4 +LocalFree@4 +LocalHandle@4 +LocalLock@4 +LocalReAlloc@12 +LocalShrink@8 +LocalSize@4 +LocalUnlock@4 +LockFile@20 +LockFileEx@24 +LockResource@4 +MapViewOfFile@20 +MapViewOfFileEx@24 +MoveFileA@8 +MoveFileExA@12 +MoveFileExW@12 +MoveFileW@8 +MulDiv@12 +MultiByteToWideChar@24 +OpenConsoleW@16 +OpenEventA@12 +OpenEventW@12 +OpenFile@12 +OpenFileMappingA@12 +OpenFileMappingW@12 +OpenMutexA@12 +OpenMutexW@12 +OpenProcess@12 +OpenProfileUserMapping@0 +OpenSemaphoreA@12 +OpenSemaphoreW@12 +OutputDebugStringA@4 +OutputDebugStringW@4 +PeekConsoleInputA@16 +PeekConsoleInputW@16 +PeekNamedPipe@24 +PostQueuedCompletionStatus@16 +PrepareTape@12 +PulseEvent@4 +PurgeComm@8 +QueryDosDeviceA@12 +QueryDosDeviceW@12 +QueryPerformanceCounter@4 +QueryPerformanceFrequency@4 +QueryWin31IniFilesMappedToRegistry@16 +RaiseException@16 +ReadConsoleA@20 +ReadConsoleInputA@16 +ReadConsoleInputW@16 +ReadConsoleOutputA@20 +ReadConsoleOutputAttribute@20 +ReadConsoleOutputCharacterA@20 +ReadConsoleOutputCharacterW@20 +ReadConsoleOutputW@20 +ReadConsoleW@20 +ReadFile@20 +ReadFileEx@20 +ReadProcessMemory@20 +RegisterConsoleVDM@44 +RegisterWaitForInputIdle@4 +RegisterWowBaseHandlers@4 +RegisterWowExec@4 +ReleaseMutex@4 +ReleaseSemaphore@12 +RemoveDirectoryA@4 +RemoveDirectoryW@4 +ResetEvent@4 +ResumeThread@4 +RtlFillMemory@12 +RtlMoveMemory@12 +RtlUnwind@16 +RtlZeroMemory@8 +ScrollConsoleScreenBufferA@20 +ScrollConsoleScreenBufferW@20 +SearchPathA@24 +SearchPathW@24 +SetCommBreak@4 +SetCommConfig@12 +SetCommMask@8 +SetCommState@8 +SetCommTimeouts@8 +SetComputerNameA@4 +SetComputerNameW@4 +SetConsoleActiveScreenBuffer@4 +SetConsoleCP@4 +SetConsoleCommandHistoryMode@4 +SetConsoleCtrlHandler@8 +SetConsoleCursor@8 +SetConsoleCursorInfo@8 +SetConsoleCursorPosition@8 +SetConsoleDisplayMode@12 +SetConsoleFont@8 +SetConsoleHardwareState@12 +SetConsoleKeyShortcuts@16 +SetConsoleMaximumWindowSize@8 +SetConsoleMenuClose@4 +SetConsoleMode@8 +SetConsoleNumberOfCommandsA@8 +SetConsoleNumberOfCommandsW@8 +SetConsoleOutputCP@4 +SetConsolePalette@12 +SetConsoleScreenBufferSize@8 +SetConsoleTextAttribute@8 +SetConsoleTitleA@4 +SetConsoleTitleW@4 +SetConsoleWindowInfo@12 +SetCurrentDirectoryA@4 +SetCurrentDirectoryW@4 +SetDefaultCommConfigA@12 +SetDefaultCommConfigW@12 +SetEndOfFile@4 +SetEnvironmentVariableA@8 +SetEnvironmentVariableW@8 +SetErrorMode@4 +SetEvent@4 +SetFileApisToANSI@0 +SetFileApisToOEM@0 +SetFileAttributesA@8 +SetFileAttributesW@8 +SetFilePointer@16 +SetFileTime@16 +SetHandleCount@4 +SetHandleInformation@12 +SetLastConsoleEventActive@0 +SetLastError@4 +SetLocalTime@4 +SetLocaleInfoA@12 +SetLocaleInfoW@12 +SetMailslotInfo@8 +SetNamedPipeHandleState@16 +SetPriorityClass@8 +SetProcessShutdownParameters@8 +SetProcessWorkingSetSize@12 +SetStdHandle@8 +SetSystemPowerState@8 +SetSystemTime@4 +SetSystemTimeAdjustment@8 +SetTapeParameters@12 +SetTapePosition@24 +SetThreadAffinityMask@8 +SetThreadContext@8 +_imp__SetThreadContext@8 +SetThreadLocale@4 +SetThreadPriority@8 +SetTimeZoneInformation@4 +SetUnhandledExceptionFilter@4 +SetVDMCurrentDirectories@8 +SetVolumeLabelA@8 +SetVolumeLabelW@8 +SetupComm@12 +ShowConsoleCursor@8 +SizeofResource@8 +Sleep@4 +SleepEx@8 +SuspendThread@4 +SystemTimeToFileTime@8 +SystemTimeToTzSpecificLocalTime@12 +TerminateProcess@8 +TerminateThread@8 +TlsAlloc@0 +TlsFree@4 +TlsGetValue@4 +TlsSetValue@8 +TransactNamedPipe@28 +TransmitCommChar@8 +TrimVirtualBuffer@4 +UnhandledExceptionFilter@4 +UnlockFile@20 +UnlockFileEx@20 +UnmapViewOfFile@4 +UpdateResourceA@24 +UpdateResourceW@24 +VDMConsoleOperation@8 +VDMOperationStarted@4 +VerLanguageNameA@12 +VerLanguageNameW@12 +VerifyConsoleIoHandle@4 +VirtualAlloc@16 +VirtualBufferExceptionHandler@12 +VirtualFree@12 +VirtualLock@8 +VirtualProtect@16 +VirtualProtectEx@20 +VirtualQuery@12 +VirtualQueryEx@16 +VirtualUnlock@8 +WaitCommEvent@12 +WaitForDebugEvent@8 +WaitForMultipleObjects@16 +WaitForMultipleObjectsEx@20 +WaitForSingleObject@8 +WaitForSingleObjectEx@12 +WaitNamedPipeA@8 +WaitNamedPipeW@8 +WideCharToMultiByte@32 +WinExec@8 +WriteConsoleA@20 +WriteConsoleInputA@16 +WriteConsoleInputVDMA@16 +WriteConsoleInputVDMW@16 +WriteConsoleInputW@16 +WriteConsoleOutputA@20 +WriteConsoleOutputAttribute@20 +WriteConsoleOutputCharacterA@20 +WriteConsoleOutputCharacterW@20 +WriteConsoleOutputW@20 +WriteConsoleW@20 +WriteFile@20 +WriteFileEx@20 +WritePrivateProfileSectionA@12 +WritePrivateProfileSectionW@12 +WritePrivateProfileStringA@16 +WritePrivateProfileStringW@16 +WritePrivateProfileStructA@20 +WritePrivateProfileStructW@20 +WriteProcessMemory@20 +WriteProfileSectionA@8 +WriteProfileSectionW@8 +WriteProfileStringA@12 +WriteProfileStringW@12 +WriteTapemark@16 +_hread@12 +_hwrite@12 +_lclose@4 +_lcreat@8 +_llseek@12 +_lopen@8 +_lread@12 +_lwrite@12 +lstrcat@8 +lstrcatA@8 +lstrcatW@8 +lstrcmp@8 +lstrcmpA@8 +lstrcmpW@8 +lstrcmpi@8 +lstrcmpiA@8 +lstrcmpiW@8 +lstrcpy@8 +lstrcpyA@8 +lstrcpyW@8 +lstrcpyn@12 +lstrcpynA@12 +lstrcpynW@12 +lstrlen@4 +lstrlenA@4 +lstrlenW@4 diff --git a/reactos/lib/ntdll/ntdll.def b/reactos/lib/ntdll/ntdll.def new file mode 100644 index 00000000000..6718843ee65 --- /dev/null +++ b/reactos/lib/ntdll/ntdll.def @@ -0,0 +1,1053 @@ +EXPORTS +?Allocate@CBufferAllocator@@UAEPAXK@Z +PropertyLengthAsVariant +RtlCompareVariants +RtlConvertPropertyToVariant +RtlConvertVariantToProperty +CsrAllocateCaptureBuffer +CsrAllocateCapturePointer +CsrAllocateMessagePointer +CsrCaptureMessageBuffer +CsrCaptureMessageString +CsrCaptureTimeout +CsrClientCallServer +CsrClientConnectToServer +CsrFreeCaptureBuffer +CsrIdentifyAlertableThread +CsrNewThread +CsrProbeForRead +CsrProbeForWrite +CsrSetPriorityClass +DbgBreakPoint +DbgPrint +DbgPrompt +DbgSsHandleKmApiMsg +DbgSsInitialize +DbgUiConnectToDbg +DbgUiContinue +DbgUiWaitStateChange +DbgUserBreakPoint +KiRaiseUserExceptionDispatcher +KiUserApcDispatcher +KiUserCallbackDispatcher +KiUserExceptionDispatcher +LdrAccessResource +LdrDisableThreadCalloutsForDll +LdrEnumResources +LdrFindEntryForAddress +LdrFindResourceDirectory_U +LdrFindResource_U +LdrGetDllHandle +LdrGetProcedureAddress +LdrInitializeThunk +LdrLoadDll +LdrProcessRelocationBlock +LdrQueryImageFileExecutionOptions +LdrQueryProcessModuleInformation +LdrShutdownProcess +LdrShutdownThread +LdrUnloadDll +LdrVerifyImageMatchesChecksum +NPXEMULATORTABLE +NlsAnsiCodePage +NlsMbCodePageTag +NlsMbOemCodePageTag +NtAcceptConnectPort +NtAccessCheck +NtAccessCheckAndAuditAlarm +NtAddAtom +NtAdjustGroupsToken +NtAdjustPrivilegesToken +NtAlertResumeThread +NtAlertThread +NtAllocateLocallyUniqueId +NtAllocateUuids +NtAllocateVirtualMemory +NtCallbackReturn +NtCancelIoFile +NtCancelTimer +NtClearEvent +NtClose +NtCloseObjectAuditAlarm +NtCompleteConnectPort +NtConnectPort +NtContinue +NtCreateChannel +NtCreateDirectoryObject +NtCreateEvent +NtCreateEventPair +NtCreateFile +NtCreateIoCompletion +NtCreateKey +NtCreateMailslotFile +NtCreateMutant +NtCreateNamedPipeFile +NtCreatePagingFile +NtCreatePort +NtCreateProcess +NtCreateProfile +NtCreateSection +NtCreateSemaphore +NtCreateSymbolicLinkObject +NtCreateThread +NtCreateTimer +NtCreateToken +NtCurrentTeb +NtDelayExecution +NtDeleteAtom +NtDeleteFile +NtDeleteKey +NtDeleteObjectAuditAlarm +NtDeleteValueKey +NtDeviceIoControlFile +NtDisplayString +NtDuplicateObject +NtDuplicateToken +NtEnumerateKey +NtEnumerateValueKey +NtExtendSection +NtFindAtom +NtFlushBuffersFile +NtFlushInstructionCache +NtFlushKey +NtFlushVirtualMemory +NtFlushWriteBuffer +NtFreeVirtualMemory +NtFsControlFile +NtGetContextThread +NtGetPlugPlayEvent +NtGetTickCount +NtImpersonateClientOfPort +NtImpersonateThread +NtInitializeRegistry +NtListenChannel +NtListenPort +NtLoadDriver +NtLoadKey2 +NtLoadKey +NtLockFile +NtLockVirtualMemory +NtMakeTemporaryObject +NtMapViewOfSection +NtNotifyChangeDirectoryFile +NtNotifyChangeKey +NtOpenChannel +NtOpenDirectoryObject +NtOpenEvent +NtOpenEventPair +NtOpenFile +NtOpenIoCompletion +NtOpenKey +NtOpenMutant +NtOpenObjectAuditAlarm +NtOpenProcess +NtOpenProcessToken +NtOpenSection +NtOpenSemaphore +NtOpenSymbolicLinkObject +NtOpenThread +NtOpenThreadToken +NtOpenTimer +NtPlugPlayControl +NtPrivilegeCheck +NtPrivilegeObjectAuditAlarm +NtPrivilegedServiceAuditAlarm +NtProtectVirtualMemory +NtPulseEvent +NtQueryAttributesFile +NtQueryDefaultLocale +NtQueryDirectoryFile +NtQueryDirectoryObject +NtQueryEaFile +NtQueryEvent +NtQueryFullAttributesFile +NtQueryInformationAtom +NtQueryInformationFile +NtQueryInformationPort +NtQueryInformationProcess +NtQueryInformationThread +NtQueryInformationToken +NtQueryIntervalProfile +NtQueryIoCompletion +NtQueryKey +NtQueryMultipleValueKey +NtQueryMutant +NtQueryObject +NtQueryOleDirectoryFile +NtQueryPerformanceCounter +NtQuerySection +NtQuerySecurityObject +NtQuerySemaphore +NtQuerySymbolicLinkObject +NtQuerySystemEnvironmentValue +NtQuerySystemInformation +NtQuerySystemTime +NtQueryTimer +NtQueryTimerResolution +NtQueryValueKey +NtQueryVirtualMemory +NtQueryVolumeInformationFile +NtQueueApcThread +NtRaiseException +NtRaiseHardError +NtReadFile +NtReadFileScatter +NtReadRequestData +NtReadVirtualMemory +NtRegisterThreadTerminatePort +NtReleaseMutant +NtReleaseSemaphore +NtRemoveIoCompletion +NtReplaceKey +NtReplyPort +NtReplyWaitReceivePort +NtReplyWaitReplyPort +NtReplyWaitSendChannel +NtRequestPort +NtRequestWaitReplyPort +NtResetEvent +NtRestoreKey +NtResumeThread +NtSaveKey +NtSendWaitReplyChannel +NtSetContextChannel +NtSetContextThread +NtSetDefaultHardErrorPort +NtSetDefaultLocale +NtSetEaFile +NtSetEvent +NtSetHighEventPair +NtSetHighWaitLowEventPair +NtSetHighWaitLowThread +NtSetInformationFile +NtSetInformationKey +NtSetInformationObject +NtSetInformationProcess +NtSetInformationThread +NtSetInformationToken +NtSetIntervalProfile +NtSetIoCompletion +NtSetLdtEntries +NtSetLowEventPair +NtSetLowWaitHighEventPair +NtSetLowWaitHighThread +NtSetSecurityObject +NtSetSystemEnvironmentValue +NtSetSystemInformation +NtSetSystemPowerState +NtSetSystemTime +NtSetTimer +NtSetTimerResolution +NtSetValueKey +NtSetVolumeInformationFile +NtShutdownSystem +NtSignalAndWaitForSingleObject +NtStartProfile +NtStopProfile +NtSuspendThread +NtSystemDebugControl +NtTerminateProcess +NtTerminateThread +NtTestAlert +NtUnloadDriver +NtUnloadKey +NtUnlockFile +NtUnlockVirtualMemory +NtUnmapViewOfSection +NtVdmControl +NtW32Call +NtWaitForMultipleObjects +NtWaitForSingleObject +NtWaitHighEventPair +NtWaitLowEventPair +NtWriteFile +NtWriteFileGather +NtWriteRequestData +NtWriteVirtualMemory +NtYieldExecution +PfxFindPrefix +PfxInitialize +PfxInsertPrefix +PfxRemovePrefix +RestoreEm87Context +RtlAbortRXact +RtlAbsoluteToSelfRelativeSD +RtlAcquirePebLock +RtlAcquireResourceExclusive +RtlAcquireResourceShared +RtlAddAccessAllowedAce +RtlAddAccessDeniedAce +RtlAddAce +RtlAddActionToRXact +RtlAddAtomToAtomTable +RtlAddAttributeActionToRXact +RtlAddAuditAccessAce +RtlAddCompoundAce +RtlAdjustPrivilege +RtlAllocateAndInitializeSid +RtlAllocateHandle +RtlAllocateHeap +RtlAnsiCharToUnicodeChar +RtlAnsiStringToUnicodeSize +RtlAnsiStringToUnicodeString +RtlAppendAsciizToString +RtlAppendStringToString +RtlAppendUnicodeStringToString +RtlAppendUnicodeToString +RtlApplyRXact +RtlApplyRXactNoFlush +RtlAreAllAccessesGranted +RtlAreAnyAccessesGranted +RtlAreBitsClear +RtlAreBitsSet +RtlAssert +RtlCaptureStackBackTrace +RtlCharToInteger +RtlCheckRegistryKey +RtlClearAllBits +RtlClearBits +RtlClosePropertySet +RtlCompactHeap +RtlCompareMemory +RtlCompareMemoryUlong +RtlCompareString +RtlCompareUnicodeString +RtlCompressBuffer +RtlConsoleMultiByteToUnicodeN +RtlConvertExclusiveToShared +RtlConvertLongToLargeInteger +RtlConvertSharedToExclusive +RtlConvertSidToUnicodeString +RtlConvertUiListToApiList +RtlConvertUlongToLargeInteger +RtlCopyLuid +RtlCopyLuidAndAttributesArray +RtlCopySecurityDescriptor +RtlCopySid +RtlCopySidAndAttributesArray +RtlCopyString +RtlCopyUnicodeString +RtlCreateAcl +RtlCreateAndSetSD +RtlCreateAtomTable +RtlCreateEnvironment +RtlCreateHeap +RtlCreateProcessParameters +RtlCreatePropertySet +RtlCreateQueryDebugBuffer +RtlCreateRegistryKey +RtlCreateSecurityDescriptor +RtlCreateTagHeap +RtlCreateUnicodeString +RtlCreateUnicodeStringFromAsciiz +RtlCreateUserProcess +RtlCreateUserSecurityObject +RtlCreateUserThread +RtlCustomCPToUnicodeN +RtlCutoverTimeToSystemTime +RtlDeNormalizeProcessParams +RtlDecompressBuffer +RtlDecompressFragment +RtlDelete +RtlDeleteAce +RtlDeleteAtomFromAtomTable +RtlDeleteCriticalSection +RtlDeleteElementGenericTable +RtlDeleteNoSplay +RtlDeleteRegistryValue +RtlDeleteResource +RtlDeleteSecurityObject +RtlDestroyAtomTable +RtlDestroyEnvironment +RtlDestroyHandleTable +RtlDestroyHeap +RtlDestroyProcessParameters +RtlDestroyQueryDebugBuffer +RtlDetermineDosPathNameType_U +RtlDoesFileExists_U +RtlDosPathNameToNtPathName_U +RtlDosSearchPath_U +RtlDowncaseUnicodeString +RtlDumpResource +RtlEmptyAtomTable +RtlEnlargedIntegerMultiply +RtlEnlargedUnsignedDivide +RtlEnlargedUnsignedMultiply +RtlEnterCriticalSection +RtlEnumProcessHeaps +RtlEnumerateGenericTable +RtlEnumerateGenericTableWithoutSplaying +RtlEnumerateProperties +RtlEqualComputerName +RtlEqualDomainName +RtlEqualLuid +RtlEqualPrefixSid +RtlEqualSid +RtlEqualString +RtlEqualUnicodeString +RtlEraseUnicodeString +RtlExpandEnvironmentStrings_U +RtlExtendHeap +RtlExtendedIntegerMultiply +RtlExtendedLargeIntegerDivide +RtlExtendedMagicDivide +RtlFillMemory +RtlFillMemoryUlong +RtlFindClearBits +RtlFindClearBitsAndSet +RtlFindLongestRunClear +RtlFindLongestRunSet +RtlFindMessage +RtlFindSetBits +RtlFindSetBitsAndClear +RtlFirstFreeAce +RtlFlushPropertySet +RtlFormatCurrentUserKeyPath +RtlFormatMessage +RtlFreeAnsiString +RtlFreeHandle +RtlFreeHeap +RtlFreeOemString +RtlFreeSid +RtlFreeUnicodeString +RtlFreeUserThreadStack +RtlGenerate8dot3Name +RtlGetAce +RtlGetCallersAddress +RtlGetCompressionWorkSpaceSize +RtlGetControlSecurityDescriptor +RtlGetCurrentDirectory_U +RtlGetDaclSecurityDescriptor +RtlGetElementGenericTable +RtlGetFullPathName_U +RtlGetGroupSecurityDescriptor +RtlGetLongestNtPathLength +RtlGetNtGlobalFlags +RtlGetNtProductType +RtlGetOwnerSecurityDescriptor +RtlGetProcessHeaps +RtlGetSaclSecurityDescriptor +RtlGetUserInfoHeap +RtlGuidToPropertySetName +RtlIdentifierAuthoritySid +RtlImageDirectoryEntryToData +RtlImageNtHeader +RtlImageRvaToSection +RtlImageRvaToVa +RtlImpersonateSelf +RtlInitAnsiString +RtlInitCodePageTable +RtlInitNlsTables +RtlInitString +RtlInitUnicodeString +RtlInitializeAtomPackage +RtlInitializeBitMap +RtlInitializeContext +RtlInitializeCriticalSection +RtlInitializeCriticalSectionAndSpinCount +RtlInitializeGenericTable +RtlInitializeHandleTable +RtlInitializeRXact +RtlInitializeResource +RtlInitializeSid +RtlInsertElementGenericTable +RtlIntegerToChar +RtlIntegerToUnicodeString +RtlIsDosDeviceName_U +RtlIsGenericTableEmpty +RtlIsNameLegalDOS8Dot3 +RtlIsTextUnicode +RtlIsValidHandle +RtlIsValidIndexHandle +RtlLargeIntegerAdd +RtlLargeIntegerArithmeticShift +RtlLargeIntegerDivide +RtlLargeIntegerNegate +RtlLargeIntegerShiftLeft +RtlLargeIntegerShiftRight +RtlLargeIntegerSubtract +RtlLargeIntegerToChar +RtlLeaveCriticalSection +RtlLengthRequiredSid +RtlLengthSecurityDescriptor +RtlLengthSid +RtlLocalTimeToSystemTime +RtlLockHeap +RtlLookupAtomInAtomTable +RtlLookupElementGenericTable +RtlMakeSelfRelativeSD +RtlMapGenericMask +RtlMoveMemory +RtlMultiByteToUnicodeN +RtlMultiByteToUnicodeSize +RtlNewInstanceSecurityObject +RtlNewSecurityGrantedAccess +RtlNewSecurityObject +RtlNormalizeProcessParams +RtlNtStatusToDosError +RtlNumberGenericTableElements +RtlNumberOfClearBits +RtlNumberOfSetBits +RtlOemStringToUnicodeSize +RtlOemStringToUnicodeString +RtlOemToUnicodeN +RtlOnMappedStreamEvent +RtlOpenCurrentUser +RtlPcToFileHeader +RtlPinAtomInAtomTable +RtlPrefixString +RtlPrefixUnicodeString +RtlPropertySetNameToGuid +RtlProtectHeap +RtlQueryAtomInAtomTable +RtlQueryEnvironmentVariable_U +RtlQueryInformationAcl +RtlQueryProcessBackTraceInformation +RtlQueryProcessDebugInformation +RtlQueryProcessHeapInformation +RtlQueryProcessLockInformation +RtlQueryProperties +RtlQueryPropertyNames +RtlQueryPropertySet +RtlQueryRegistryValues +RtlQuerySecurityObject +RtlQueryTagHeap +RtlQueryTimeZoneInformation +RtlRaiseException +RtlRaiseStatus +RtlRandom +RtlReAllocateHeap +RtlRealPredecessor +RtlRealSuccessor +RtlReleasePebLock +RtlReleaseResource +RtlRemoteCall +RtlResetRtlTranslations +RtlRunDecodeUnicodeString +RtlRunEncodeUnicodeString +RtlSecondsSince1970ToTime +RtlSecondsSince1980ToTime +RtlSelfRelativeToAbsoluteSD +RtlSetAllBits +RtlSetAttributesSecurityDescriptor +RtlSetBits +RtlSetCriticalSectionSpinCount +RtlSetCurrentDirectory_U +RtlSetCurrentEnvironment +RtlSetDaclSecurityDescriptor +RtlSetEnvironmentVariable +RtlSetGroupSecurityDescriptor +RtlSetInformationAcl +RtlSetOwnerSecurityDescriptor +RtlSetProperties +RtlSetPropertyNames +RtlSetPropertySetClassId +RtlSetSaclSecurityDescriptor +RtlSetSecurityObject +RtlSetTimeZoneInformation +RtlSetUnicodeCallouts +RtlSetUserFlagsHeap +RtlSetUserValueHeap +RtlSizeHeap +RtlSplay +RtlStartRXact +RtlSubAuthorityCountSid +RtlSubAuthoritySid +RtlSubtreePredecessor +RtlSubtreeSuccessor +RtlSystemTimeToLocalTime +RtlTimeFieldsToTime +RtlTimeToElapsedTimeFields +RtlTimeToSecondsSince1970 +RtlTimeToSecondsSince1980 +RtlTimeToTimeFields +RtlTryEnterCriticalSection +RtlUnicodeStringToAnsiSize +RtlUnicodeStringToAnsiString +RtlUnicodeStringToCountedOemString +RtlUnicodeStringToInteger +RtlUnicodeStringToOemSize +RtlUnicodeStringToOemString +RtlUnicodeToCustomCPN +RtlUnicodeToMultiByteN +RtlUnicodeToMultiByteSize +RtlUnicodeToOemN +RtlUniform +RtlUnlockHeap +RtlUnwind +RtlUpcaseUnicodeChar +RtlUpcaseUnicodeString +RtlUpcaseUnicodeStringToAnsiString +RtlUpcaseUnicodeStringToCountedOemString +RtlUpcaseUnicodeStringToOemString +RtlUpcaseUnicodeToCustomCPN +RtlUpcaseUnicodeToMultiByteN +RtlUpcaseUnicodeToOemN +RtlUpperChar +RtlUpperString +RtlUsageHeap +RtlValidAcl +RtlValidSecurityDescriptor +RtlValidSid +RtlValidateHeap +RtlValidateProcessHeaps +RtlWalkHeap +RtlWriteRegistryValue +RtlZeroHeap +RtlZeroMemory +RtlpNtCreateKey +RtlpNtEnumerateSubKey +RtlpNtMakeTemporaryKey +RtlpNtOpenKey +RtlpNtQueryValueKey +RtlpNtSetValueKey +RtlpUnWaitCriticalSection +RtlpWaitForCriticalSection +RtlxAnsiStringToUnicodeSize +RtlxOemStringToUnicodeSize +RtlxUnicodeStringToAnsiSize +RtlxUnicodeStringToOemSize +SaveEm87Context +ZwAcceptConnectPort +ZwAccessCheck +ZwAccessCheckAndAuditAlarm +ZwAddAtom +ZwAdjustGroupsToken +ZwAdjustPrivilegesToken +ZwAlertResumeThread +ZwAlertThread +ZwAllocateLocallyUniqueId +ZwAllocateUuids +ZwAllocateVirtualMemory +ZwCallbackReturn +ZwCancelIoFile +ZwCancelTimer +ZwClearEvent +ZwClose +ZwCloseObjectAuditAlarm +ZwCompleteConnectPort +ZwConnectPort +ZwContinue +ZwCreateChannel +ZwCreateDirectoryObject +ZwCreateEvent +ZwCreateEventPair +ZwCreateFile +ZwCreateIoCompletion +ZwCreateKey +ZwCreateMailslotFile +ZwCreateMutant +ZwCreateNamedPipeFile +ZwCreatePagingFile +ZwCreatePort +ZwCreateProcess +ZwCreateProfile +ZwCreateSection +ZwCreateSemaphore +ZwCreateSymbolicLinkObject +ZwCreateThread +ZwCreateTimer +ZwCreateToken +ZwDelayExecution +ZwDeleteAtom +ZwDeleteFile +ZwDeleteKey +ZwDeleteObjectAuditAlarm +ZwDeleteValueKey +ZwDeviceIoControlFile +ZwDisplayString +ZwDuplicateObject +ZwDuplicateToken +ZwEnumerateKey +ZwEnumerateValueKey +ZwExtendSection +ZwFindAtom +ZwFlushBuffersFile +ZwFlushInstructionCache +ZwFlushKey +ZwFlushVirtualMemory +ZwFlushWriteBuffer +ZwFreeVirtualMemory +ZwFsControlFile +ZwGetContextThread +ZwGetPlugPlayEvent +ZwGetTickCount +ZwImpersonateClientOfPort +ZwImpersonateThread +ZwInitializeRegistry +ZwListenChannel +ZwListenPort +ZwLoadDriver +ZwLoadKey2 +ZwLoadKey +ZwLockFile +ZwLockVirtualMemory +ZwMakeTemporaryObject +ZwMapViewOfSection +ZwNotifyChangeDirectoryFile +ZwNotifyChangeKey +ZwOpenChannel +ZwOpenDirectoryObject +ZwOpenEvent +ZwOpenEventPair +ZwOpenFile +ZwOpenIoCompletion +ZwOpenKey +ZwOpenMutant +ZwOpenObjectAuditAlarm +ZwOpenProcess +ZwOpenProcessToken +ZwOpenSection +ZwOpenSemaphore +ZwOpenSymbolicLinkObject +ZwOpenThread +ZwOpenThreadToken +ZwOpenTimer +ZwPlugPlayControl +ZwPrivilegeCheck +ZwPrivilegeObjectAuditAlarm +ZwPrivilegedServiceAuditAlarm +ZwProtectVirtualMemory +ZwPulseEvent +ZwQueryAttributesFile +ZwQueryDefaultLocale +ZwQueryDirectoryFile +ZwQueryDirectoryObject +ZwQueryEaFile +ZwQueryEvent +ZwQueryFullAttributesFile +ZwQueryInformationAtom +ZwQueryInformationFile +ZwQueryInformationPort +ZwQueryInformationProcess +ZwQueryInformationThread +ZwQueryInformationToken +ZwQueryIntervalProfile +ZwQueryIoCompletion +ZwQueryKey +ZwQueryMultipleValueKey +ZwQueryMutant +ZwQueryObject +ZwQueryOleDirectoryFile +ZwQueryPerformanceCounter +ZwQuerySection +ZwQuerySecurityObject +ZwQuerySemaphore +ZwQuerySymbolicLinkObject +ZwQuerySystemEnvironmentValue +ZwQuerySystemInformation +ZwQuerySystemTime +ZwQueryTimer +ZwQueryTimerResolution +ZwQueryValueKey +ZwQueryVirtualMemory +ZwQueryVolumeInformationFile +ZwQueueApcThread +ZwRaiseException +ZwRaiseHardError +ZwReadFile +ZwReadFileScatter +ZwReadRequestData +ZwReadVirtualMemory +ZwRegisterThreadTerminatePort +ZwReleaseMutant +ZwReleaseSemaphore +ZwRemoveIoCompletion +ZwReplaceKey +ZwReplyPort +ZwReplyWaitReceivePort +ZwReplyWaitReplyPort +ZwReplyWaitSendChannel +ZwRequestPort +ZwRequestWaitReplyPort +ZwResetEvent +ZwRestoreKey +ZwResumeThread +ZwSaveKey +ZwSendWaitReplyChannel +ZwSetContextChannel +ZwSetContextThread +ZwSetDefaultHardErrorPort +ZwSetDefaultLocale +ZwSetEaFile +ZwSetEvent +ZwSetHighEventPair +ZwSetHighWaitLowEventPair +ZwSetHighWaitLowThread +ZwSetInformationFile +ZwSetInformationKey +ZwSetInformationObject +ZwSetInformationProcess +ZwSetInformationThread +ZwSetInformationToken +ZwSetIntervalProfile +ZwSetIoCompletion +ZwSetLdtEntries +ZwSetLowEventPair +ZwSetLowWaitHighEventPair +ZwSetLowWaitHighThread +ZwSetSecurityObject +ZwSetSystemEnvironmentValue +ZwSetSystemInformation +ZwSetSystemPowerState +ZwSetSystemTime +ZwSetTimer +ZwSetTimerResolution +ZwSetValueKey +ZwSetVolumeInformationFile +ZwShutdownSystem +ZwSignalAndWaitForSingleObject +ZwStartProfile +ZwStopProfile +ZwSuspendThread +ZwSystemDebugControl +ZwTerminateProcess +ZwTerminateThread +ZwTestAlert +ZwUnloadDriver +ZwUnloadKey +ZwUnlockFile +ZwUnlockVirtualMemory +ZwUnmapViewOfSection +ZwVdmControl +ZwW32Call +ZwWaitForMultipleObjects +ZwWaitForSingleObject +ZwWaitHighEventPair +ZwWaitLowEventPair +ZwWriteFile +ZwWriteFileGather +ZwWriteRequestData +ZwWriteVirtualMemory +ZwYieldExecution +_CIpow +__eCommonExceptions +__eEmulatorInit +__eF2XM1 +__eFABS +__eFADD32 +__eFADD64 +__eFADDPreg +__eFADDreg +__eFADDtop +__eFCHS +__eFCOM +__eFCOM32 +__eFCOM64 +__eFCOMP +__eFCOMP32 +__eFCOMP64 +__eFCOMPP +__eFCOS +__eFDECSTP +__eFDIV32 +__eFDIV64 +__eFDIVPreg +__eFDIVR32 +__eFDIVR64 +__eFDIVRPreg +__eFDIVRreg +__eFDIVRtop +__eFDIVreg +__eFDIVtop +__eFFREE +__eFIADD16 +__eFIADD32 +__eFICOM16 +__eFICOM32 +__eFICOMP16 +__eFICOMP32 +__eFIDIV16 +__eFIDIV32 +__eFIDIVR16 +__eFIDIVR32 +__eFILD16 +__eFILD32 +__eFILD64 +__eFIMUL16 +__eFIMUL32 +__eFINCSTP +__eFINIT +__eFIST16 +__eFIST32 +__eFISTP16 +__eFISTP32 +__eFISTP64 +__eFISUB16 +__eFISUB32 +__eFISUBR16 +__eFISUBR32 +__eFLD1 +__eFLD32 +__eFLD64 +__eFLD80 +__eFLDCW +__eFLDENV +__eFLDL2E +__eFLDLN2 +__eFLDPI +__eFLDZ +__eFMUL32 +__eFMUL64 +__eFMULPreg +__eFMULreg +__eFMULtop +__eFPATAN +__eFPREM +__eFPREM1 +__eFPTAN +__eFRNDINT +__eFRSTOR +__eFSAVE +__eFSCALE +__eFSIN +__eFSQRT +__eFST +__eFST32 +__eFST64 +__eFSTCW +__eFSTENV +__eFSTP +__eFSTP32 +__eFSTP64 +__eFSTP80 +__eFSTSW +__eFSUB32 +__eFSUB64 +__eFSUBPreg +__eFSUBR32 +__eFSUBR64 +__eFSUBRPreg +__eFSUBRreg +__eFSUBRtop +__eFSUBreg +__eFSUBtop +__eFTST +__eFUCOM +__eFUCOMP +__eFUCOMPP +__eFXAM +__eFXCH +__eFXTRACT +__eFYL2X +__eFYL2XP1 +__eGetStatusWord +__isascii +__iscsym +__iscsymf +__toascii +_alldiv +_allmul +_alloca_probe +_allrem +_allshl +_allshr +_atoi64 +_aulldiv +_aullrem +_aullshr +_chkstk +_fltused +_ftol +_i64toa +_i64tow +_itoa +_itow +_ltoa +_ltow +_memccpy +_memicmp +_snprintf +_snwprintf +_splitpath +_strcmpi +_stricmp +_strlwr +_strnicmp +_strupr +_tolower +_toupper +_ultoa +_ultow +_vsnprintf +_wcsicmp +_wcslwr +_wcsnicmp +_wcsupr +_wtoi +_wtoi64 +_wtol +abs +atan +atoi +atol +ceil +cos +fabs +floor +isalnum +isalpha +iscntrl +isdigit +isgraph +islower +isprint +ispunct +isspace +isupper +iswalpha +iswctype +isxdigit +labs +log +mbstowcs +memchr +memcmp +memcpy +memmove +memset +pow +qsort +sin +sprintf +sqrt +sscanf +strcat +strchr +strcmp +strcpy +strcspn +strlen +strncat +strncmp +strncpy +strpbrk +strrchr +strspn +strstr +strtol +strtoul +swprintf +tan +tolower +toupper +towlower +towupper +vsprintf +wcscat +wcschr +wcscmp +wcscpy +wcscspn +wcslen +wcsncat +wcsncmp +wcsncpy +wcspbrk +wcsrchr +wcsspn +wcsstr +wcstol +wcstombs +wcstoul +wcstoul diff --git a/reactos/lib/ntdll/stubs.asm b/reactos/lib/ntdll/stubs.asm new file mode 100644 index 00000000000..6f6b033fbe0 --- /dev/null +++ b/reactos/lib/ntdll/stubs.asm @@ -0,0 +1,9 @@ +; Machine generated, don't edit + + +NtAlertThread: + mov eax,4 + lea edx,[esp+4] + int 2Eh + ret 14 + diff --git a/reactos/lib/ntdll/sysfuncs.lst b/reactos/lib/ntdll/sysfuncs.lst new file mode 100644 index 00000000000..85dbbbc1fdb --- /dev/null +++ b/reactos/lib/ntdll/sysfuncs.lst @@ -0,0 +1,7 @@ +# +# This defines the kernel entry points used by ntdll +# +# They have the following format +# +# +NtAlertThread 4 14 diff --git a/reactos/ntoskrnl/ex/fmutex.c b/reactos/ntoskrnl/ex/fmutex.c new file mode 100644 index 00000000000..52301362fee --- /dev/null +++ b/reactos/ntoskrnl/ex/fmutex.c @@ -0,0 +1,70 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ex/fmutex.c + * PURPOSE: Implements fast mutexes + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID ExAcquireFastMutex(PFAST_MUTEX FastMutex) +{ + KeEnterCriticalRegion(); + ExAcquireFastMutexUnsafe(FastMutex); +} + +VOID ExAcquireFastMutexUnsafe(PFAST_MUTEX FastMutex) +{ + if (InterlockedDecrement(&(FastMutex->Count))==0) + { + return; + } + FastMutex->Contention++; + KeWaitForSingleObject(&(FastMutex->Event),Executive,KernelMode, + FALSE,NULL); + FastMutex->Owner=KeGetCurrentThread(); +} + +VOID ExInitializeFastMutex(PFAST_MUTEX FastMutex) +{ + FastMutex->Count=1; + FastMutex->Owner=NULL; + FastMutex->Contention=0; + KeInitializeEvent(&(FastMutex->Event),SynchronizationEvent,FALSE); +} + +VOID ExReleaseFastMutexUnsafe(PFAST_MUTEX FastMutex) +{ + assert(FastMutex->Owner==KeGetCurrentThread()); + FastMutex->Owner=NULL; + if (InterlockedIncrement(&(FastMutex->Count))<=0) + { + return; + } + KeSetEvent(&(FastMutex->Event),0,FALSE); +} + +VOID ExReleaseFastMutex(PFAST_MUTEX FastMutex) +{ + ExReleaseFastMutexUnsafe(FastMutex); + KeLeaveCriticalRegion(); +} + +BOOLEAN ExTryToAcquireFastMutex(PFAST_MUTEX FastMutex) +{ + InterlockedCompareExchange(&(FastMutex->Count),0,0); +} + + + diff --git a/reactos/ntoskrnl/ex/interlck.c b/reactos/ntoskrnl/ex/interlck.c new file mode 100644 index 00000000000..46ede4042fd --- /dev/null +++ b/reactos/ntoskrnl/ex/interlck.c @@ -0,0 +1,45 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ex/interlck.c + * PURPOSE: Implements interlocked functions + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +INTERLOCKED_RESULT ExInterlockedDecrementLong(PLONG Addend, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +ULONG ExInterlockedExchangeUlong(PULONG Target, + ULONG Value, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +ULONG ExInterlockedAddUlong(PULONG Addend, + ULONG Increment, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +INTERLOCKED_RESULT ExInterlockedIncrementLong(PLONG Addend, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/ex/resource.c b/reactos/ntoskrnl/ex/resource.c new file mode 100644 index 00000000000..e02046c2b4e --- /dev/null +++ b/reactos/ntoskrnl/ex/resource.c @@ -0,0 +1,133 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/excutive/resource.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +BOOLEAN ExAcquireResourceExclusive(PERESOURCE Resource, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +BOOLEAN ExAcquireResourceExclusiveLite(PERESOURCE Resource, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +BOOLEAN ExAcquireResourceSharedLite(PERESOURCE Resource, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +VOID ExConvertExclusiveToSharedLite(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +ULONG ExGetExclusiveWaiterCount(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +BOOLEAN ExAcquireSharedStarveExclusive(PERESOURCE Resource, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +BOOLEAN ExAcquireSharedWaitForExclusive(PERESOURCE Resource, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +NTSTATUS ExDeleteResource(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +NTSTATUS ExDeleteResourceLite(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +ERESOURCE_THREAD ExGetCurrentResourceThread() +{ + UNIMPLEMENTED; +} + +ULONG ExGetSharedWaiterCount(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +NTSTATUS ExInitializeResource(PERESOURCE Resource) +{ +} + +NTSTATUS ExInitializeResourceLite(PERESOURCE Resource) +{ + Resource->NumberOfSharedWaiters = 0; + Resource->NumberOfExclusiveWaiters = 0; + KeInitializeSpinLock(&Resource->SpinLock); + Resource->Flag=0; + KeInitializeEvent(&Resource->ExclusiveWaiters,SynchronizationEvent, + FALSE); + KeInitializeSemaphore(&Resource->SharedWaiters,5,0); + Resource->ActiveCount = 0; +} + +BOOLEAN ExIsResourceAcquiredExclusiveLite(PERESOURCE Resource) +{ + return(Resource->NumberOfExclusiveWaiters!=0); +} + +BOOLEAN ExIsResourceAcquiredSharedLite(PERESOURCE Resource) +{ + return(Resource->NumberOfSharedWaiters!=0); +} + +VOID ExReinitializeResourceLite(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +VOID ExReleaseResource(PERESOURCE Resource) +{ + UNIMPLEMENTED; +} + +VOID ExReleaseResourceForThread(PERESOURCE Resource, + ERESOURCE_THREAD ResourceThreadId) +{ + UNIMPLEMENTED; +} + +VOID ExReleaseResourceForThreadLite(PERESOURCE Resource, + ERESOURCE_THREAD ResourceThreadId) +{ + UNIMPLEMENTED; +} + +BOOLEAN ExTryToAcquireResourceExclusiveLite(PERESOURCE Resource) +{ + LARGE_INTEGER timeout; + timeout.HighPart = 0; + timeout.LowPart = 0; + KeWaitForSingleObject(&Resource->ExclusiveWaiters,Executive,KernelMode, + FALSE,&timeout); +} + + diff --git a/reactos/ntoskrnl/ex/time.c b/reactos/ntoskrnl/ex/time.c new file mode 100644 index 00000000000..4c6b9194bcc --- /dev/null +++ b/reactos/ntoskrnl/ex/time.c @@ -0,0 +1,31 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/excutive/time.c + * PURPOSE: Time + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID ExLocalTimeToSystemTime(PLARGE_INTEGER LocalTime, + PLARGE_INTEGER SystemTime) +{ + UNIMPLEMENTED; +} + +VOID ExSystemTimeToLocalTime(PLARGE_INTEGER SystemTime, + PLARGE_INTEGER LocalTime) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/ex/work.c b/reactos/ntoskrnl/ex/work.c new file mode 100644 index 00000000000..83a7a7afc5f --- /dev/null +++ b/reactos/ntoskrnl/ex/work.c @@ -0,0 +1,157 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/kernel/work.c + * PURPOSE: Manage system work queues + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 29/06/98: Created + */ + +/* INCLUDES ******************************************************************/ + +#include +#include +#include + +#include + +/* TYPES *********************************************************************/ + +typedef struct +{ + /* + * PURPOSE: Head of the list of waiting work items + */ + LIST_ENTRY Head; + + /* + * PURPOSE: Sychronize access to the access + */ + KSPIN_LOCK Lock; + + /* + * PURPOSE: Worker threads with nothing to do wait on this event + */ + KEVENT Busy; + + /* + * PURPOSE: Thread associated with work queue + */ + HANDLE Thread; +} WORK_QUEUE, *PWORK_QUEUE; + +/* GLOBALS *******************************************************************/ + +/* + * PURPOSE: Queue of items waiting to be processed at normal priority + */ +WORK_QUEUE normal_work_queue; + +#define WAIT_INTERVAL (0) + +/* FUNCTIONS ****************************************************************/ + +static NTSTATUS ExWorkerThreadEntryPoint(PVOID context) +/* + * FUNCTION: Entry point for a worker thread + * ARGUMENTS: + * context = Parameters + * RETURNS: Status + * NOTE: To kill a worker thread you must queue an item whose callback + * calls PsTerminateSystemThread + */ +{ + PWORK_QUEUE param = (PWORK_QUEUE)context; + PWORK_QUEUE_ITEM item; + PLIST_ENTRY current; + + while (1) + { + current = ExInterlockedRemoveHeadList(¶m->Head,¶m->Lock); + if (current!=NULL) + { + item = CONTAINING_RECORD(current,WORK_QUEUE_ITEM,Entry); + item->Routine(item->Context); + } + else + { + KeClearEvent(¶m->Busy); + KeWaitForSingleObject((PVOID)¶m->Busy,Executive,KernelMode, + FALSE,WAIT_INTERVAL); + } + }; +} + +static VOID ExKillWorkerThreadCallback(PVOID Context) +{ + PsTerminateSystemThread(STATUS_SUCCESS); +} + +void ExKillWorkerThreads(void) +/* + * FUNCTION: Kill all running worker threads in preparation for a shutdown + */ +{ + WORK_QUEUE_ITEM item1; + + ExInitializeWorkItem(&item1,ExKillWorkerThreadCallback,NULL); + ExQueueWorkItem(&item1,DelayedWorkQueue); +} + +void ExInitializeWorkerThreads(void) +{ + InitializeListHead(&normal_work_queue.Head); + KeInitializeSpinLock(&normal_work_queue.Lock); + KeInitializeEvent(&normal_work_queue.Busy,NotificationEvent,FALSE); + PsCreateSystemThread(&normal_work_queue.Thread,THREAD_ALL_ACCESS, + NULL,NULL,NULL,ExWorkerThreadEntryPoint, + &normal_work_queue); +} + +VOID ExInitializeWorkItem(PWORK_QUEUE_ITEM Item, + PWORKER_THREAD_ROUTINE Routine, + PVOID Context) +/* + * FUNCTION: Initializes a work item to be processed by one of the system + * worker threads + * ARGUMENTS: + * Item = Pointer to the item to be initialized + * Routine = Routine to be called by the worker thread + * Context = Parameter to be passed to the callback + */ +{ + ASSERT_IRQL(DISPATCH_LEVEL); + + Item->Routine=Routine; + Item->Context=Context; + Item->Entry.Flink=NULL; + Item->Entry.Blink=NULL; +} + +VOID ExQueueWorkItem(PWORK_QUEUE_ITEM WorkItem, + WORK_QUEUE_TYPE QueueType) +/* + * FUNCTION: Inserts a work item in a queue for one of the system worker + * threads to process + * ARGUMENTS: + * WorkItem = Item to insert + * QueueType = Queue to insert it in + */ +{ + assert(WorkItem!=NULL); + ASSERT_IRQL(DISPATCH_LEVEL); + + /* + * Insert the item in the appropiate queue and wake on any thread + * waiting for something to do + */ + switch(QueueType) + { + case DelayedWorkQueue: + ExInterlockedInsertTailList(&normal_work_queue.Head,&(WorkItem->Entry), + &normal_work_queue.Lock); + KeSetEvent(&normal_work_queue.Busy,IO_NO_INCREMENT,FALSE); + break; + }; +} diff --git a/reactos/ntoskrnl/exports.lst b/reactos/ntoskrnl/exports.lst new file mode 100644 index 00000000000..c078ea0f774 --- /dev/null +++ b/reactos/ntoskrnl/exports.lst @@ -0,0 +1,375 @@ +# +# This lists all the symbols exported from the kernel to services +# +# NOTE: Give an export the name you normally call the function with +# This doesn't support overloading or class members +# Also the function should be defined with asmlinkage +# +# +# +DbgPrint +printk +ExAcquireFastMutex +ExAcquireFastMutexUnsafe +ExAcquireResourceExclusive +ExAcquireResourceExclusiveLite +ExAcquireResourceSharedLite +ExAcquireSharedStarveExclusive +ExAcquireSharedWaitForExclusive +ExAllocateFromNPagedLookasideList +ExAllocateFromPagedLookasideList +ExAllocateFromZone +ExAllocatePool +ExAllocatePoolWithQuota +ExAllocatePoolWithQuotaTag +ExAllocatePoolWithTag +ExConvertExclusiveToSharedLite +ExDeleteNPagedLookasideList +ExDeletePagedLookasideList +ExDeleteResource +ExDeleteResourceLite +ExExtendZone +ExFreePool +ExFreeToNPagedLookasideList +ExFreeToPagedLookasideList +ExFreeToZone +ExGetCurrentResourceThread +ExGetExclusiveWaiterCount +ExGetSharedWaiterCount +ExHookException +ExInitializeFastMutex +ExInitializeNPagedLookasideList +ExInitializePagedLookasideList +ExInitializeResource +ExInitializeResourceLite +ExInitializeSListHead +ExInitializeWorkItem +ExInitializeZone +ExInterlockedAddLargeInteger +ExInterlockedAddUlong +ExInterlockedAllocateFromZone +ExInterlockedDecrementLong +ExInterlockedExchangeUlong +ExInterlockedExtendZone +ExInterlockedFreeToZone +ExInterlockedIncrementLong +ExInterlockedInsertHeadList +ExInterlockedInsertTailList +ExInterlockedPopEntryList +ExInterlockedPopEntrySList +ExInterlockedPushEntryList +ExInterlockedPushEntrySList +ExInterlockedRemoveHeadList +ExIsFullZone +ExIsObjectInFirstZoneSegment +ExIsResourceAcquiredExclusiveLite +ExIsResourceAcquiredSharedLite +ExLocalTimeToSystemTime +ExQueryDepthSListHead +ExQueueWorkItem +ExRaiseStatus +ExReinitializeResourceLite +ExReleaseFastMutex +ExReleaseFastMutexUnsafe +ExReleaseResource +ExReleaseResourceForThread +ExReleaseResourceForThreadLite +ExSystemTimeToLocalTime +ExTryToAcquireFastMutex +ExTryToAcquireResourceExclusiveLite +InterlockedCompareExchange +InterlockedExchange +InterlockedExchangeAdd +InterlockedIncrement +HalAllocateCommonBuffer +HalAssignSlotResources +HalExamineMBR +HalFreeCommonBuffer +HalGetAdapter +HalGetBusData +HalGetBusDataByOffset +HalGetDmaAlignmentRequirement +HalGetInterruptVector +HalQuerySystemInformation +HalReadDmaCounter +HalSetBusData +HalSetBusDataByOffset +HalTranslateBusAddress +IoAcquireCancelSpinLock +IoAllocateAdapterChannel +IoAllocateController +IoAllocateErrorLogEntry +IoAllocateIrp +IoAllocateMdl +IoAssignArcName +IoAssignResources +IoAttachDevice +IoAttachDeviceByPointer +IoAttachDeviceToDeviceStack +IoBuildAsynchronousFsdRequest +IoBuildDeviceIoControlRequest +IoBuildPartialMdl +IoBuildSynchronousFsdRequest +IoCallDriver +IoCancelIrp +IoCheckShareAccess +IoCompleteRequest +IoConnectInterrupt +IoCreateController +IoCreateDevice +IoCreateNotificationEvent +IoCreateSymbolicLink +IoCreateSynchronizationEvent +IoCreateUnprotectedSymbolicLink +IoDeassignArcName +IoDeleteController +IoDeleteDevice +IoDeleteSymbolicLink +IoDetachDevice +IoDisconnectInterrupt +IoFlushAdapterBuffers +IoFreeAdapterChannel +IoFreeController +IoFreeIrp +IoFreeMapRegisters +IoFreeMdl +IoGetConfigurationInformation +IoGetCurrentIrpStackLocation +IoGetCurrentProcess +IoGetDeviceObjectPointer +IoGetDeviceToVerify +IoGetFileObjectGenericMapping +IoGetFunctionCodeFromCtlCode +IoGetInitialStack +IoGetNextIrpStackLocation +IoGetRelatedDeviceObject +IoInitializeDpcRequest +IoInitializeIrp +IoInitializeTimer +IoIsErrorUserInduced +IoIsTotalDeviceFailure +IoMakeAssociatedIrp +IoMapTransfer +IoMarkIrpPending +IoQueryDeviceDescription +IoRaiseHardError +IoRaiseInformationalHardError +IoReadPartitionTable +IoRegisterDriverReinitialization +IoRegisterShutdownNotification +IoReleaseCancelSpinLock +IoRemoveShareAccess +IoReportResourceUsage +IoRequestDpc +IoSetCancelRoutine +IoSetCompletionRoutine +IoSetHardErrorOrVerifyDevice +IoSetNextIrpStackLocation +IoSetPartitionInformation +IoSetShareAccess +IoSizeOfIrp +IoStartNextPacket +IoStartNextPacketByKey +IoStartPacket +IoStartTimer +IoStopTimer +IoUnregisterShutdownNotification +IoUpdateShareAccess +IoWriteErrorLogEntry +IoWritePartitionTable +KeAcquireSpinLock +KeAcquireSpinLockAtDpcLevel +KeBugCheck +KeBugCheckEx +KeCancelTimer +KeClearEvent +KeDelayExecutionThread +KeDeregisterBugCheckCallback +KeEnterCriticalRegion +KeFlushIoBuffers +KeGetCurrentIrql +KeGetCurrentProcessorNumber +KeGetDcacheFillSize +KeInitializeCallbackRecord +KeInitializeDeviceQueue +KeInitializeDpc +KeInitializeEvent +KeInitializeMutex +KeInitializeSemaphore +KeInitializeSpinLock +KeInitializeTimer +KeInitializeTimerEx +KeInsertByKeyDeviceQueue +KeInsertDeviceQueue +KeInsertQueueDpc +KeLeaveCriticalRegion +KeLowerIrql +KeQueryPerformanceCounter +KeQuerySystemTime +KeQueryTickCount +KeQueryTimeIncrement +KeRaiseIrql +KeReadStateEvent +KeReadStateMutex +KeReadStateSemaphore +KeReadStateTimer +KeRegisterBugCheckCallback +KeReleaseMutex +KeReleaseSemaphore +KeReleaseSpinLock +KeReleaseSpinLockFromDpcLevel +KeRemoveByKeyDeviceQueue +KeRemoveDeviceQueue +KeRemoveQueueDpc +KeResetEvent +KeSetBasePriorityThread +KeSetEvent +KeSetPriorityThread +KeSetTimer +KeSetTimerEx +KeStallExecutionProcessor +KeSynchronizeExecution +KeWaitForMultipleObjects +KeWaitForMutexObject +KeWaitForSingleObject +MmAllocateContiguousMemory +MmAllocateNonCachedMemory +MmBuildMdlForNonPagedPool +MmCreateMdl +MmFreeContiguousMemory +MmFreeNonCachedMemory +MmGetMdlByteCount +MmGetMdlByteOffset +MmGetMdlVirtualAddress +MmGetPhysicalAddress +MmGetSystemAddressForMdl +MmInitializeMdl +MmIsAddressValid +MmIsNonPagedSystemAddressValid +MmIsThisAnNtAsSystem +MmLockPagableCodeSection +MmLockPagableDataSection +MmLockPagableSectionByHandle +MmMapIoSpace +MmMapLockedPages +MmPageEntireDriver +MmResetDriverPaging +MmPrepareMdlForReuse +MmProbeAndLockPages +MmQuerySystemSize +MmSizeOfMdl +MmUnlockPages +MmUnlockPagableImageSection +MmUnmapIoSpace +MmUnmapLockedPages +ObDereferenceObject +ObReferenceObjectByHandle +ObReferenceObjectByPointer +PsCreateSystemThread +PsGetCurrentProcess +PsGetCurrentThread +PsTerminateSystemThread +InitializeListHead +InitializeObjectAttributes +InsertHeadList +InsertTailList +PopEntryList +PushEntryList +RemoveEntryList +RemoveHeadList +RemoveTailList +RtlAnsiStringToUnicodeSize +RtlAnsiStringToUnicodeString +RtlAppendUnicodeStringToString +RtlAppendUnicodeToString +RtlCharToInteger +RtlCheckRegistryKey +RtlCompareMemory +RtlCompareString +RtlCompareUnicodeString +RtlConvertLongToLargeInteger +RtlConvertUlongToLargeInteger +RtlCopyBytes +RtlCopyMemory +RtlCopyString +RtlCopyUnicodeString +RtlCreateRegistryKey +RtlCreateSecurityDescriptor +RtlDeleteRegistryValue +RtlEnlargedIntegerMultiply +RtlEnlargedUnsignedDivide +RtlEnlargedUnsignedMultiply +RtlEqualString +RtlEqualUnicodeString +RtlExtendedIntegerMultiply +RtlExtendedLargeIntegerDivide +RtlExtendedMagicDivide +RtlFillMemory +RtlFreeAnsiString +RtlFreeUnicodeString +RtlInitAnsiString +RtlInitString +RtlInitUnicodeString +RtlIntegerToUnicodeString +RtlLargeIntegerAdd +RtlLargeIntegerAnd +RtlLargeIntegerArithmeticShift +RtlLargeIntegerDivide +RtlLargeIntegerEqualTo +RtlLargeIntegerEqualToZero +RtlLargeIntegerGreaterThan +RtlLargeIntegerGreaterThanOrEqualTo +RtlLargeIntegerGreaterThanOrEqualToZero +RtlLargeIntegerGreaterThanZero +RtlLargeIntegerLessThan +RtlLargeIntegerLessThanOrEqualTo +RtlLargeIntegerLessThanZero +RtlLargeIntegerNegate +RtlLargeIntegerNotEqualTo +RtlLargeIntegerShiftLeft +RtlLargeIntegerShiftRight +RtlLargeIntegerSubtract +RtlLengthSecurityDescriptor +RtlMoveMemory +RtlQueryRegistryValues +RtlRetrieveUlong +RtlRetrieveUshort +RtlSetDaclSecurityDescriptor +RtlStoreUlong +RtlStoreUshort +RtlTimeFieldsToTime +RtlTimeToTimeFields +RtlUnicodeStringToAnsiString +RtlUnicodeStringToInteger +RtlUpcaseUnicodeString +RtlUpperString +RtlValidSecurityDescriptor +RtlWriteRegistryValue +RtlZeroMemory +SeAccessCheck +SeAssignSecurity +SeDeassignSecurity +SeSinglePrivilegeCheck +ZwClose +ZwCreateDirectoryObject +ZwCreateFile +ZwCreateKey +ZwDeleteKey +ZwEnumerateKey +ZwEnumerateValueKey +ZwFlushKey +ZwMakeTemporaryObject +ZwMapViewOfSection +ZwOpenFile +ZwOpenKey +ZwOpenSection +ZwQueryInformationFile +ZwQueryKey +ZwQueryValueKey +ZwReadFile +ZwSetInformationFile +ZwSetInformationThread +ZwSetValueKey +ZwUnmapViewOfSection +ZwWriteFile +sprintf diff --git a/reactos/ntoskrnl/hal/x86/bios32.c b/reactos/ntoskrnl/hal/x86/bios32.c new file mode 100644 index 00000000000..34e967ca2f6 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/bios32.c @@ -0,0 +1,140 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/eisa.c + * PURPOSE: Interfaces to the PCI bus + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 05/06/98: Created + */ + +/* + * NOTES: Sections copied from the Linux pci support + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include +#include +#include + +/* TYPES ******************************************************************/ + +typedef struct +{ + /* + * "_32_" if present + */ + unsigned int signature; + + /* + * Entry point (physical address) + */ + unsigned long int entry; + + /* + * Revision level + */ + unsigned char revision; + + /* + * Length in paragraphs + */ + unsigned char length; + + /* + * Checksum (so all bytes add up to zero) + */ + unsigned char checksum; + + unsigned char reserved[5]; +} bios32; + +BOOLEAN bios32_detected = FALSE; + +static struct +{ + unsigned long address; + unsigned short segment; +} bios32_indirect = {0,KERNEL_CS}; + +/* FUNCTIONS **************************************************************/ + +#define BIOS32_SIGNATURE (('_' << 0)+('3'<<8)+('2'<<16)+('_'<<24)) + +BOOL static checksum(bios32* service_entry) +/* + * FUNCTION: Checks the checksum of a bios32 service entry + * ARGUMENTS: + * service_entry = Pointer to the service entry + * RETURNS: True if the sum of the bytes in the entry was zero + * False otherwise + */ +{ + unsigned char* p = (unsigned char *)service_entry; + int i; + unsigned char sum=0; + + for (i=0; i<(service_entry->length*16); i++) + { + sum=sum+p[i]; + } +// printk("sum = %d\n",sum); + if (sum==0) + { + return(TRUE); + } + return(FALSE); +} + +BOOLEAN Hal_bios32_is_service_present(ULONG service) +{ + unsigned char return_code; + unsigned int address; + unsigned int length; + unsigned int entry; + + __asm__("lcall (%%edi)" + : "=a" (return_code), + "=b" (address), + "=c" (length), + "=d" (entry) + : "0" (service), + "1" (0), + "D" (&bios32_indirect)); + if (return_code==0) + { + return(address+entry); + } + return(0); +} + +VOID Hal_bios32_probe() +/* + * FUNCTION: Probes for an BIOS32 extension + * RETURNS: True if detected + */ +{ + int i; + + for (i=0xe0000;i<=0xffff0;i++) + { + bios32* service_entry = (bios32 *)physical_to_linear(i); + if ( service_entry->signature != BIOS32_SIGNATURE ) + { + continue; + } +// printk("Signature detected at %x\n",i); + if (!checksum(service_entry)) + { + continue; + } + printk("BIOS32 detected at %x\n",i); + bios32_indirect.address = service_entry->entry; + bios32_detected=TRUE; + } +} diff --git a/reactos/ntoskrnl/hal/x86/bus.c b/reactos/ntoskrnl/hal/x86/bus.c new file mode 100644 index 00000000000..73ecce9e507 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/bus.c @@ -0,0 +1,79 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS HalAssignSlotResources(PUNICODE_STRING RegistryPath, + PUNICODE_STRING DriverClassName, + PDRIVER_OBJECT DriverObject, + PDEVICE_OBJECT DeviceObject, + INTERFACE_TYPE BusType, + ULONG BusNumber, + ULONG SlotNumber, + PCM_RESOURCE_LIST* AllocatedResources) +{ + UNIMPLEMENTED; +} + +ULONG HalGetBusData(BUS_DATA_TYPE BusDataType, + ULONG BusNumber, + ULONG SlotNumber, + PVOID Buffer, + ULONG Length) +{ + UNIMPLEMENTED; +} + +ULONG HalGetBusDataByOffset(BUS_DATA_TYPE BusDataType, + ULONG BusNumber, + ULONG SlotNumber, + PVOID Buffer, + ULONG Offset, + ULONG Length) +{ + UNIMPLEMENTED; +} +ULONG HalSetBusData(BUS_DATA_TYPE BusDataType, + ULONG BusNumber, + ULONG SlotNumber, + PVOID Buffer, + ULONG Length) +{ + UNIMPLEMENTED; +} + +ULONG HalSetBusDataByOffset(BUS_DATA_TYPE BusDataType, + ULONG BusNumber, + ULONG SlotNumber, + PVOID Buffer, + ULONG Offset, + ULONG Length) +{ + UNIMPLEMENTED; +} + +BOOLEAN HalTranslateBusAddress(INTERFACE_TYPE InterfaceType, + ULONG BusNumber, + PHYSICAL_ADDRESS BusAddress, + PULONG AddressSpace, + PPHYSICAL_ADDRESS TranslatedAddress) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/hal/x86/dma.c b/reactos/ntoskrnl/hal/x86/dma.c new file mode 100644 index 00000000000..f87d5971e7b --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/dma.c @@ -0,0 +1,132 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/dma.c + * PURPOSE: DMA functions + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* TYPES *********************************************************************/ + +#define MAP_REGISTER_SIZE (PAGESIZE) +#define NR_MAP_REGISTERS (32) + +typedef struct +{ + PVOID VirtualAddress; + PVOID PhysicalAddress; +} MAP_REGISTER, *PMAP_REGISTER; +/* +typedef struct _ADAPTER_OBJECT +{ + DEVICE_DESCRIPTION desc; + KDEVICE_QUEUE wait_queue; +} ADAPTER_OBJECT, *PADAPTER_OBJECT +*/ +/* GLOBALS *******************************************************************/ + +static PMAP_REGISTER map_registers[]; + +/* FUNCTIONS *****************************************************************/ + +VOID HalInitializeAdapterSupport() +{ + /* ?? */ +} + +ULONG HalGetDmaAlignmentRequirement() +/* + * FUNCTION: Returns the size of the cache boundary + */ +{ + return(1); +} + +PVOID HalAllocateCommonBuffer(PADAPTER_OBJECT AdapterObject, + ULONG Length, + PPHYSICAL_ADDRESS LogicalAddress, + BOOLEAN CacheEnabled) +/* + * FUNCTION: Allocates memory that is visible to both the processor(s) and + * a dma device + * ARGUMENTS: + * AdapterObject = Adapter object representing the bus master or + * system dma controller + * Length = Number of bytes to allocate + * LogicalAddress = Logical address the driver can use to access the + * buffer + * CacheEnabled = Specifies if the memory can be cached + * RETURNS: The base virtual address of the memory allocated + * NULL on failure + */ +{/* + PVOID Buffer; + PHYSICAL_ADDRESS highest_address; + + highest_address.HighPart = 0; + if (AdapterObject->Desc.Dma32BitAddresses ) + { + highest_address.LowPart = 0xffffffff; + } + else + { + highest_address.LowPart = 0xfffff; + } + Buffer = MmAllocateContiguousMemory(Length,&highest_address); + LogicalAddress->HighPart = 0; + LogicalAddress->LowPart = MmGetPhysicalAddress(Buffer); + return(Buffer);*/ +} + +VOID HalFreeCommonBuffer(PADAPTER_OBJECT AdapterObject, + ULONG Length, + PHYSICAL_ADDRESS LogicalAddress, + PVOID VirtualAddress, + BOOLEAN CacheEnabled) +{ + MmFreeContiguousMemory(VirtualAddress); +} + +PADAPTER_OBJECT HalGetAdapter(PDEVICE_DESCRIPTION DeviceDescription, + PULONG NumberOfMapRegisters) +/* + * FUNCTION: Returns a pointer to an adapter object for the DMA device + * defined the device description structure + * ARGUMENTS: + * DeviceObject = Structure describing the attributes of the device + * NumberOfMapRegisters (OUT) = Returns the maximum number of map + * registers the device driver can + * allocate for DMA transfer operations + * RETURNS: The allocated adapter object on success + * NULL on failure + */ +{ +/* PADAPTER_OBJECT adapter; + + adapter = ExAllocatePool(NonPagedPool,sizeof(ADAPTER_OBJECT)); + RtlCopyMemory(&adapter->desc,DeviceDescription,sizeof(DEVICE_DESCRIPTION)); + */ +} + +ULONG HalReadDmaCounter(PADAPTER_OBJECT AdapterObject) +{ + UNIMPLEMENTED; +} + +ULONG KeGetDcacheFillSize() +/* + * FUNCTION: Returns the microprocessor's data cache-line boundary in bytes + */ +{ + return(1); +} diff --git a/reactos/ntoskrnl/hal/x86/exp.c b/reactos/ntoskrnl/hal/x86/exp.c new file mode 100644 index 00000000000..54b4f9ec8fe --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/exp.c @@ -0,0 +1,224 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/exp.c + * PURPOSE: Handling exceptions + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * ??/??/??: Created + */ + +/* INCLUDES *****************************************************************/ + +#include + +#include +#include +#include + +/* GLOBALS *****************************************************************/ + +extern descriptor idt[256]; +static exception_hook* exception_hooks[256]={NULL,}; + +#define _STR(x) #x +#define STR(x) _STR(x) + +/* FUNCTIONS ****************************************************************/ + +#define EXCEPTION_HANDLER_WITH_ERROR(x,y) \ + void exception_handler##y (void); \ + __asm__("\n\t_exception_handler"##x":\n\t" \ + "pushl %ds\n\t" \ + "pushl $"##x"\n\t" \ + "pusha\n\t" \ + "movw $"STR(KERNEL_DS)",%ax\n\t" \ + "movw %ax,%ds\n\t" \ + "call _exception_handler\n\t" \ + "popa\n\t" \ + "addl $8,%esp\n\t" \ + "iret\n\t") + +#define EXCEPTION_HANDLER_WITHOUT_ERROR(x,y) \ + asmlinkage void exception_handler##y (void); \ + __asm__("\n\t_exception_handler"##x":\n\t" \ + "pushl $0\n\t" \ + "pushl %ds\n\t" \ + "pushl $"##x"\n\t" \ + "pusha\n\t" \ + "movw $"STR(KERNEL_DS)",%ax\n\t" \ + "movw %ax,%ds\n\t" \ + "call _exception_handler\n\t" \ + "popa\n\t" \ + "addl $8,%esp\n\t" \ + "iret\n\t") + +asmlinkage void exception_handler_unknown(void); + __asm__("\n\t_exception_handler_unknown:\n\t" + "pushl $0\n\t" + "pushl %ds\n\t" + "pushl $0xff\n\t" + "pusha\n\t" + "movw $"STR(KERNEL_DS)",%ax\n\t" + "movw %ax,%ds\n\t" + "call _exception_handler\n\t" + "popa\n\t" + "addl $8,%esp\n\t" + "iret\n\t"); + + +EXCEPTION_HANDLER_WITHOUT_ERROR("0",0); +EXCEPTION_HANDLER_WITHOUT_ERROR("1",1); +EXCEPTION_HANDLER_WITHOUT_ERROR("2",2); +EXCEPTION_HANDLER_WITHOUT_ERROR("3",3); +EXCEPTION_HANDLER_WITHOUT_ERROR("4",4); +EXCEPTION_HANDLER_WITHOUT_ERROR("5",5); +EXCEPTION_HANDLER_WITHOUT_ERROR("6",6); +EXCEPTION_HANDLER_WITHOUT_ERROR("7",7); +EXCEPTION_HANDLER_WITH_ERROR("8",8); +EXCEPTION_HANDLER_WITHOUT_ERROR("9",9); +EXCEPTION_HANDLER_WITH_ERROR("10",10); +EXCEPTION_HANDLER_WITH_ERROR("11",11); +EXCEPTION_HANDLER_WITH_ERROR("12",12); +EXCEPTION_HANDLER_WITH_ERROR("13",13); + +/* + * The page fault handler is defined by the memory managment because it is + * special + */ +//EXCEPTION_HANDLER_WITH_ERROR("14",14); +asmlinkage void exception_handler14(void); + +EXCEPTION_HANDLER_WITH_ERROR("15",15); +EXCEPTION_HANDLER_WITHOUT_ERROR("16",16); + +extern unsigned int etext; + +asmlinkage void exception_handler(unsigned int edi, + unsigned int esi, unsigned int ebp, + unsigned int esp, unsigned int ebx, + unsigned int edx, unsigned int ecx, + unsigned int eax, + unsigned int type, + unsigned int ds, + unsigned int error_code, + unsigned int eip, + unsigned int cs, unsigned int eflags, + unsigned int esp0, unsigned int ss0) +/* + * FUNCTION: Called by the lowlevel execption handlers to print an amusing + * message and halt the computer + * ARGUMENTS: + * Complete CPU context + */ +{ + unsigned int cr2; + unsigned int i; + unsigned int* stack; + + /* + * Activate any hook for the exception + */ + if (exception_hooks[type]!=NULL) + { + exception_hooks[type](NULL,type); + } + + /* + * Print out the CPU registers + */ + printk("Exception: %d(%x)\n",type,error_code&0xffff); + printk("CS:EIP %x:%x\n",cs&0xffff,eip); + printk("EAX: %.8x EBX: %.8x ECX: %.8x\n",eax,ebx,ecx); + printk("EDX: %.8x EBP: %.8x ESI: %.8x\n",edx,ebp,esi); + printk("EDI: %.8x EFLAGS: %.8x ",edi,eflags); + if ((cs&0xffff)==KERNEL_CS) + { + printk("ESP %.8x\n",esp); + } + + __asm__("movl %%cr2,%0\n\t" + : "=d" (cr2)); + printk("cr2 %x\n",cr2); + + if ((cs&0xffff)==KERNEL_CS) + { + printk("ESP %x\n",esp); + stack=(unsigned int *)(esp+24); + +// #if 0 + printk("Stack:\n"); + for (i=0;i<16;i=i+4) + { + printk("%.8x %.8x %.8x %.8x\n",stack[i],stack[i+1],stack[i+2], + stack[i+3]); + } + printk("Frames:\n"); + for (i=0;i<32;i++) + { + if (stack[i] > KERNEL_BASE && + stack[i] < ((unsigned int)&etext) ) + { + printk("%.8x ",stack[i]); + } + } +// #endif + } + else + { + printk("SS:ESP %x:%x\n",ss0,esp0); + } + + for(;;); +} + +static void set_interrupt_gate(unsigned int sel, unsigned int func) +{ + idt[sel].a = (((int)func)&0xffff) + + (KERNEL_CS << 16); + idt[sel].b = 0x8f00 + (((int)func)&0xffff0000); +} + +asmlinkage unsigned int ExHookException(exception_hook fn, unsigned int exp) +/* + * FUNCTION: Hook an exception + */ +{ + if (exp>=256) + { + return(1); + } + exception_hooks[exp]=fn; + return(0); +} + +asmlinkage void InitalizeExceptions(void) +/* + * FUNCTION: Initalize CPU exception handling + */ +{ + int i; + + set_interrupt_gate(0,(int)exception_handler0); + set_interrupt_gate(1,(int)exception_handler1); + set_interrupt_gate(2,(int)exception_handler2); + set_interrupt_gate(3,(int)exception_handler3); + set_interrupt_gate(4,(int)exception_handler4); + set_interrupt_gate(5,(int)exception_handler5); + set_interrupt_gate(6,(int)exception_handler6); + set_interrupt_gate(7,(int)exception_handler7); + set_interrupt_gate(8,(int)exception_handler8); + set_interrupt_gate(9,(int)exception_handler9); + set_interrupt_gate(10,(int)exception_handler10); + set_interrupt_gate(11,(int)exception_handler11); + set_interrupt_gate(12,(int)exception_handler12); + set_interrupt_gate(13,(int)exception_handler13); + set_interrupt_gate(14,(int)exception_handler14); + set_interrupt_gate(15,(int)exception_handler15); + set_interrupt_gate(16,(int)exception_handler16); + + for (i=17;i<256;i++) + { + set_interrupt_gate(i,(int)exception_handler_unknown); + } +} diff --git a/reactos/ntoskrnl/hal/x86/halinit.c b/reactos/ntoskrnl/hal/x86/halinit.c new file mode 100644 index 00000000000..a578df6b728 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/halinit.c @@ -0,0 +1,43 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/x86/halinit.c + * PURPOSE: Initalize the uniprocessor, x86 hal + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 11/06/98: Created + */ + +/* INCLUDES *****************************************************************/ + +#include +#include + +/* FUNCTIONS ***************************************************************/ + +VOID HalInit(boot_param* bp) +{ + + InitalizeExceptions(); + InitalizeIRQ(); + + /* + * Probe for a BIOS32 extension + */ + Hal_bios32_probe(); + + /* + * Probe for buses attached to the computer + * NOTE: Order is important here because ISA is the default + */ + #if 0 + if (HalPciProbe()) + { + return; + } + HalIsaProbe(); + #endif +} + + + diff --git a/reactos/ntoskrnl/hal/x86/head.s b/reactos/ntoskrnl/hal/x86/head.s new file mode 100644 index 00000000000..b56d771532f --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/head.s @@ -0,0 +1,81 @@ +#define NR_TASKS 128 + +.globl _stext +.globl _idt +.globl _gdt +.globl _start +.globl _mainCRTStartup +.globl start + +_stext: +_mainCRTStartup: +_start: +start: + lidt _idt_descr + lgdt _gdt_descr + + movw $0x28,%ax + movw %ax,%ds + + popl %eax + popl %eax + movl $_init_stack_top,%esp + pushl %eax + pushl $0 + + jmp __main + +.data +_gdt: + .word 0 + .word 0 + .word 0 + .word 0 + + .word 0x0000 + .word 0x0000 + .word 0xfa00 + .word 0x00cc + + .word 0x0000 + .word 0x0000 + .word 0xf200 + .word 0x00cc + + .word 0xffff + .word 0x0000 + .word 0x9200 + .word 0x00cf + + .word 0xffff + .word 0x0000 + .word 0x9a00 + .word 0x00cf + + .word 0xffff + .word 0x0000 + .word 0x9200 + .word 0x00cf + + .fill 128,8,0 + +_idt_descr: + .word (256*8)-1 + .long _idt + +_gdt_descr: +/* .word ((6+128)*8)-1 */ + .word ((6+NR_TASKS)*8)-1 + .long _gdt + +_idt: + .fill 256,8,0 + +_init_stack: + .fill 4096,1,0 +_init_stack_top: + +#if 0 +_stext: +#endif + diff --git a/reactos/ntoskrnl/hal/x86/irq.c b/reactos/ntoskrnl/hal/x86/irq.c new file mode 100644 index 00000000000..232ad8f0d87 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/irq.c @@ -0,0 +1,369 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/x86/irq.c + * PURPOSE: IRQ handling + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 29/05/98: Created + */ + +/* + * NOTE: In general the PIC interrupt priority facilities are used to + * preserve the NT IRQL semantics, global interrupt disables are only used + * to keep the PIC in a consistent state + * + */ + +/* INCLUDES ****************************************************************/ + +#include + +#include +#include +#include +#include +#include + +#include +#include + +#define NDEBUG +#include + +/* GLOBALS *****************************************************************/ + +#define NR_IRQS (16) +#define IRQ_BASE (0x20) + +asmlinkage void irq_handler_0(void); +asmlinkage void irq_handler_1(void); +asmlinkage void irq_handler_2(void); +asmlinkage void irq_handler_3(void); +asmlinkage void irq_handler_4(void); +asmlinkage void irq_handler_5(void); +asmlinkage void irq_handler_6(void); +asmlinkage void irq_handler_7(void); +asmlinkage void irq_handler_8(void); +asmlinkage void irq_handler_9(void); +asmlinkage void irq_handler_10(void); +asmlinkage void irq_handler_11(void); +asmlinkage void irq_handler_12(void); +asmlinkage void irq_handler_13(void); +asmlinkage void irq_handler_14(void); +asmlinkage void irq_handler_15(void); + +static unsigned int irq_handler[NR_IRQS]= + { + (int)&irq_handler_0, + (int)&irq_handler_1, + (int)&irq_handler_2, + (int)&irq_handler_3, + (int)&irq_handler_4, + (int)&irq_handler_5, + (int)&irq_handler_6, + (int)&irq_handler_7, + (int)&irq_handler_8, + (int)&irq_handler_9, + (int)&irq_handler_10, + (int)&irq_handler_11, + (int)&irq_handler_12, + (int)&irq_handler_13, + (int)&irq_handler_14, + (int)&irq_handler_15, + }; + +/* + * PURPOSE: Object describing each isr + * NOTE: The data in this table is only modified at passsive level but can + * be accessed at any irq level. + */ +static LIST_ENTRY isr_table[NR_IRQS]={{NULL,NULL},}; +static PKSPIN_LOCK isr_lock[NR_IRQS]; +static KSPIN_LOCK isr_table_lock; + +/* FUNCTIONS ****************************************************************/ + + +#define PRESENT (0x8000) +#define I486_INTERRUPT_GATE (0xe00) + +asmlinkage void KiInterruptDispatch(unsigned int irq) +/* + * FUNCTION: Calls the irq specific handler for an irq + * ARGUMENTS: + * irq = IRQ that has interrupted + */ +{ + KIRQL old_level; + PKINTERRUPT isr; + PLIST_ENTRY current; + + /* + * Notify the rest of the kernel of the raised irq level + */ + old_level = KeGetCurrentIrql(); + DPRINT("old_level %d\n",old_level); + KeSetCurrentIrql(HIGH_LEVEL - irq); + + /* + * Enable interrupts + * NOTE: Only higher priority interrupts will get through + */ + __asm__("sti\n\t"); + + if (irq==0) + { + KeTimerInterrupt(); + } + else + { + DPRINT("KiInterruptDispatch(irq %x)\n",irq); + /* + * Iterate the list until one of the isr tells us its device interrupted + */ + current = isr_table[irq].Flink; + isr = CONTAINING_RECORD(current,KINTERRUPT,Entry); + DPRINT("current %x isr %x\n",current,isr); + while (current!=NULL && !isr->ServiceRoutine(isr,isr->ServiceContext)) + { + current = current->Flink; + isr = CONTAINING_RECORD(current,KINTERRUPT,Entry); + DPRINT("current %x isr %x\n",current,isr); + } + } + + /* + * Disable interrupts + */ + __asm__("cli\n\t"); + + /* + * Send EOI to the PIC + */ + outb(0x20,0x20); + if (irq>=8) + { + outb(0xa0,0x20); + } + + /* + * Unmask the related irq + */ + if (irq<8) + { + outb(0x21,inb(0x21)&(~(1<= NR_IRQS) + { + return(STATUS_INVALID_PARAMETER); + } + if (FloatingSave == TRUE) + { + return(STATUS_INVALID_PARAMETER); + } + + /* + * Acquire the table spinlock + */ + KeAcquireSpinLock(&isr_table_lock,&oldlvl); + + /* + * Check if the vector is already in use that we can share it + */ + ListHead = CONTAINING_RECORD(isr_table[Vector].Flink,KINTERRUPT,Entry); + if (!IsListEmpty(&isr_table[Vector]) && + (ShareVector == FALSE || ListHead->Shareable==FALSE)) + { + KeReleaseSpinLock(&isr_table_lock,oldlvl); + return(STATUS_INVALID_PARAMETER); + } + else + { + isr_lock[Vector]=ExAllocatePool(NonPagedPool,sizeof(KSPIN_LOCK)); + KeInitializeSpinLock(isr_lock[Vector]); + isr_lock[Vector]->irql = SynchronizeIrql; + } + + /* + * Initialize interrupt object + */ + (*InterruptObject)=ExAllocatePool(NonPagedPool,sizeof(KINTERRUPT)); + if ((*InterruptObject)==NULL) + { + return(STATUS_INSUFFICIENT_RESOURCES); + } + (*InterruptObject)->ServiceContext = ServiceContext; + (*InterruptObject)->ServiceRoutine = ServiceRoutine; + (*InterruptObject)->Vector = Vector; + (*InterruptObject)->ProcessorEnableMask = ProcessorEnableMask; + (*InterruptObject)->SynchLevel = SynchronizeIrql; + (*InterruptObject)->Shareable = ShareVector; + (*InterruptObject)->FloatingSave = FALSE; + (*InterruptObject)->IrqLock = isr_lock[Vector]; + + KeRaiseIrql((*InterruptObject)->SynchLevel,&synch_oldlvl); + KeAcquireSpinLockAtDpcLevel((*InterruptObject)->IrqLock); + DPRINT("%x %x\n",isr_table[Vector].Flink,isr_table[Vector].Blink); + InsertTailList(&isr_table[Vector],&((*InterruptObject)->Entry)); + DPRINT("%x %x\n",(*InterruptObject)->Entry.Flink, + (*InterruptObject)->Entry.Blink); + KeReleaseSpinLockFromDpcLevel((*InterruptObject)->IrqLock); + KeLowerIrql(synch_oldlvl); + + /* + * Release the table spinlock + */ + KeReleaseSpinLock(&isr_table_lock,oldlvl); + + return(STATUS_SUCCESS); +} + + +VOID IoDisconnectInterrupt(PKINTERRUPT InterruptObject) +/* + * FUNCTION: Releases a drivers isr + * ARGUMENTS: + * InterruptObject = isr to release + */ +{ + KIRQL oldlvl; + + KeRaiseIrql(InterruptObject->SynchLevel,&oldlvl); + KeAcquireSpinLockAtDpcLevel(InterruptObject->IrqLock); + RemoveEntryFromList(&isr_table[InterruptObject->Vector], + &InterruptObject->Entry); + KeReleaseSpinLockFromDpcLevel(InterruptObject->IrqLock); + KeLowerIrql(oldlvl); +} + +ULONG HalGetInterruptVector(INTERFACE_TYPE InterfaceType, + ULONG BusNumber, + ULONG BusInterruptLevel, + ULONG BusInterruptVector, + PKIRQL Irql, + PKAFFINITY Affinity) +/* + * FUNCTION: Returns a mapped system interrupt vector for passing to + * IoConnectInterrupt + * ARGUMENTS: + * InterfaceType = Type bus the device is on + * BusNumber = Zero based number of the bus + * BusInterruptLevel = Bus specific interrupt level + * BusInterruptVector = Bus specific interrupt vector + * Irql (IN/OUT) = On entry the bus relative IRQL + * On exit the DIRQL + * Affinity (OUT) = Caller supplied storage for the interrupt + * affinity mask + * RETURNS: The mapped vector + */ +{ + ULONG ret; + +// ASSERT_IRQL(PASSIVE_LEVEL); + + switch (InterfaceType) + { + case Internal: + *Irql = HIGH_LEVEL - BusInterruptVector; + ret = BusInterruptVector; + break; + + default: + ret = -1; + printk("(%s:%d) Don't know that bus type\n",__FILE__,__LINE__); + break; + } + return(ret); +} + + diff --git a/reactos/ntoskrnl/hal/x86/irqhand.asm b/reactos/ntoskrnl/hal/x86/irqhand.asm new file mode 100644 index 00000000000..aa70708e3a2 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/irqhand.asm @@ -0,0 +1,106 @@ +; +; This module has code to handle IRQs +; + +%include "internal/hal/segment.inc" + +bits 32 +section .text +extern _KiInterruptDispatch + +%macro IRQ_HANDLER_FIRST 1 +global _irq_handler_%1 +_irq_handler_%1: + + ; + ; Save registers + ; + pusha + push ds + + ; + ; Load DS + ; + mov ax,KERNEL_DS + mov ds,ax + + ; + ; Mask the corresponding vector at the PIC + ; NOTE: Since lower priority interrupts are masked until an EOI + ; is sent to the PIC this preserves the IRQL semantics. + ; + in al,0x21 + or al,1<<%1 + out 0x21,al + + ; + ; Call the irq dispatcher (passing the IRQ number as an argument) + ; + push dword %1 + call _KiInterruptDispatch + + ; + ; Restore stack, registers and return to interrupted routine + ; + pop eax + pop ds + popa + iret +%endmacro + +%macro IRQ_HANDLER_SECOND 1 +global _irq_handler_%1 +_irq_handler_%1: + ; + ; Save registers + ; + pusha + push ds + + ; + ; Load DS + ; + mov ax,KERNEL_DS + mov ds,ax + + ; + ; Mask the related vector at the PIC + ; + in al,0xa1 + or al,1<<(%1-8) + out 0xa1,al + + ; + ; Call the irq dispatcher + ; + push dword %1 + call _KiInterruptDispatch + + ; + ; Restore stack, registers and return to the interrupted routine + ; + pop eax + pop ds + popa + iret +%endmacro + + +IRQ_HANDLER_FIRST 0 +IRQ_HANDLER_FIRST 1 +IRQ_HANDLER_FIRST 2 +IRQ_HANDLER_FIRST 3 +IRQ_HANDLER_FIRST 4 +IRQ_HANDLER_FIRST 5 +IRQ_HANDLER_FIRST 6 +IRQ_HANDLER_FIRST 7 +IRQ_HANDLER_SECOND 8 +IRQ_HANDLER_SECOND 9 +IRQ_HANDLER_SECOND 10 +IRQ_HANDLER_SECOND 11 +IRQ_HANDLER_SECOND 12 +IRQ_HANDLER_SECOND 13 +IRQ_HANDLER_SECOND 14 +IRQ_HANDLER_SECOND 15 + + diff --git a/reactos/ntoskrnl/hal/x86/irql.c b/reactos/ntoskrnl/hal/x86/irql.c new file mode 100644 index 00000000000..878d3f5fc52 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/irql.c @@ -0,0 +1,139 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/irql.c + * PURPOSE: Implements IRQLs + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ******************************************************************/ + +/* + * PURPOSE: Current irq level + */ +static KIRQL CurrentIrql = HIGH_LEVEL; + +/* FUNCTIONS ****************************************************************/ + +static unsigned int pic_get_current_mask(void) +{ + unsigned int mask; + + mask = inb_p(0x21); + mask = mask | (inb_p(0xa1)<<8); +} + +static unsigned int pic_set_current_mask(unsigned int mask) +{ + outb_p(0x21,mask & 0xff); + outb_p(0xa1,(mask >> 8) & 0xff); +} + +static void switch_irql(void) +/* + * FUNCTION: Switches to the current irql + * NOTE: Must be called with interrupt disabled + */ +{ + unsigned int i; + + if (CurrentIrql == HIGH_LEVEL) + { + pic_set_current_mask(0xffff); + return; + } + if (CurrentIrql > DISPATCH_LEVEL) + { + unsigned int current_mask = 0; + + for (i=(CurrentIrql-DISPATCH_LEVEL);i>DISPATCH_LEVEL;i--) + { + set_bit(NR_DEVICE_SPECIFIC_LEVELS - i,¤t_mask); + } + + pic_set_current_mask(current_mask); + __asm__("sti\n\t"); + return; + } + + if (CurrentIrql <= DISPATCH_LEVEL) + { + pic_set_current_mask(0); + __asm__("sti\n\t"); + return; + } +} + +VOID KeSetCurrentIrql(KIRQL newlvl) +/* + * PURPOSE: Sets the current irq level without taking any action + */ +{ + DPRINT("KeSetCurrentIrql(newlvl %x)\n",newlvl); + CurrentIrql = newlvl; +} + +KIRQL KeGetCurrentIrql() +/* + * PURPOSE: Returns the current irq level + * RETURNS: The current irq level + */ +{ + return(CurrentIrql); +} + +VOID KeLowerIrql(KIRQL NewIrql) +/* + * PURPOSE: Restores the irq level on the current processor + * ARGUMENTS: + * NewIrql = Irql to lower to + */ +{ + __asm__("cli\n\t"); + + DPRINT("NewIrql %x CurrentIrql %x\n",NewIrql,CurrentIrql); + assert(NewIrql <= CurrentIrql); + CurrentIrql = NewIrql; + switch_irql(); +} + +VOID KeRaiseIrql(KIRQL NewIrql, PKIRQL OldIrql) +/* + * FUNCTION: Raises the hardware priority (irql) + * ARGUMENTS: + * NewIrql = Irql to raise to + * OldIrql (OUT) = Caller supplied storage for the previous irql + */ +{ + /* + * sanity check + */ +// printk("CurrentIrql %x NewIrql %x OldIrql %x\n",CurrentIrql,NewIrql, +// OldIrql); + if (NewIrql < CurrentIrql) + { + printk("%s:%d\n",__FILE__,__LINE__); + for(;;); + } + + __asm__("cli\n\t"); + *OldIrql = CurrentIrql; + CurrentIrql = NewIrql; +// *OldIrql = InterlockedExchange(&CurrentIrql,NewIrql); + DPRINT("NewIrql %x OldIrql %x CurrentIrql %x\n",NewIrql,*OldIrql, + CurrentIrql); + switch_irql(); +} + + + diff --git a/reactos/ntoskrnl/hal/x86/irql.s b/reactos/ntoskrnl/hal/x86/irql.s new file mode 100644 index 00000000000..f2a09e38584 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/irql.s @@ -0,0 +1,205 @@ + .file "irql.c" +gcc2_compiled.: +___gnu_compiled_c: +.globl _CurrentIrql +.data +_CurrentIrql: + .byte 19 +.text + .p2align 2 +_pic_get_current_mask: + pushl %ebp + movl %esp,%ebp +/APP + inb $33,%al + outb %al,$0x80 + inb $161,%al + outb %al,$0x80 +/NO_APP + leave + ret + .p2align 2 +_pic_set_current_mask: + pushl %ebp + movl %esp,%ebp + movl 8(%ebp),%eax +/APP + outb %al,$33 + outb %al,$0x80 +/NO_APP + shrl $8,%eax +/APP + outb %al,$161 + outb %al,$0x80 +/NO_APP + leave + ret + .p2align 2 +_switch_irql: + pushl %ebp + movl %esp,%ebp + subl $4,%esp + pushl %ebx + movb _CurrentIrql,%al + cmpb $19,%al + jne L62 + pushl $65535 + call _pic_set_current_mask + jmp L61 + .align 2,0x90 +L62: + cmpb $2,%al + jbe L71 + movl $0,-4(%ebp) + movzbl _CurrentIrql,%eax + leal -2(%eax),%edx + cmpl $2,%edx + jbe L65 + movl $16,%ebx + leal -4(%ebp),%ecx + .align 2,0x90 +L67: + movl %ebx,%eax + subl %edx,%eax +/APP + btsl %eax,(%ecx) + sbbl %eax,%eax +/NO_APP + decl %edx + cmpl $2,%edx + ja L67 +L65: + pushl -4(%ebp) + call _pic_set_current_mask +/APP + sti + +/NO_APP + jmp L61 + .align 2,0x90 +L71: + pushl $0 + call _pic_set_current_mask +/APP + sti + +/NO_APP +L61: + movl -8(%ebp),%ebx + leave + ret + .p2align 2 +.globl _KeSetCurrentIrql +_KeSetCurrentIrql: + pushl %ebp + movl %esp,%ebp + movl 8(%ebp),%eax + movb %al,_CurrentIrql + leave + ret + .p2align 2 +.globl _KeGetCurrentIrql +_KeGetCurrentIrql: + pushl %ebp + movl %esp,%ebp + movzbl _CurrentIrql,%eax + leave + ret +LC0: + .ascii "irql.c\0" +LC1: + .ascii "(%s:%d) \0" +LC2: + .ascii "NewIrql %x CurrentIrql %x\12\0" +LC3: + .ascii "Assertion NewIrql <= CurrentIrql failed at %s:%d\12\0" + .p2align 2 +.globl _KeLowerIrql +_KeLowerIrql: + pushl %ebp + movl %esp,%ebp + pushl %ebx + movb 8(%ebp),%bl +/APP + cli + +/NO_APP + pushl $103 + pushl $LC0 + pushl $LC1 + call _printk + movzbl _CurrentIrql,%eax + pushl %eax + movzbl %bl,%eax + pushl %eax + pushl $LC2 + call _printk + addl $24,%esp + cmpb %bl,_CurrentIrql + jae L79 + pushl $104 + pushl $LC0 + pushl $LC3 + call _printk + .align 2,0x90 +L82: + jmp L82 + .align 2,0x90 +L79: + movb %bl,_CurrentIrql + call _switch_irql + movl -4(%ebp),%ebx + leave + ret +LC4: + .ascii "%s:%d\12\0" +LC5: + .ascii "NewIrql %x OldIrql %x CurrentIrql %x\12\0" + .p2align 2 +.globl _KeRaiseIrql +_KeRaiseIrql: + pushl %ebp + movl %esp,%ebp + pushl %esi + pushl %ebx + movl 12(%ebp),%esi + movb 8(%ebp),%al + cmpb %al,_CurrentIrql + jbe L84 + pushl $122 + pushl $LC0 + pushl $LC4 + call _printk + .align 2,0x90 +L87: + jmp L87 + .align 2,0x90 +L84: +/APP + cli + +/NO_APP + movzbl %al,%ebx + pushl %ebx + pushl $_CurrentIrql + call _InterlockedExchange + movb %al,(%esi) + pushl $129 + pushl $LC0 + pushl $LC1 + call _printk + movzbl _CurrentIrql,%eax + pushl %eax + movzbl (%esi),%eax + pushl %eax + pushl %ebx + pushl $LC5 + call _printk + addl $28,%esp + call _switch_irql + leal -8(%ebp),%esp + popl %ebx + popl %esi + leave + ret +.comm ___ProcessHeap,4 diff --git a/reactos/ntoskrnl/hal/x86/isa.c b/reactos/ntoskrnl/hal/x86/isa.c new file mode 100644 index 00000000000..bba10b97ea6 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/isa.c @@ -0,0 +1,36 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/eisa.c + * PURPOSE: Interfaces to the ISA bus + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 05/06/98: Created + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include +#include + +/* FUNCTIONS *****************************************************************/ + +BOOL HalIsaProbe() +/* + * FUNCTION: Probes for an ISA bus + * RETURNS: True if detected + * NOTE: Since ISA is the default we are called last and always return + * true + */ +{ + printk("Assuming ISA bus\n"); + + /* + * Probe for plug and play support + */ + +} diff --git a/reactos/ntoskrnl/hal/x86/mbr.c b/reactos/ntoskrnl/hal/x86/mbr.c new file mode 100644 index 00000000000..991b3ac4382 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/mbr.c @@ -0,0 +1,27 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/mbr.c + * PURPOSE: Functions for reading the master boot record (MBR) + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID HalExamineMBR(PDEVICE_OBJECT DeviceObject, + ULONG SectorSize, + ULONG MBRTypeIdentifier, + PVOID Buffer) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/hal/x86/mp.c b/reactos/ntoskrnl/hal/x86/mp.c new file mode 100644 index 00000000000..1633dcc5fe6 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/mp.c @@ -0,0 +1,27 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/mp.c + * PURPOSE: Multiprocessor stubs + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +ULONG KeGetCurrentProcessorNumber(VOID) +/* + * FUNCTION: Returns the system assigned number of the current processor + */ +{ + return(0); +} diff --git a/reactos/ntoskrnl/hal/x86/page.c b/reactos/ntoskrnl/hal/x86/page.c new file mode 100644 index 00000000000..e74f0465e13 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/page.c @@ -0,0 +1,205 @@ +/* + * COPYRIGHT: See COPYING in the top directory + * PROJECT: ReactOS kernel v0.0.2 + * FILE: hal/page.cc + * PURPOSE: low level memory managment manipulation + * PROGRAMER: David Welch + * UPDATE HISTORY: + * 9/3/98: Created + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS *****************************************************************/ + +#define PA_BIT_PRESENT (0) +#define PA_BIT_READWRITE (1) +#define PA_BIT_USER (2) + +#define PA_PRESENT (1<cr3); +#else + unsigned int* page_dir = get_page_directory(); +#endif + unsigned int* page_tlb = NULL; + + /* + * Check the page directory exists + */ + if (!(page_dir[VADDR_TO_PD_OFFSET(vaddr)]&PA_PRESENT)) + { + return(FALSE); + } + + page_tlb = (unsigned int *)physical_to_linear( + PAGE_MASK(page_dir[VADDR_TO_PD_OFFSET(vaddr)])); + + if (!(page_tlb[VADDR_TO_PT_OFFSET(vaddr)/4]&PA_PRESENT)) + { + return(FALSE); + } + + return(TRUE); +} + +unsigned int* get_page_entry(unsigned int vaddr) +/* + * FUNCTION: Returns a pointer to a page entry + * NOTE: This function will create a page table if none exists so just to + * check if mem exists use the is_page_present function + */ +{ + unsigned int page_table; + unsigned int* page_tlb; + +#if 0 + unsigned int* page_dir = physical_to_linear(current_task->cr3); +#else + unsigned int* page_dir = get_page_directory(); +#endif + + DPRINT("vaddr %x ",vaddr); + page_tlb = (unsigned int *)physical_to_linear( + PAGE_MASK(page_dir[VADDR_TO_PD_OFFSET(vaddr)])); + DPRINT("page_tlb %x\n",page_tlb); + + if (PAGE_MASK(page_dir[VADDR_TO_PD_OFFSET(vaddr)])==0) + { + DPRINT("Creating new page directory\n",0); + page_table = get_free_page(); // Returns a physical address + page_tlb=(unsigned int *)physical_to_linear(page_table); + memset(page_tlb,0,PAGESIZE); + page_dir[VADDR_TO_PD_OFFSET(vaddr)]=page_table+0x7; + + } + return(&page_tlb[VADDR_TO_PT_OFFSET(vaddr)/4]); +} + + diff --git a/reactos/ntoskrnl/hal/x86/pci.c b/reactos/ntoskrnl/hal/x86/pci.c new file mode 100644 index 00000000000..d1692dd34be --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/pci.c @@ -0,0 +1,40 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/hal/eisa.c + * PURPOSE: Interfaces to the PCI bus + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 05/06/98: Created + */ + +/* + * NOTES: Sections copied from the Linux pci support + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include +#include + +/* FUNCTIONS **************************************************************/ + +#define PCI_SERVICE (('$' << 0) + ('P' << 8) + ('C' << 16) + ('I'<<24)) + +BOOL HalPciProbe() +/* + * FUNCTION: Probes for an PCI bus + * RETURNS: True if detected + */ +{ + if (Hal_bios32_is_service_present(PCI_SERVICE)) + { + printk("Detected PCI service\n"); + return(TRUE); + } + return(FALSE); +} diff --git a/reactos/ntoskrnl/hal/x86/printk.c b/reactos/ntoskrnl/hal/x86/printk.c new file mode 100644 index 00000000000..6815f0f0362 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/printk.c @@ -0,0 +1,247 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/printk.c + * PURPOSE: Writing to the console + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * ??/??/??: Created + * 05/06/98: Implemented BSOD + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include +#include + +#include + +/* GLOBALS ******************************************************************/ + +/* + * PURPOSE: Current cursor position + */ +static unsigned int cursorx=0, cursory=0; + +static unsigned int lines_seen = 0; + +#define NR_ROWS 25 +#define NR_COLUMNS 80 +#define VIDMEM_BASE 0xb8000 + +/* + * PURPOSE: Points to the base of text mode video memory + */ +static char* vidmem = (char *)(VIDMEM_BASE + IDMAP_BASE); + +#define CRTC_COMMAND 0x3d4 +#define CRTC_DATA 0x3d5 +#define CRTC_CURLO 0x0f +#define CRTC_CURHI 0x0e + +/* + * PURPOSE: This flag is set to true if the system is in HAL managed + * console mode. This is initially true then once the graphics drivers + * initialize, it is turned off, HAL console mode is reentered if a fatal + * error occurs or on system shutdown + */ +static unsigned int in_hal_console = 1; + +/* + * PURPOSE: Defines the hal console video mode + */ +static unsigned char mode03[] = {0x67,0x00,0x03,0x00,0x03,0x00,0x02, + 0x5f,0x4f,0x50,0x82,0x55,0x81,0xbf, + 0x1f,0x00,0x4f,0x0e,0x0f,0x00,0x00, + 0x00,0x00,0x9c,0x0e,0x8f,0x28,0x01, + 0x96,0xb9,0xa3,0xff,0x00,0x00,0x00, + 0x00,0x00,0x10,0x0e,0x00,0xff,0x00, + 0x00,0x01,0x02,0x03,0x04,0x05,0x06, + 0x07,0x10,0x11,0x12,0x13,0x14,0x15, + 0x16,0x17,0x0c,0x00,0x0f,0x08,0x00}; + +/* FUNCTIONS ***************************************************************/ + +void HalSwitchToBlueScreen(void) +/* + * FUNCTION: Switches the monitor to text mode and writes a blue background + * NOTE: This function is entirely self contained and can be used from any + * graphics mode. + */ +{ + /* + * Sanity check + */ + if (in_hal_console) + { + return; + } + + /* + * Reset the cursor position + */ + cursorx=0; + cursory=0; + + /* + * This code section is taken from the sample routines by + * Jeff Morgan (kinfira@hotmail.com) + */ + +} + +void HalDisplayString(char* string) +/* + * FUNCTION: Switches the screen to HAL console mode (BSOD) if not there + * already and displays a string + * ARGUMENT: + * string = ASCII string to display + * NOTE: Use with care because there is no support for returning from BSOD + * mode + */ +{ + if (!in_hal_console) + { + HalSwitchToBlueScreen(); + } + printk("%s",string); +} + +static void putchar(char c) +/* + * FUNCTION: Writes a character to the console and updates the cursor position + * ARGUMENTS: + * c = the character to write + * NOTE: This function handles newlines as well + */ +{ + char* address; + int offset; + int i; + + switch(c) + { + case '\n': + cursory++; + cursorx=0; + lines_seen++; + break; + + default: + vidmem[(cursorx*2) + (cursory*80*2)]=c; + vidmem[(cursorx*2) + (cursory*80*2)+1]=0x7; + cursorx++; + if (cursorx>=NR_COLUMNS) + { + cursory++; + lines_seen++; + cursorx=0; + } + } + + #if 0 + if (lines_seen == 24) + { + char str[] = "--- press escape to continue"; + + lines_seen = 0; + for (i=0;str[i]!=0;i++) + { + vidmem[NR_COLUMNS*(NR_ROWS-1)*2+i*2]=str[i]; + vidmem[NR_COLUMNS*(NR_ROWS-1)*2+i*2+1]=0x7; + } + + while (inb_p(0x60)!=0x81); + memset(&vidmem[NR_COLUMNS*(NR_ROWS-1)*2],0,NR_COLUMNS*2); + } + #endif + + if (cursory>=NR_ROWS) + { + memcpy(vidmem,&vidmem[NR_COLUMNS*2], + NR_COLUMNS*(NR_ROWS-1)*2); + memset(&vidmem[NR_COLUMNS*(NR_ROWS-1)*2],0,NR_COLUMNS*2); + cursory=24; + } + + /* + * Set the cursor position + */ + + offset=cursory*NR_COLUMNS; + offset=offset+cursorx; + + outb_p(CRTC_COMMAND,CRTC_CURLO); + outb_p(CRTC_DATA,offset); + outb_p(CRTC_COMMAND,CRTC_CURHI); + offset>>=8; + outb_p(CRTC_DATA,offset); + +} + +asmlinkage void printk(const char* fmt, ...) +/* + * FUNCTION: Print a formatted string to the hal console + * ARGUMENTS: As for printf + * NOTE: So it can used from irq handlers this function disables interrupts + * during its execution, they are restored to the previous state on return + */ +{ + char buffer[256]; + char* str=buffer; + va_list ap; + unsigned int eflags; + + /* + * Because this is used by alomost every subsystem including irqs it + * must be atomic. The following code sequence disables interrupts after + * saving the previous state of the interrupt flag + */ + __asm__("pushf\n\tpop %0\n\tcli\n\t" + : "=m" (eflags) + : /* */); + + /* + * Process the format string into a fixed length buffer using the + * standard C RTL function + */ + va_start(ap,fmt); + vsprintf(buffer,fmt,ap); + va_end(ap); + + while ((*str)!=0) + { + putchar(*str); + str++; + } + + /* + * Restore the interrupt flag + */ + __asm__("push %0\n\tpopf\n\t" + : + : "m" (eflags)); +} + +int bad_user_access_length(void) +{ + printk("Bad user access length\n"); +} + +ULONG DbgPrint(PCH Format, ...) +{ + UNIMPLEMENTED; +} + +void InitConsole(boot_param* bp) +/* + * FUNCTION: Initalize the console + * ARGUMENTS: + * bp = Parameters setup by the boot loader + */ +{ + cursorx=bp->cursorx; + cursory=bp->cursory; +} diff --git a/reactos/ntoskrnl/hal/x86/sources b/reactos/ntoskrnl/hal/x86/sources new file mode 100644 index 00000000000..a1a3bd0cafb --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/sources @@ -0,0 +1,5 @@ +HAL_OBJECTS = hal/x86/head.o hal/x86/irq.o hal/x86/exp.o hal/x86/isa.o \ +hal/x86/pci.o hal/x86/irqhand.o hal/x86/page.o hal/x86/halinit.o \ +hal/x86/irql.o hal/x86/bios32.o hal/x86/thread.o hal/x86/spinlock.o \ +hal/x86/printk.o hal/x86/mp.o hal/x86/dma.o hal/x86/bus.o hal/x86/mbr.o \ +hal/x86/sysinfo.o diff --git a/reactos/ntoskrnl/hal/x86/spinlock.c b/reactos/ntoskrnl/hal/x86/spinlock.c new file mode 100644 index 00000000000..efc26eaee1f --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/spinlock.c @@ -0,0 +1,104 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/spinlock.c + * PURPOSE: Implements spinlocks + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 3/6/98: Created + */ + +/* + * NOTE: On a uniprocessor machine spinlocks are implemented by raising + * the irq level + */ + +/* INCLUDES ****************************************************************/ + +#include +#include + +#include + +/* FUNCTIONS ***************************************************************/ + +BOOLEAN KeSynchronizeExecution(PKINTERRUPT Interrupt, + PKSYNCHRONIZE_ROUTINE SynchronizeRoutine, + PVOID SynchronizeContext) +/* + * FUNCTION: Synchronizes the execution of a given routine with the ISR + * of a given interrupt object + * ARGUMENTS: + * Interrupt = Interrupt object to synchronize with + * SynchronizeRoutine = Routine to call whose execution is + * synchronized with the ISR + * SynchronizeContext = Parameter to pass to the synchronized routine + * RETURNS: TRUE if the operation succeeded + */ +{ + KIRQL oldlvl; + BOOLEAN ret; + + KeRaiseIrql(Interrupt->SynchLevel,&oldlvl); + KeAcquireSpinLockAtDpcLevel(Interrupt->IrqLock); + + ret = SynchronizeRoutine(SynchronizeContext); + + KeReleaseSpinLockFromDpcLevel(Interrupt->IrqLock); + KeLowerIrql(oldlvl); + + return(ret); +} + +VOID KeInitializeSpinLock(PKSPIN_LOCK SpinLock) +/* + * FUNCTION: Initalizes a spinlock + * ARGUMENTS: + * SpinLock = Caller supplied storage for the spinlock + */ +{ + SpinLock->irql = DISPATCH_LEVEL; +} + +VOID KeAcquireSpinLockAtDpcLevel(PKSPIN_LOCK SpinLock) +/* + * FUNCTION: Acquires a spinlock when the caller is already running at + * dispatch level + * ARGUMENTS: + * SpinLock = Spinlock to acquire + */ +{ +} + +VOID KeReleaseSpinLockFromDpcLevel(PKSPIN_LOCK SpinLock) +/* + * FUNCTION: Releases a spinlock when the caller was running at dispatch + * level before acquiring it + * ARGUMENTS: + * SpinLock = Spinlock to release + */ +{ +} + +VOID KeAcquireSpinLock(PKSPIN_LOCK SpinLock, PKIRQL OldIrql) +/* + * FUNCTION: Acquires a spinlock + * ARGUMENTS: + * SpinLock = Spinlock to acquire + * OldIrql (OUT) = Caller supplied storage for the previous irql + */ +{ + KeRaiseIrql(DISPATCH_LEVEL,OldIrql); +} + +VOID KeReleaseSpinLock(PKSPIN_LOCK SpinLock, KIRQL NewIrql) +/* + * FUNCTION: Releases a spinlock + * ARGUMENTS: + * SpinLock = Spinlock to release + * NewIrql = Irql level before acquiring the spinlock + */ +{ + KeLowerIrql(NewIrql); +} + diff --git a/reactos/ntoskrnl/hal/x86/syscall.c b/reactos/ntoskrnl/hal/x86/syscall.c new file mode 100644 index 00000000000..84f8a636ff8 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/syscall.c @@ -0,0 +1,9 @@ +/* + * COPYRIGHT: See COPYRIGHT in the top level source + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/syscall.c + * PURPOSE: Handles calls from user mode + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 21/07/98: Created + */ diff --git a/reactos/ntoskrnl/hal/x86/sysinfo.c b/reactos/ntoskrnl/hal/x86/sysinfo.c new file mode 100644 index 00000000000..2a1904082f7 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/sysinfo.c @@ -0,0 +1,25 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID HalQuerySystemInformation() +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/hal/x86/thread.c b/reactos/ntoskrnl/hal/x86/thread.c new file mode 100644 index 00000000000..b5729e22f5c --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/thread.c @@ -0,0 +1,163 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/hal/x86/thread.c + * PURPOSE: HAL multitasking functions + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 27/06/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ***************************************************************/ + +#define FIRST_TSS_SELECTOR (KERNEL_DS + 0x8) +#define FIRST_TSS_OFFSET (FIRST_TSS_SELECTOR / 8) + +/* FUNCTIONS **************************************************************/ + +void HalTaskSwitch(PKTHREAD thread) +/* + * FUNCTION: Switch tasks + * ARGUMENTS: + * thread = Thread to switch to + * NOTE: This function will not return until the current thread is scheduled + * again + */ +{ + __asm__("pushfl\n\t" + "cli\n\t" + "ljmp %0\n\t" + "popfl\n\t" + : /* No outputs */ + : "m" (*(((unsigned char *)(&(thread->context.nr)))-4) ) + : "ax","dx"); +} + +static unsigned int allocate_tss_descriptor(void) +/* + * FUNCTION: Allocates a slot within the GDT to describe a TSS + * RETURNS: The offset within the GDT of the slot allocated on succcess + * Zero on failure + */ +{ + unsigned int i; + for (i=0;i<16;i++) + { + if (gdt[FIRST_TSS_OFFSET + i].a==0 && + gdt[FIRST_TSS_OFFSET + i].b==0) + { + return(FIRST_TSS_OFFSET + i); + } + } + return(0); +} + +static void begin_thread(PKSTART_ROUTINE fn, PVOID start_context) +/* + * FUNCTION: This function is the start point for all new threads + * ARGUMENTS: + * fn = Actual start point of the thread + * start_context = Parameter to pass to the start routine + * RETURNS: Can't + */ +{ + NTSTATUS ret; + DPRINT("begin_thread %x %x\n",fn,start_context); + KeLowerIrql(PASSIVE_LEVEL); + ret = fn(start_context); + PsTerminateSystemThread(ret); + for(;;); +} + +BOOLEAN HalInitTask(PKTHREAD thread, PKSTART_ROUTINE fn, + PVOID StartContext) +/* + * FUNCTION: Initializes the HAL portion of a thread object + * ARGUMENTS: + * thread = Object describes the thread + * fn = Entrypoint for the thread + * StartContext = parameter to pass to the thread entrypoint + * RETURNS: True if the function succeeded + */ +{ + unsigned int desc = allocate_tss_descriptor(); + unsigned int length = sizeof(hal_thread_state) - 1; + unsigned int base = (unsigned int)(&(thread->context)); + unsigned int* kernel_stack = ExAllocatePool(NonPagedPool,4096); + + /* + * Make sure + */ + assert(sizeof(hal_thread_state)>=0x68); + + /* + * Setup a TSS descriptor + */ + gdt[desc].a = (length & 0xffff) | ((base & 0xffff) << 16); + gdt[desc].b = ((base & 0xff0000)>>16) | 0x8900 | (length & 0xf0000) + | (base & 0xff000000); + + /* + * Initialize the stack for the thread (including the two arguments to + * the general start routine). + */ + kernel_stack[1023] = (unsigned int)StartContext; + kernel_stack[1022] = (unsigned int)fn; + kernel_stack[1021] = NULL; + + /* + * Initialize the thread context + */ + memset(&thread->context,0,sizeof(hal_thread_state)); + thread->context.ldt = 0; + thread->context.eflags = (1<<1)+(1<<9); + thread->context.iomap_base = FIELD_OFFSET(hal_thread_state,io_bitmap); + thread->context.esp0 = &kernel_stack[1021]; + thread->context.ss0 = KERNEL_DS; + thread->context.esp = &kernel_stack[1021]; + thread->context.ss = KERNEL_DS; + thread->context.cs = KERNEL_CS; + thread->context.eip = (unsigned long)begin_thread; + thread->context.io_bitmap[0] = 0xff; + thread->context.cr3 = ((unsigned int)get_page_directory()) - IDMAP_BASE; + thread->context.ds = KERNEL_DS; + thread->context.es = KERNEL_DS; + thread->context.fs = KERNEL_DS; + thread->context.gs = KERNEL_DS; + thread->context.nr = desc * 8; + + return(TRUE); +} + +void HalInitFirstTask(PKTHREAD thread) +/* + * FUNCTION: Called to setup the HAL portion of a thread object for the + * initial thread + */ +{ + /* + * Initialize the thread context + */ + HalInitTask(thread,NULL,NULL); + + /* + * Load the task register + */ + __asm__("ltr %%ax" + : /* no output */ + : "a" (FIRST_TSS_OFFSET*8)); +} diff --git a/reactos/ntoskrnl/hal/x86/usercall.asm b/reactos/ntoskrnl/hal/x86/usercall.asm new file mode 100644 index 00000000000..bab7e271370 --- /dev/null +++ b/reactos/ntoskrnl/hal/x86/usercall.asm @@ -0,0 +1,46 @@ +; +; + +%include "internal/hal/segment.inc" + +bits 32 +section .text +extern _SystemServiceTable + +_kernel_mode_call_handler: + + ; + ; Save some registers + ; + push ds + push es + push esi + push edi + + ; + ; Transfer the parameters from user mode + ; + push USER_DS + pop es + + mov edx,esi + mov esp,edi + mov ecx,_SystemServiceTable[eax*4] + sub esp,ecx + cld + rep movsb + + ; + ; Call the actual service routine + ; + mov eax,_SystemServiceTable[eax*4+4] + jmp eax + + ; + ; Restore registers and return + ; + pop edi + pop esi + pop es + pop ds + ret diff --git a/reactos/ntoskrnl/io/adapter.c b/reactos/ntoskrnl/io/adapter.c new file mode 100644 index 00000000000..4c2d2da114f --- /dev/null +++ b/reactos/ntoskrnl/io/adapter.c @@ -0,0 +1,60 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/adapter.c + * PURPOSE: DMA handling + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS IoAllocateAdapterChannel(PADAPTER_OBJECT AdapterObject, + PDEVICE_OBJECT DeviceObject, + ULONG NumberOfMapRegisters, + PDRIVER_CONTROL ExecutionRoutine, + PVOID Context) +{ + UNIMPLEMENTED; +} + +BOOLEAN IoFlushAdapterBuffers(PADAPTER_OBJECT AdapterObject, + PMDL Mdl, + PVOID MapRegisterBase, + PVOID CurrentVa, + ULONG Length, + BOOLEAN WriteToDevice) +{ + UNIMPLEMENTED; +} + +PHYSICAL_ADDRESS IoMapTransfer(PADAPTER_OBJECT AdapterObject, + PMDL Mdl, + PVOID MapRegisterBase, + PVOID CurrentVa, + PULONG Length, + BOOLEAN WriteToDevice) +{ + UNIMPLEMENTED; +} + +VOID IoFreeAdapterChannel(PADAPTER_OBJECT AdapterObject) +{ + UNIMPLEMENTED; +} + +VOID IoFreeMapRegisters(PADAPTER_OBJECT AdapterObject, + PVOID MapRegisterBase, + ULONG NumberOfMapRegisters) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/arc.c b/reactos/ntoskrnl/io/arc.c new file mode 100644 index 00000000000..fe89d6be8e9 --- /dev/null +++ b/reactos/ntoskrnl/io/arc.c @@ -0,0 +1,30 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID IoAssignArcName(PUNICODE_STRING ArcName, + PUNICODE_STRING DeviceName) +{ + IoCreateSymbolicLink(ArcName,DeviceName); +} + +VOID IoDeassignArcName(PUNICODE_STRING ArcName) +{ + IoDeleteSymbolicLink(ArcName); +} diff --git a/reactos/ntoskrnl/io/cancel.c b/reactos/ntoskrnl/io/cancel.c new file mode 100644 index 00000000000..6501387afc9 --- /dev/null +++ b/reactos/ntoskrnl/io/cancel.c @@ -0,0 +1,62 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/cancel.c + * PURPOSE: Cancel routine + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS *******************************************************************/ + +static KSPIN_LOCK CancelSpinLock; + +/* FUNCTIONS *****************************************************************/ + +BOOLEAN IoCancelIrp(PIRP Irp) +{ + KIRQL oldlvl; + + DPRINT("IoCancelIrp(Irp %x)\n",Irp); + + IoAcquireCancelSpinLock(&oldlvl); + Irp->Cancel = TRUE; + if (Irp->CancelRoutine==NULL) + { + return(FALSE); + } + Irp->CancelRoutine(Irp->Stack[0].DeviceObject,Irp); + IoReleaseCancelSpinLock(&oldlvl); + return(TRUE); +} + +VOID IoInitCancelHandling(VOID) +{ + KeInitializeSpinLock(&CancelSpinLock); +} + +VOID IoAcquireCancelSpinLock(PKIRQL Irql) +{ + KeAcquireSpinLock(&CancelSpinLock,Irql); +} + +VOID IoReleaseCancelSpinLock(KIRQL Irql) +{ + KeReleaseSpinLock(&CancelSpinLock,Irql); +} + +PDRIVER_CANCEL IoSetCancelRoutine(PIRP Irp, PDRIVER_CANCEL CancelRoutine) +{ + return((PDRIVER_CANCEL)InterlockedExchange((PULONG)&Irp->CancelRoutine, + (ULONG)CancelRoutine)); +} diff --git a/reactos/ntoskrnl/io/cntrller.c b/reactos/ntoskrnl/io/cntrller.c new file mode 100644 index 00000000000..07f7e00432e --- /dev/null +++ b/reactos/ntoskrnl/io/cntrller.c @@ -0,0 +1,145 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/cntrller.c + * PURPOSE: Implements the controller object + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* TYPES ********************************************************************/ + +typedef struct +/* + * PURPOSE: A entry in the queue waiting for a controller object + */ +{ + KDEVICE_QUEUE_ENTRY Entry; + PDEVICE_OBJECT DeviceObject; + PDRIVER_CONTROL ExecutionRoutine; + PVOID Context; +} CONTROLLER_QUEUE_ENTRY, *PCONTROLLER_QUEUE_ENTRY; + +/* FUNCTIONS *****************************************************************/ + +VOID IoAllocateController(PCONTROLLER_OBJECT ControllerObject, + PDEVICE_OBJECT DeviceObject, + PDRIVER_CONTROL ExecutionRoutine, + PVOID Context) +/* + * FUNCTION: Sets up a call to a driver-supplied ControllerControl routine + * as soon as the device controller, represented by the given controller + * object, is available to carry out an I/O operation for the target device, + * represented by the given device object. + * ARGUMENTS: + * ControllerObject = Driver created controller object + * DeviceObject = Target device for the current irp + * ExecutionRoutine = Routine to be called when the device is available + * Context = Driver supplied context to be passed on to the above routine + * NOTE: Is the below implementation correct. + */ +{ + PCONTROLLER_QUEUE_ENTRY entry; + IO_ALLOCATION_ACTION Result; + + assert(KeGetCurrentIrql()==DISPATCH_LEVEL); + + entry=ExAllocatePool(NonPagedPool,sizeof(CONTROLLER_QUEUE_ENTRY)); + assert(entry!=NULL); + + entry->DeviceObject = DeviceObject; + entry->ExecutionRoutine = ExecutionRoutine; + entry->Context = Context; + + if (KeInsertDeviceQueue(&ControllerObject->DeviceWaitQueue,&entry->Entry)) + { + return; + } + Result = ExecutionRoutine(DeviceObject,DeviceObject->CurrentIrp, + NULL,Context); + if (Result == DeallocateObject) + { + IoFreeController(ControllerObject); + ExFreePool(entry); + } +} + +PCONTROLLER_OBJECT IoCreateController(ULONG Size) +/* + * FUNCTION: Allocates memory and initializes a controller object + * ARGUMENTS: + * Size = Size (in bytes) to be allocated for the controller extension + * RETURNS: A pointer to the created object + */ +{ + PCONTROLLER_OBJECT controller; + + assert(KeGetCurrentIrql()==PASSIVE_LEVEL); + + controller = ExAllocatePool(NonPagedPool,sizeof(CONTROLLER_OBJECT)); + if (controller==NULL) + { + return(NULL); + } + + controller->ControllerExtension=ExAllocatePool(NonPagedPool,Size); + if (controller->ControllerExtension==NULL) + { + ExFreePool(controller); + return(NULL); + } + + KeInitializeDeviceQueue(&controller->DeviceWaitQueue); + return(controller); +} + +VOID IoDeleteController(PCONTROLLER_OBJECT ControllerObject) +/* + * FUNCTION: Removes a given controller object from the system + * ARGUMENTS: + * ControllerObject = Controller object to be released + */ +{ + assert(KeGetCurrentIrql()==PASSIVE_LEVEL); + + ExFreePool(ControllerObject->ControllerExtension); + ExFreePool(ControllerObject); +} + +VOID IoFreeController(PCONTROLLER_OBJECT ControllerObject) +/* + * FUNCTION: Releases a previously allocated controller object when a + * device has finished an I/O request + * ARGUMENTS: + * ControllerObject = Controller object to be released + */ +{ + PKDEVICE_QUEUE_ENTRY QEntry = KeRemoveDeviceQueue(&ControllerObject-> + DeviceWaitQueue); + CONTROLLER_QUEUE_ENTRY* Entry = CONTAINING_RECORD(QEntry, + CONTROLLER_QUEUE_ENTRY, + Entry); + IO_ALLOCATION_ACTION Result; + + if (QEntry==NULL) + { + return; + } + Result = Entry->ExecutionRoutine(Entry->DeviceObject, + Entry->DeviceObject->CurrentIrp,NULL, + Entry->Context); + if (Result == DeallocateObject) + { + ExFreePool(Entry); + } +} + diff --git a/reactos/ntoskrnl/io/create.c b/reactos/ntoskrnl/io/create.c new file mode 100644 index 00000000000..a2436afcf64 --- /dev/null +++ b/reactos/ntoskrnl/io/create.c @@ -0,0 +1,101 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/iomgr/create.cc + * PURPOSE: Handling file create/open apis + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 24/05/98: Created + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* FUNCTIONS *************************************************************/ + +NTSTATUS ZwCreateFile(PHANDLE FileHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes, + PIO_STATUS_BLOCK IoStatusBlock, + PLARGE_INTEGER AllocateSize, + ULONG FileAttributes, + ULONG ShareAccess, + ULONG CreateDisposition, + ULONG CreateOptions, + PVOID EaBuffer, + ULONG EaLength) +{ + UNIMPLEMENTED; +} + +NTSTATUS ZwOpenFile(PHANDLE FileHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes, + PIO_STATUS_BLOCK IoStatusBlock, + ULONG ShareAccess, + ULONG OpenOptions) +{ + UNIMPLEMENTED; +} + +HANDLE STDCALL CreateFileA(LPCSTR lpFileName, DWORD dwDesiredAccess, + DWORD dwShareMode, + LPSECURITY_ATTRIBUTES lpSecurityAttributes, + DWORD dwCreationDisposition, + DWORD dwFlagsAndAttributes, + HANDLE hTemplateFile) +{ + PDEVICE_OBJECT DeviceObject; + PIRP Irp; + HANDLE hfile; + UNICODE_STRING filename; + ANSI_STRING afilename; + + RtlInitAnsiString(&afilename,lpFileName); + RtlAnsiStringToUnicodeString(&filename,&afilename,TRUE); + DeviceObject = ObLookupObject(NULL,&filename); + DPRINT("Sending IRP for IRP_MJ_CREATE to %x\n",DeviceObject); + if (DeviceObject==NULL) + { + DPRINT("(%s:%d) Object not found\n",__FILE__,__LINE__); + return(NULL); + } + + hfile = ObAddHandle(DeviceObject); + + /* + * Tell the device we are openining it + */ + Irp = IoAllocateIrp(DeviceObject->StackSize, TRUE); + if (Irp==NULL) + { + return(NULL); + } + + DPRINT("Preparing IRP\n"); + + /* + * Set up the stack location + */ + Irp->Stack[Irp->CurrentLocation].MajorFunction = IRP_MJ_CREATE; + Irp->Stack[Irp->CurrentLocation].MinorFunction = 0; + Irp->Stack[Irp->CurrentLocation].Flags = 0; + Irp->Stack[Irp->CurrentLocation].Control = 0; + Irp->Stack[Irp->CurrentLocation].DeviceObject = DeviceObject; +// Irp->Stack[Irp->StackPtr].FileObject = &files[hfile]; + + DPRINT("Sending IRP\n"); + IoCallDriver(DeviceObject,Irp); + + DPRINT("Returning %x\n",hfile); + return(hfile); +} + diff --git a/reactos/ntoskrnl/io/device.c b/reactos/ntoskrnl/io/device.c new file mode 100644 index 00000000000..18c988dd3db --- /dev/null +++ b/reactos/ntoskrnl/io/device.c @@ -0,0 +1,186 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/iomgr/device.cc + * PURPOSE: Manage devices + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 15/05/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include + +#include +#include +#include +#include + +//#define NDEBUG +#include + +/* FUNCTIONS ***************************************************************/ + +NTSTATUS IoAttachDeviceByPointer(PDEVICE_OBJECT SourceDevice, + PDEVICE_OBJECT TargetDevice) +{ + UNIMPLEMENTED; +} + +VOID IoDeleteDevice(PDEVICE_OBJECT DeviceObject) +{ + UNIMPLEMENTED; +} + +PDEVICE_OBJECT IoGetRelatedDeviceObject(PFILE_OBJECT FileObject) +{ + return(FileObject->DeviceObject); +} + +NTSTATUS IoGetDeviceObjectPointer(PUNICODE_STRING ObjectName, + ACCESS_MASK DesiredAccess, + PFILE_OBJECT* FileObject, + PDEVICE_OBJECT* DeviceObject) +{ + UNIMPLEMENTED; +} + +VOID IoDetachDevice(PDEVICE_OBJECT TargetDevice) +{ + UNIMPLEMENTED; +} + +PDEVICE_OBJECT IoAttachDeviceToDeviceStack(PDEVICE_OBJECT SourceDevice, + PDEVICE_OBJECT TargetDevice) +{ + UNIMPLEMENTED; +} + +VOID IoRegisterDriverReinitialization(PDRIVER_OBJECT DriverObject, + PDRIVER_REINITIALIZE ReinitRoutine, + PVOID Context) +{ + UNIMPLEMENTED; +} + + +NTSTATUS InitalizeLoadedDriver(PDRIVER_INITIALIZE entry) +/* + * FUNCTION: Called to initalize a loaded driver + * ARGUMENTS: + */ +{ + NTSTATUS ret; + PDRIVER_OBJECT DriverObject; + + /* + * Allocate memory for a driver object + * NOTE: The object only becomes system visible once the associated + * device objects are intialized + */ + DriverObject=ExAllocatePool(NonPagedPool,sizeof(DRIVER_OBJECT)); + if (DriverObject==NULL) + { + printk("%s:%d\n",__FILE__,__LINE__); + return(STATUS_INSUFFICIENT_RESOURCES); + } + memset(DriverObject,sizeof(DRIVER_OBJECT),0); + + /* + * Initalize the driver + * FIXME: Registry in general please + */ + if ((ret=entry(DriverObject,NULL))!=STATUS_SUCCESS) + { + DPRINT("Failed to load driver (status %x)\n",ret); + ExFreePool(DriverObject); + return(ret); + } + return(STATUS_SUCCESS); +} + +NTSTATUS IoAttachDevice(PDEVICE_OBJECT SourceDevice, + PUNICODE_STRING TargetDevice, + PDEVICE_OBJECT* AttachedDevice) +/* + * FUNCTION: Layers a device over the highest device in a device stack + * ARGUMENTS: + * SourceDevice = Device to attached + * TargetDevice = Name of the target device + * AttachedDevice (OUT) = Caller storage for the device attached to + */ +{ + UNIMPLEMENTED; +} + +NTSTATUS IoCreateDevice(PDRIVER_OBJECT DriverObject, + ULONG DeviceExtensionSize, + PUNICODE_STRING DeviceName, + DEVICE_TYPE DeviceType, + ULONG DeviceCharacteristics, + BOOLEAN Exclusive, + PDEVICE_OBJECT* DeviceObject) +/* + * FUNCTION: Allocates memory for and intializes a device object for use for + * a driver + * ARGUMENTS: + * DriverObject : Driver object passed by iomgr when the driver was + * loaded + * DeviceExtensionSize : Number of bytes for the device extension + * DeviceName : Unicode name of device + * DeviceType : Device type + * DeviceCharacteristics : Bit mask of device characteristics + * Exclusive : True if only one thread can access the device at a + * time + * RETURNS: + * Success or failure + * DeviceObject : Contains a pointer to allocated device object + * if the call succeeded + * NOTES: See the DDK documentation for more information + */ +{ + PDEVICE_OBJECT dev; + OBJECT_ATTRIBUTES dev_attr; + HANDLE devh; + + InitializeObjectAttributes(&dev_attr,DeviceName,0,NULL,NULL); + dev = ObGenericCreateObject(&devh,0,&dev_attr,OBJTYP_DEVICE); + + *DeviceObject=NULL; + + if (dev==NULL) + { + return(STATUS_INSUFFICIENT_RESOURCES); + } + + if (DriverObject->DeviceObject==NULL) + { + DriverObject->DeviceObject = dev; + dev->NextDevice=NULL; + } + else + { + dev->NextDevice=DriverObject->DeviceObject; + DriverObject->DeviceObject=dev; + } + + dev->DriverObject = DriverObject; + dev->CurrentIrp=NULL; + dev->Flags=0; + + dev->DeviceExtension=ExAllocatePool(NonPagedPool,DeviceExtensionSize); + if (DeviceExtensionSize > 0 && dev->DeviceExtension==NULL) + { + ExFreePool(dev); + return(STATUS_INSUFFICIENT_RESOURCES); + } + + dev->DeviceType=DeviceType; + dev->StackSize=1; + dev->AlignmentRequirement=1; + + *DeviceObject=dev; + + return(STATUS_SUCCESS); +} diff --git a/reactos/ntoskrnl/io/dpc.c b/reactos/ntoskrnl/io/dpc.c new file mode 100644 index 00000000000..93d7f45b6d9 --- /dev/null +++ b/reactos/ntoskrnl/io/dpc.c @@ -0,0 +1,33 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID IoInitializeDpcRequest(PDEVICE_OBJECT DeviceObject, + PIO_DPC_ROUTINE DpcRoutine) +{ + KeInitializeDpc(&DeviceObject->Dpc,(PKDEFERRED_ROUTINE)DpcRoutine, + DeviceObject); +} + +VOID IoRequestDpc(PDEVICE_OBJECT DeviceObject, + PIRP Irp, + PVOID Context) +{ + KeInsertQueueDpc(&DeviceObject->Dpc,Irp,Context); +} diff --git a/reactos/ntoskrnl/io/drvlck.c b/reactos/ntoskrnl/io/drvlck.c new file mode 100644 index 00000000000..01ea765ddbc --- /dev/null +++ b/reactos/ntoskrnl/io/drvlck.c @@ -0,0 +1,50 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/iomgr/drvlck.c + * PURPOSE: Managing driver managing + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID MmUnlockPagableImageSection(PVOID ImageSectionHandle) +{ + UNIMPLEMENTED; +} + +VOID MmLockPagableSectionByHandle(PVOID ImageSectionHandle) +{ + UNIMPLEMENTED; +} + +PVOID MmLockPagableCodeSection(PVOID AddressWithinSection) +{ + UNIMPLEMENTED; +} + +PVOID MmLockPagableDataSection(PVOID AddressWithinSection) +{ + UNIMPLEMENTED; +} + +VOID MmPageEntireDriver(PVOID AddressWithinSection) +{ + UNIMPLEMENTED; +} + +VOID MmResetDriverPaging(PVOID AddressWithinSection) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/io/errlog.c b/reactos/ntoskrnl/io/errlog.c new file mode 100644 index 00000000000..25b30760f64 --- /dev/null +++ b/reactos/ntoskrnl/io/errlog.c @@ -0,0 +1,30 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PVOID IoAllocateErrorLogEntry(PVOID IoObject, UCHAR EntrySize) +{ + UNIMPLEMENTED; +} + +VOID IoWriteErrorLogEntry(PVOID ElEntry) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/io/error.c b/reactos/ntoskrnl/io/error.c new file mode 100644 index 00000000000..64d0f624821 --- /dev/null +++ b/reactos/ntoskrnl/io/error.c @@ -0,0 +1,57 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +BOOLEAN IoIsErrorUserInduced(NTSTATUS Status) +{ + switch(Status) + { + case STATUS_DEVICE_NOT_READY: + case STATUS_IO_TIMEOUT: + case STATUS_MEDIA_WRITE_PROTECTED: + case STATUS_NO_MEDIA_IN_DRIVE: + case STATUS_VERIFY_REQUIRED: + case STATUS_UNRECOGNIZED_MEDIA: + case STATUS_WRONG_VOLUME: + return(TRUE); + } + return(FALSE); +} + +VOID IoSetHardErrorOrVerifyDevice(PIRP Irp, PDEVICE_OBJECT DeviceObject) +{ + UNIMPLEMENTED; +} + +VOID IoRaiseHardError(PIRP Irp, PVPB Vpb, PDEVICE_OBJECT RealDeviceObject) +{ + UNIMPLEMENTED; +} + +BOOLEAN IoIsTotalDeviceFailure(NTSTATUS Status) +{ + UNIMPLEMENTED; +} + +BOOLEAN IoRaiseInformationalHardError(NTSTATUS ErrorStatus, + PUNICODE_STRING String, + PKTHREAD Thread) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/event.c b/reactos/ntoskrnl/io/event.c new file mode 100644 index 00000000000..5e3e25a442e --- /dev/null +++ b/reactos/ntoskrnl/io/event.c @@ -0,0 +1,32 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/event.c + * PURPOSE: Implements named events + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PKEVENT IoCreateNotificationEvent(PUNICODE_STRING EventName, + PHANDLE EventHandle) +{ + UNIMPLEMENTED; +} + +PKEVENT IoCreateSynchronizationEvent(PUNICODE_STRING EventName, + PHANDLE EventHandle) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/io/fdisk.c b/reactos/ntoskrnl/io/fdisk.c new file mode 100644 index 00000000000..678dc8c645f --- /dev/null +++ b/reactos/ntoskrnl/io/fdisk.c @@ -0,0 +1,44 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/fdisk.c + * PURPOSE: Handling fixed disks + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS IoReadPartitionTable(PDEVICE_OBJECT DeviceObject, + ULONG SectorSize, + BOOLEAN ReturnRecognizedPartitions, + struct _DRIVE_LAYOUT_INFORMATION** PBuffer) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoSetPartitionInformation(PDEVICE_OBJECT DeviceObject, + ULONG SectorSize, + ULONG PartitionNumber, + ULONG PartitionType) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoWritePartitionTable(PDEVICE_OBJECT DeviceObject, + ULONG SectorSize, + ULONG SectorsPerTrack, + ULONG NumberOfHeads, + struct _DRIVE_LAYOUT_INFORMATION* PBuffer) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/file.c b/reactos/ntoskrnl/io/file.c new file mode 100644 index 00000000000..127793741d1 --- /dev/null +++ b/reactos/ntoskrnl/io/file.c @@ -0,0 +1,42 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/io/file.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS ZwQueryInformationFile(HANDLE FileHandle, + PIO_STATUS_BLOCK IoStatusBlock, + PVOID FileInformation, + ULONG Length, + FILE_INFORMATION_CLASS FileInformationClass) +{ + UNIMPLEMENTED; +} + +NTSTATUS ZwSetInformationFile(HANDLE FileHandle, + PIO_STATUS_BLOCK IoStatusBlock, + PVOID FileInformation, + ULONG Length, + FILE_INFORMATION_CLASS FileInformationClass) +{ + UNIMPLEMENTED; +} + +PGENERIC_MAPPING IoGetFileObjectGenericMapping() +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/ioctrl.c b/reactos/ntoskrnl/io/ioctrl.c new file mode 100644 index 00000000000..1e4cd3af73c --- /dev/null +++ b/reactos/ntoskrnl/io/ioctrl.c @@ -0,0 +1,24 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +ULONG IoGetFunctionCodeFromCtlCode(ULONG ControlCode) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/iomgr.c b/reactos/ntoskrnl/io/iomgr.c new file mode 100644 index 00000000000..b523aa30cc7 --- /dev/null +++ b/reactos/ntoskrnl/io/iomgr.c @@ -0,0 +1,55 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/iomgr.c + * PURPOSE: Initializes the io manager + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 29/07/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include + +/* GLOBALS *******************************************************************/ + +OBJECT_TYPE DeviceObjectType = {{NULL,0,0}, + 0, + 0, + ULONG_MAX, + ULONG_MAX, + sizeof(DEVICE_OBJECT), + 0, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + }; + + +/* FUNCTIONS ****************************************************************/ + +VOID IoInit(VOID) +{ + OBJECT_ATTRIBUTES attr; + HANDLE handle; + UNICODE_STRING string; + ANSI_STRING astring; + + ObRegisterType(OBJTYP_DEVICE,&DeviceObjectType); + + RtlInitAnsiString(&astring,"\\Device"); + RtlAnsiStringToUnicodeString(&string,&astring,TRUE); + InitializeObjectAttributes(&attr,&string,0,NULL,NULL); + ZwCreateDirectoryObject(&handle,0,&attr); + + IoInitCancelHandling(); +} diff --git a/reactos/ntoskrnl/io/irp.c b/reactos/ntoskrnl/io/irp.c new file mode 100644 index 00000000000..01891dd15ab --- /dev/null +++ b/reactos/ntoskrnl/io/irp.c @@ -0,0 +1,295 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/irp.c + * PURPOSE: Handle IRPs + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 24/05/98: Created + */ + +/* NOTES ******************************************************************* + * + * Layout of an IRP + * + * ################ + * # Headers # + * ################ + * # # + * # Variable # + * # length list # + * # of io stack # + * # locations # + * # # + * ################ + * + * + * + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include + +#define NDEBUG +#include + +/* FUNCTIONS ****************************************************************/ + +PDEVICE_OBJECT IoGetDeviceToVerify(PETHREAD Thread) +/* + * FUNCTION: Returns a pointer to the device, representing a removable-media + * device, that is the target of the given thread's I/O request + */ +{ + UNIMPLEMENTED; +} + +VOID IoFreeIrp(PIRP Irp) +/* + * FUNCTION: Releases a caller allocated irp + * ARGUMENTS: + * Irp = Irp to free + */ +{ + ExFreePool(Irp); +} + +PIRP IoMakeAssociatedIrp(PIRP Irp, CCHAR StackSize) +/* + * FUNCTION: Allocates and initializes an irp to associated with a master irp + * ARGUMENTS: + * Irp = Master irp + * StackSize = Number of stack locations to be allocated in the irp + * RETURNS: The irp allocated + */ +{ + PIRP AssocIrp; + + AssocIrp = IoAllocateIrp(StackSize,FALSE); + UNIMPLEMENTED; +} + +VOID IoMarkIrpPending(PIRP Irp) +/* + * FUNCTION: Marks the specified irp, indicating further processing will + * be required by other driver routines + * ARGUMENTS: + * Irp = Irp to mark + */ +{ + IoGetCurrentIrpStackLocation(Irp)->Control |= SL_PENDING_RETURNED; +} + +PIRP IoBuildAsynchronousFsdRequest(ULONG MajorFunction, + PDEVICE_OBJECT DeviceObject, + PVOID Buffer, + ULONG Length, + PLARGE_INTEGER StartingOffset, + PIO_STATUS_BLOCK IoStatusBlock) +{ + UNIMPLEMENTED; +} + +PIRP IoBuildDeviceIoControlRequest(ULONG IoControlCode, + PDEVICE_OBJECT DeviceObject, + PVOID InputBuffer, + ULONG InputBufferLength, + PVOID OutputBuffer, + ULONG OutputBufferLength, + BOOLEAN InternalDeviceIoControl, + PKEVENT Event, + PIO_STATUS_BLOCK IoStatusBlock) +{ + UNIMPLEMENTED; +} + +PIRP IoBuildSynchronousFsdRequest(ULONG MajorFunction, + PDEVICE_OBJECT DeviceObject, + PVOID Buffer, + ULONG Length, + PLARGE_INTEGER StartingOffset, + PKEVENT Event, + PIO_STATUS_BLOCK IoStatusBlock) +{ + PDRIVER_OBJECT DriverObject = DeviceObject->DriverObject; + PIRP irp; + PIO_STACK_LOCATION StackPtr; + + /* + * Allocate an IRP for the transfer + */ + irp = IoAllocateIrp(DeviceObject->StackSize,TRUE); + if (irp==NULL) + { + printk("Failed to allocate IRP\n"); + return(FALSE); + } + + /* + * Prepare the parameter in the next IO stack location + */ + StackPtr = IoGetNextIrpStackLocation(irp); + StackPtr->MajorFunction = MajorFunction; + StackPtr->MinorFunction = 0; + StackPtr->Flags = 0; + StackPtr->Control = 0; +} + +USHORT IoSizeOfIrp(CCHAR StackSize) +/* + * FUNCTION: Determines the size of an IRP + * ARGUMENTS: + * StackSize = number of stack locations in the IRP + * RETURNS: The size of the IRP in bytes + */ +{ + return(sizeof(IRP)+((StackSize-1)*sizeof(IO_STACK_LOCATION))); +} + +VOID IoInitializeIrp(PIRP Irp, USHORT PacketSize, CCHAR StackSize) +/* + * FUNCTION: Initalizes an irp allocated by the caller + * ARGUMENTS: + * Irp = IRP to initalize + * PacketSize = Size in bytes of the IRP + * StackSize = Number of stack locations in the IRP + */ +{ + assert(Irp!=NULL); + memset(Irp,0,PacketSize); + Irp->CurrentLocation=StackSize; + Irp->Tail.Overlay.CurrentStackLocation=IoGetCurrentIrpStackLocation(Irp); +} + +PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(PIRP Irp) +/* + * FUNCTION: Gets a pointer to the callers location in the I/O stack in + * the given IRP + * ARGUMENTS: + * Irp = Points to the IRP + * RETURNS: A pointer to the stack location + */ +{ + return(&Irp->Stack[Irp->CurrentLocation]); +} + + +VOID IoSetNextIrpStackLocation(PIRP Irp) +{ + Irp->CurrentLocation--; + Irp->Tail.Overlay.CurrentStackLocation--; +} + +PIO_STACK_LOCATION IoGetNextIrpStackLocation(PIRP Irp) +/* + * FUNCTION: Gives a higher level driver access to the next lower driver's + * I/O stack location + * ARGUMENTS: + * Irp = points to the irp + * RETURNS: A pointer to the stack location + */ +{ + assert(Irp!=NULL); + DPRINT("Irp %x Irp->StackPtr %x\n",Irp,Irp->CurrentLocation); + return(&Irp->Stack[Irp->CurrentLocation-1]); +} + +NTSTATUS IoCallDriver(PDEVICE_OBJECT DevObject, PIRP irp) +/* + * FUNCTION: Sends an IRP to the next lower driver + */ +{ + PDRIVER_OBJECT drv = DevObject->DriverObject; + IO_STACK_LOCATION* param = IoGetNextIrpStackLocation(irp); + + irp->Tail.Overlay.CurrentStackLocation--; + irp->CurrentLocation--; + DPRINT("Io stack address %x\n",param); + DPRINT("Function %d Routine %x\n",param->MajorFunction, + drv->MajorFunction[param->MajorFunction]); + DPRINT("IRP_MJ_CREATE %d\n",IRP_MJ_CREATE); + return(drv->MajorFunction[param->MajorFunction](DevObject,irp)); +} + +PIRP IoAllocateIrp(CCHAR StackSize, BOOLEAN ChargeQuota) +/* + * FUNCTION: Allocates an IRP + * ARGUMENTS: + * StackSize = the size of the stack required for the irp + * ChargeQuota = Charge allocation to current threads quota + * RETURNS: Irp allocated + */ +{ + PIRP Irp; + + DPRINT("IoAllocateIrp(StackSize %d ChargeQuota %d)\n",StackSize, + ChargeQuota); + if (ChargeQuota) + { + Irp = ExAllocatePoolWithQuota(NonPagedPool,IoSizeOfIrp(StackSize)); + } + else + { + Irp = ExAllocatePool(NonPagedPool,IoSizeOfIrp(StackSize)); + } + + if (Irp==NULL) + { + return(NULL); + } + + Irp->CurrentLocation=StackSize; + + DPRINT("Irp %x Irp->StackPtr %d\n",Irp,Irp->CurrentLocation); + return(Irp); +} + +VOID IoSetCompletionRoutine(PIRP Irp, + PIO_COMPLETION_ROUTINE CompletionRoutine, + PVOID Context, + BOOLEAN InvokeOnSuccess, + BOOLEAN InvokeOnError, + BOOLEAN InvokeOnCancel) +{ + IO_STACK_LOCATION* param = IoGetNextIrpStackLocation(Irp); + + param->CompletionRoutine=CompletionRoutine; + param->CompletionContext=Context; + if (InvokeOnSuccess) + { + param->Control = SL_INVOKE_ON_SUCCESS; + } + if (InvokeOnError) + { + param->Control = param->Control | SL_INVOKE_ON_ERROR; + } + if (InvokeOnCancel) + { + param->Control = param->Control | SL_INVOKE_ON_CANCEL; + } +} + +VOID IoCompleteRequest(IRP* Irp, CCHAR PriorityBoost) +/* + * FUNCTION: Indicates the caller has finished all processing for a given + * I/O request and is returning the given IRP to the I/O manager + * ARGUMENTS: + * Irp = Irp to be cancelled + * PriorityBoost = Increment by which to boost the priority of the + * thread making the request + */ +{ + unsigned int i; + + for (i=0;i<0;i++) + { + if (Irp->Stack[i].CompletionRoutine!=NULL) + { + Irp->Stack[i].CompletionRoutine(Irp->Stack[i].DeviceObject,Irp, + Irp->Stack[i].CompletionContext); + } + } +} diff --git a/reactos/ntoskrnl/io/mdl.c b/reactos/ntoskrnl/io/mdl.c new file mode 100644 index 00000000000..7df6c991ee7 --- /dev/null +++ b/reactos/ntoskrnl/io/mdl.c @@ -0,0 +1,69 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PMDL IoAllocateMdl(PVOID VirtualAddress, + ULONG Length, + BOOLEAN SecondaryBuffer, + BOOLEAN ChargeQuota, + PIRP Irp) +{ + PMDL Mdl; + + if (ChargeQuota) + { + Mdl = ExAllocatePoolWithQuota(NonPagedPool, + MmSizeOfMdl(VirtualAddress,Length)); + } + else + { + Mdl = ExAllocatePool(NonPagedPool,MmSizeOfMdl(VirtualAddress,Length)); + } + MmInitializeMdl(Mdl,VirtualAddress,Length); + if (Irp!=NULL && !SecondaryBuffer) + { + Irp->MdlAddress = Mdl; + } + return(Mdl); +} + +VOID IoBuildPartialMdl(PMDL SourceMdl, + PMDL TargetMdl, + PVOID VirtualAddress, + ULONG Length) +{ + PULONG TargetPages = (PULONG)(TargetMdl + 1); + PULONG SourcePages = (PULONG)(SourceMdl + 1); + ULONG Va; + ULONG Delta = (PAGE_ROUND_DOWN(VirtualAddress) - (ULONG)SourceMdl->StartVa)/ + PAGESIZE; + + for (Va = 0; Va < (PAGE_ROUND_UP(Length)/PAGESIZE); Va++) + { + TargetPages[Va] = SourcePages[Va+Delta]; + } +} + +VOID IoFreeMdl(PMDL Mdl) +{ + MmUnmapLockedPages(MmGetSystemAddressForMdl(Mdl),Mdl); + MmUnlockPages(Mdl); + ExFreePool(Mdl); +} diff --git a/reactos/ntoskrnl/io/process.c b/reactos/ntoskrnl/io/process.c new file mode 100644 index 00000000000..5be918882ae --- /dev/null +++ b/reactos/ntoskrnl/io/process.c @@ -0,0 +1,29 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/iomgr/process.c + * PURPOSE: Process functions that, bizarrely, are in the iomgr + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PEPROCESS IoGetCurrentProcess() +{ + return(PsGetCurrentProcess()); +} + +PVOID IoGetInitialStack() +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/queue.c b/reactos/ntoskrnl/io/queue.c new file mode 100644 index 00000000000..4bd30e4a84e --- /dev/null +++ b/reactos/ntoskrnl/io/queue.c @@ -0,0 +1,112 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/queue.c + * PURPOSE: Implement device queueing + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES ******************************************************************/ + +#include +#include +#include +#include + +/* FUNCTIONS *****************************************************************/ + +VOID IoStartNextPacketByKey(PDEVICE_OBJECT DeviceObject, + BOOLEAN Cancelable, + ULONG Key) +/* + * FUNCTION: Dequeues the next packet from the given device object's + * associated device queue according to a specified sort-key value and calls + * the drivers StartIo routine with that IRP + * ARGUMENTS: + * DeviceObject = Device object for which the irp is to dequeued + * Cancelable = True if IRPs in the key can be canceled + * Key = Sort key specifing which entry to remove from the queue + */ +{ + PKDEVICE_QUEUE_ENTRY entry; + PIRP Irp; + KIRQL oldirql; + + entry = KeRemoveByKeyDeviceQueue(&DeviceObject->DeviceQueue,Key); + + if (entry!=NULL) + { + Irp = CONTAINING_RECORD(entry,IRP,Tail.Overlay.DeviceQueueEntry); + DeviceObject->DriverObject->DriverStartIo(DeviceObject,Irp); + } +} + +VOID IoStartNextPacket(PDEVICE_OBJECT DeviceObject, BOOLEAN Cancelable) +/* + * FUNCTION: Removes the next packet from the device's queue and calls + * the driver's StartIO + * ARGUMENTS: + * DeviceObject = Device + * Cancelable = True if irps in the queue can be canceled + */ +{ + PKDEVICE_QUEUE_ENTRY entry; + PIRP Irp; + KIRQL oldirql; + + entry = KeRemoveDeviceQueue(&DeviceObject->DeviceQueue); + + if (entry!=NULL) + { + Irp = CONTAINING_RECORD(entry,IRP,Tail.Overlay.DeviceQueueEntry); + DeviceObject->DriverObject->DriverStartIo(DeviceObject,Irp); + } + +} + +VOID IoStartPacket(PDEVICE_OBJECT DeviceObject, + PIRP Irp, PULONG Key, PDRIVER_CANCEL CancelFunction) +/* + * FUNCTION: Either call the device's StartIO routine with the packet or, + * if the device is busy, queue it. + * ARGUMENTS: + * DeviceObject = Device to start the packet on + * Irp = Irp to queue + * Key = Where to insert the irp + * If zero then insert in the tail of the queue + * CancelFunction = Optional function to cancel the irqp + */ +{ + BOOLEAN stat; + KIRQL oldirql; + + ASSERT_IRQL(DISPATCH_LEVEL); + + IoAcquireCancelSpinLock(&oldirql); + + if (CancelFunction != NULL) + { + Irp->CancelRoutine = CancelFunction; + } + + if (Key!=0) + { + stat = KeInsertByKeyDeviceQueue(&DeviceObject->DeviceQueue, + &Irp->Tail.Overlay.DeviceQueueEntry, + *Key); + } + else + { + stat = KeInsertDeviceQueue(&DeviceObject->DeviceQueue, + &Irp->Tail.Overlay.DeviceQueueEntry); + } + + IoReleaseCancelSpinLock(oldirql); + + if (!stat) + { + DeviceObject->DriverObject->DriverStartIo(DeviceObject,Irp); + } +} + + diff --git a/reactos/ntoskrnl/io/resource.c b/reactos/ntoskrnl/io/resource.c new file mode 100644 index 00000000000..c7dad78b4ae --- /dev/null +++ b/reactos/ntoskrnl/io/resource.c @@ -0,0 +1,59 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/resource.c + * PURPOSE: Hardware resource managment + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PCONFIGURATION_INFORMATION IoGetConfigurationInformation() +{ + UNIMPLEMENTED; +} + +NTSTATUS IoReportResourceUsage(PUNICODE_STRING DriverClassName, + PDRIVER_OBJECT DriverObject, + PCM_RESOURCE_LIST DriverList, + ULONG DriverListSize, + PDEVICE_OBJECT DeviceObject, + PCM_RESOURCE_LIST DeviceList, + ULONG DeviceListSize, + BOOLEAN OverrideConflict, + PBOOLEAN ConflictDetected) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoAssignResources(PUNICODE_STRING RegistryPath, + PUNICODE_STRING DriverClassName, + PDRIVER_OBJECT DriverObject, + PDEVICE_OBJECT DeviceObject, + PIO_RESOURCE_REQUIREMENTS_LIST RequestedResources, + PCM_RESOURCE_LIST* AllocatedResources) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoQueryDeviceDescription(PINTERFACE_TYPE BusType, + PULONG BusNumber, + PCONFIGURATION_TYPE ControllerType, + PULONG ControllerNumber, + PCONFIGURATION_TYPE PeripheralType, + PULONG PeripheralNumber, + PIO_QUERY_DEVICE_ROUTINE CalloutRoutine, + PVOID Context) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/rw.c b/reactos/ntoskrnl/io/rw.c new file mode 100644 index 00000000000..ac64be3b6f3 --- /dev/null +++ b/reactos/ntoskrnl/io/rw.c @@ -0,0 +1,228 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/rw.c + * PURPOSE: Implements read/write APIs + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 30/05/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include +#include + +//#define NDEBUG +#include + +#ifndef NDEBUG +#define DPRINT1(x) printk(x) +#else +#define DPRINT1(x) +#endif + +/* FUNCTIONS ***************************************************************/ + +NTSTATUS ZwReadFile(HANDLE FileHandle, + HANDLE Event, + PIO_APC_ROUTINE ApcRoutine, + PVOID ApcContext, + PIO_STATUS_BLOCK IoStatusBlock, + PVOID Buffer, + ULONG Length, + PLARGE_INTEGER ByteOffset, + PULONG Key) +{ + UNIMPLEMENTED; +} + +NTSTATUS ZwWriteFile(HANDLE FileHandle, + HANDLE Event, + PIO_APC_ROUTINE ApcRoutine, + PVOID ApcContext, + PIO_STATUS_BLOCK IoStatusBlock, + PVOID Buffer, + ULONG Length, + PLARGE_INTEGER ByteOffset, + PULONG Key) +{ + UNIMPLEMENTED; +} + +static BOOL WriteDevice(PDEVICE_OBJECT dev, LPVOID lpBuffer, + DWORD nNumberOfBytesToWrite, + LPDWORD lpNumberOfBytesWritten, + LPOVERLAPPED lpOverlapped) +{ + PDRIVER_OBJECT drv = dev->DriverObject; + PIRP irp; + PIO_STACK_LOCATION StackPtr; + + DPRINT("dev %x drv %x\n",dev,drv); + + /* + * Build an irp for the transfer + */ + irp = IoAllocateIrp(dev->StackSize,TRUE); + if (irp==NULL) + { + printk("Failed to allocate IRP\n"); + return(FALSE); + } + + /* + * Prepare the user buffer + */ + DPRINT1("Preparing user buffer\n"); + irp->UserBuffer = (LPVOID)lpBuffer; // This handles the 'neither' method + if (dev->Flags&DO_BUFFERED_IO) + { + DPRINT1("Doing buffer i/o\n"); + irp->AssociatedIrp.SystemBuffer = (PVOID) + ExAllocatePool(NonPagedPool,nNumberOfBytesToWrite); + if (irp->AssociatedIrp.SystemBuffer==NULL) + { + return(FALSE); + } + memcpy(irp->AssociatedIrp.SystemBuffer,lpBuffer,nNumberOfBytesToWrite); + irp->UserBuffer = NULL; + } + if (dev->Flags&DO_DIRECT_IO) + { + DPRINT1("Doing direct i/o\n"); + + irp->MdlAddress = MmCreateMdl(NULL,lpBuffer,nNumberOfBytesToWrite); + MmProbeAndLockPages(irp->MdlAddress,UserMode,IoWriteAccess); + irp->UserBuffer = NULL; + irp->AssociatedIrp.SystemBuffer = NULL; + } + + /* + * Set up the stack location + */ + StackPtr = IoGetNextIrpStackLocation(irp); + StackPtr->MajorFunction = IRP_MJ_WRITE; + StackPtr->MinorFunction = 0; + StackPtr->Flags = 0; + StackPtr->Control = 0; + StackPtr->DeviceObject = dev; + StackPtr->FileObject = NULL; + StackPtr->Parameters.Write.Length = nNumberOfBytesToWrite; + + DPRINT1("Sending IRP\n"); + IoCallDriver(dev,irp); + + + /* + * Free the above buffer + */ +} + +WINBOOL STDCALL WriteFile(HANDLE hFile, LPCVOID lpBuffer, + DWORD nNumberOfBytesToWrite, + LPDWORD lpNumberOfBytesWritten, + LPOVERLAPPED lpOverlapped) +{ + COMMON_BODY_HEADER* hdr = ObGetObjectByHandle(hFile); + + if (hdr->Type==OBJTYP_DEVICE) + { + return(WriteDevice(hdr,lpBuffer,nNumberOfBytesToWrite, + lpNumberOfBytesWritten,lpOverlapped)); + } + return(FALSE); +} + +static BOOL ReadDevice(PDEVICE_OBJECT dev, LPVOID lpBuffer, + DWORD nNumberOfBytesToWrite, + LPDWORD lpNumberOfBytesWritten, + LPOVERLAPPED lpOverlapped) +{ + PDRIVER_OBJECT drv = dev->DriverObject; + PIRP irp; + PIO_STACK_LOCATION StackPtr; + + DPRINT("dev %x drv %x\n",dev,drv); + + /* + * Build an irp for the transfer + */ + irp = IoAllocateIrp(dev->StackSize,TRUE); + if (irp==NULL) + { + printk("Failed to allocate IRP\n"); + return(FALSE); + } + + /* + * Prepare the user buffer + */ + DPRINT1("Preparing user buffer\n"); + irp->UserBuffer = (LPVOID)lpBuffer; // This handles the 'neither' method + if (dev->Flags&DO_BUFFERED_IO) + { + DPRINT1("Doing buffer i/o\n"); + irp->AssociatedIrp.SystemBuffer = (PVOID) + ExAllocatePool(NonPagedPool,nNumberOfBytesToWrite); + if (irp->AssociatedIrp.SystemBuffer==NULL) + { + return(FALSE); + } + memcpy(irp->AssociatedIrp.SystemBuffer,lpBuffer,nNumberOfBytesToWrite); + irp->UserBuffer = NULL; + } + if (dev->Flags&DO_DIRECT_IO) + { + DPRINT1("Doing direct i/o\n"); + + irp->MdlAddress = MmCreateMdl(NULL,lpBuffer,nNumberOfBytesToWrite); + MmProbeAndLockPages(irp->MdlAddress,UserMode,IoWriteAccess); + irp->UserBuffer = NULL; + irp->AssociatedIrp.SystemBuffer = NULL; + } + + /* + * Set up the stack location + */ + StackPtr = IoGetNextIrpStackLocation(irp); + StackPtr->MajorFunction = IRP_MJ_READ; + StackPtr->MinorFunction = 0; + StackPtr->Flags = 0; + StackPtr->Control = 0; + StackPtr->DeviceObject = dev; + StackPtr->FileObject = NULL; + StackPtr->Parameters.Write.Length = nNumberOfBytesToWrite; + + DPRINT1("Sending IRP\n"); + IoCallDriver(dev,irp); + + + /* + * Free the above buffer + */ + DPRINT1("Finished ReadDevice\n"); +} + + + +WINBOOL STDCALL ReadFile(HANDLE hFile, LPVOID lpBuffer, + DWORD nNumberOfBytesToWrite, + LPDWORD lpNumberOfBytesWritten, + LPOVERLAPPED lpOverlapped) +{ + COMMON_BODY_HEADER* hdr = ObGetObjectByHandle(hFile); + + if (hdr->Type==OBJTYP_DEVICE) + { + return(ReadDevice((PDEVICE_OBJECT)hdr,lpBuffer,nNumberOfBytesToWrite, + lpNumberOfBytesWritten,lpOverlapped)); + } + return(FALSE); +} + + diff --git a/reactos/ntoskrnl/io/share.c b/reactos/ntoskrnl/io/share.c new file mode 100644 index 00000000000..cb4ba94730b --- /dev/null +++ b/reactos/ntoskrnl/io/share.c @@ -0,0 +1,47 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID IoUpdateShareAccess(PFILE_OBJECT FileObject, PSHARE_ACCESS ShareAccess) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoCheckShareAccess(ACCESS_MASK DesiredAccess, + ULONG DesiredShareAccess, + PFILE_OBJECT FileObject, + PSHARE_ACCESS ShareAccess, + BOOLEAN Update) +{ + UNIMPLEMENTED; +} + +VOID IoRemoveShareAccess(PFILE_OBJECT FileObject, + PSHARE_ACCESS ShareAccess) +{ + UNIMPLEMENTED; +} + +VOID IoSetShareAccess(ACCESS_MASK DesiredAccess, + ULONG DesiredShareAccess, + PFILE_OBJECT FileObject, + PSHARE_ACCESS ShareAccess) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/shutdown.c b/reactos/ntoskrnl/io/shutdown.c new file mode 100644 index 00000000000..3214df76b83 --- /dev/null +++ b/reactos/ntoskrnl/io/shutdown.c @@ -0,0 +1,29 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/io/shutdown.c + * PURPOSE: Implements shutdown notification + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS IoRegisterShutdownNotification(PDEVICE_OBJECT DeviceObject) +{ + UNIMPLEMENTED; +} + +VOID IoUnregisterShutdownNotification(PDEVICE_OBJECT DeviceObject) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/symlink.c b/reactos/ntoskrnl/io/symlink.c new file mode 100644 index 00000000000..47132628b2e --- /dev/null +++ b/reactos/ntoskrnl/io/symlink.c @@ -0,0 +1,36 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/iomgr/symlink.c + * PURPOSE: Implements symbolic links + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS IoCreateUnprotectedSymbolicLink(PUNICODE_STRING SymbolicLinkName, + PUNICODE_STRING DeviceName) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoCreateSymbolicLink(PUNICODE_STRING SymbolicLinkName, + PUNICODE_STRING DeviceName) +{ + UNIMPLEMENTED; +} + +NTSTATUS IoDeleteSymbolicLink(PUNICODE_STRING DeviceName) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/io/timer.c b/reactos/ntoskrnl/io/timer.c new file mode 100644 index 00000000000..9376a2cb5df --- /dev/null +++ b/reactos/ntoskrnl/io/timer.c @@ -0,0 +1,66 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/iomgr/timer.c + * PURPOSE: IO timers + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS IoInitializeTimer(PDEVICE_OBJECT DeviceObject, + PIO_TIMER_ROUTINE TimerRoutine, + PVOID Context) +/* + * FUNCTION: Sets up a driver-supplied IoTimer routine associated with a given + * device object + * ARGUMENTS: + * DeviceObject = Device object whose timer is be initialized + * TimerRoutine = Driver supplied routine which will be called once per + * second if the timer is active + * Context = Driver supplied context to be passed to the TimerRoutine + * RETURNS: Status + */ +{ + DeviceObject->Timer = ExAllocatePool(NonPagedPool,sizeof(IO_TIMER)); + KeInitializeTimer(&(DeviceObject->Timer->timer)); + KeInitializeDpc(&(DeviceObject->Timer->dpc),TimerRoutine,Context); +} + +VOID IoStartTimer(PDEVICE_OBJECT DeviceObject) +/* + * FUNCTION: Starts a timer so the driver-supplied IoTimer routine will be + * called once per second + * ARGUMENTS: + * DeviceObject = Device whose timer is to be started + */ +{ + LARGE_INTEGER li; + + li.HighPart = -1; + li.LowPart = 10000000; + + KeSetTimerEx(&DeviceObject->Timer->timer,li,1000, + &(DeviceObject->Timer->dpc)); +} + +VOID IoStopTimer(PDEVICE_OBJECT DeviceObject) +/* + * FUNCTION: Disables for a specified device object so the driver-supplied + * IoTimer is not called + * ARGUMENTS: + * DeviceObject = Device whose timer is to be stopped + */ +{ + KeCancelTimer(&(DeviceObject->Timer->timer)); +} diff --git a/reactos/ntoskrnl/ke/apc.c b/reactos/ntoskrnl/ke/apc.c new file mode 100644 index 00000000000..1f21f37ba8d --- /dev/null +++ b/reactos/ntoskrnl/ke/apc.c @@ -0,0 +1,20 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ke/apc.c + * PURPOSE: Possible implementation of APCs + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + diff --git a/reactos/ntoskrnl/ke/bug.c b/reactos/ntoskrnl/ke/bug.c new file mode 100644 index 00000000000..fa0171ee776 --- /dev/null +++ b/reactos/ntoskrnl/ke/bug.c @@ -0,0 +1,83 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* GLOBALS ******************************************************************/ + +static LIST_ENTRY BugcheckCallbackListHead = {NULL,NULL}; + +/* FUNCTIONS *****************************************************************/ + +BOOLEAN KeDeregisterBugCheckCallback(PKBUGCHECK_CALLBACK_RECORD CallbackRecord) +{ + UNIMPLEMENTED; +} + +VOID KeInitializeBugCheck(VOID) +{ + InitializeListHead(&BugcheckCallbackListHead); +} + +VOID KeInitializeCallbackRecord(PKBUGCHECK_CALLBACK_RECORD CallbackRecord) +{ +} + +BOOLEAN KeRegisterBugCheckCallback(PKBUGCHECK_CALLBACK_RECORD CallbackRecord, + PKBUGCHECK_CALLBACK_ROUTINE CallbackRoutine, + PVOID Buffer, + ULONG Length, + PUCHAR Component) +{ + InsertTailList(&BugcheckCallbackListHead,&CallbackRecord->Entry); + CallbackRecord->Length=Length; + CallbackRecord->Buffer=Buffer; + CallbackRecord->Component=Component; + CallbackRecord->CallbackRoutine=CallbackRoutine; +} + +asmlinkage VOID KeBugCheckEx(ULONG BugCheckCode, + ULONG BugCheckParameter1, + ULONG BugCheckParameter2, + ULONG BugCheckParameter3, + ULONG BugCheckParameter4) +/* + * FUNCTION: Brings the system down in a controlled manner when an + * inconsistency that might otherwise cause corruption has been detected + * ARGUMENTS: + * BugCheckCode = Specifies the reason for the bug check + * BugCheckParameter[1-4] = Additional information about bug + * RETURNS: Doesn't + */ +{ + printk("Bug detected (code %x param %x %x %x %x)\n",BugCheckCode, + BugCheckParameter1,BugCheckParameter2,BugCheckParameter3, + BugCheckParameter4); + for(;;); +} + +asmlinkage VOID KeBugCheck(ULONG BugCheckCode) +/* + * FUNCTION: Brings the system down in a controlled manner when an + * inconsistency that might otherwise cause corruption has been detected + * ARGUMENTS: + * BugCheckCode = Specifies the reason for the bug check + * RETURNS: Doesn't + */ +{ + KeBugCheckEx(BugCheckCode,0,0,0,0); +} + diff --git a/reactos/ntoskrnl/ke/catch.c b/reactos/ntoskrnl/ke/catch.c new file mode 100644 index 00000000000..2e1d6950811 --- /dev/null +++ b/reactos/ntoskrnl/ke/catch.c @@ -0,0 +1,21 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/kernel/catch.c + * PURPOSE: Exception handling + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +/* FUNCTIONS ****************************************************************/ + +VOID ExRaiseStatus(NTSTATUS Status) +{ + printk("ExRaiseStatus(%d)\n",Status); + for(;;); +} diff --git a/reactos/ntoskrnl/ke/critical.c b/reactos/ntoskrnl/ke/critical.c new file mode 100644 index 00000000000..4916b8e8d97 --- /dev/null +++ b/reactos/ntoskrnl/ke/critical.c @@ -0,0 +1,29 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/critical.c + * PURPOSE: Implement critical regions + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID KeEnterCriticalRegion() +{ + UNIMPLEMENTED; +} + +VOID KeLeaveCriticalRegion() +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/ke/dispatch.c b/reactos/ntoskrnl/ke/dispatch.c new file mode 100644 index 00000000000..d061f100d8b --- /dev/null +++ b/reactos/ntoskrnl/ke/dispatch.c @@ -0,0 +1,26 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/kernel/dispatch.c + * PURPOSE: Handles a dispatch interrupt + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +/* FUNCTIONS ****************************************************************/ + +void KiDispatchInterrupt(unsigned int irq) +/* + * FUNCTION: Called after an irq when the interrupted processor was at a lower + * level than DISPATCH_LEVEL + */ +{ + KeExpireTimers(); + KeDrainDpcQueue(); + PsDispatchThread(); +} diff --git a/reactos/ntoskrnl/ke/dpc.c b/reactos/ntoskrnl/ke/dpc.c new file mode 100644 index 00000000000..81485b8f0d7 --- /dev/null +++ b/reactos/ntoskrnl/ke/dpc.c @@ -0,0 +1,114 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/kernel/dpc.cc + * PURPOSE: Handle DPCs (Delayed Procedure Calls) + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 28/05/98: Created + */ + +/* + * NOTE: See also the higher level support routines in mkernel/iomgr/iodpc.cc + */ + +/* INCLUDES ***************************************************************/ + +#include + +#include + +/* TYPES *******************************************************************/ + +/* GLOBALS ******************************************************************/ + +LIST_ENTRY DpcQueueHead; + +/* FUNCTIONS ****************************************************************/ + +VOID KeInitializeDpc(PKDPC Dpc, PKDEFERRED_ROUTINE DeferredRoutine, + PVOID DeferredContext) +/* + * FUNCTION: Initalizes a DPC + * ARGUMENTS: + * Dpc = Caller supplied DPC to be initialized + * DeferredRoutine = Associated DPC callback + * DeferredContext = Parameter to be passed to the callback + * NOTE: Callers must be running at IRQL PASSIVE_LEVEL + */ +{ + Dpc->Type=0; + Dpc->DeferredRoutine=DeferredRoutine; + Dpc->DeferredContext=DeferredContext; + Dpc->Lock=0; +} + +void KeDrainDpcQueue(void) +/* + * FUNCTION: Called to execute queued dpcs + */ +{ + PLIST_ENTRY current_entry = ExInterlockedRemoveHeadList(&DpcQueueHead,NULL); + PKDPC current = CONTAINING_RECORD(¤t_entry,KDPC,DpcListEntry); + + while (current_entry!=NULL) + { + current->DeferredRoutine(current,current->DeferredContext, + current->SystemArgument1, + current->SystemArgument2); + current_entry = ExInterlockedRemoveHeadList(&DpcQueueHead,NULL); + current = CONTAINING_RECORD(¤t_entry,KDPC,DpcListEntry); + } +} + +BOOLEAN KeRemoveQueueDpc(PKDPC Dpc) +/* + * FUNCTION: Removes DPC object from the system dpc queue + * ARGUMENTS: + * Dpc = DPC to remove + * RETURNS: TRUE if the DPC was in the queue + * FALSE otherwise + */ +{ + if (!Dpc->Lock) + { + return(FALSE); + } + ExInterlockedRemoveEntryList(&DpcQueueHead,&Dpc->DpcListEntry,NULL); + Dpc->Lock=0; +} + +BOOLEAN KeInsertQueueDpc(PKDPC dpc, PVOID SystemArgument1, + PVOID SystemArgument2) +/* + * FUNCTION: Queues a DPC for execution when the IRQL of a processor + * drops below DISPATCH_LEVEL + * ARGUMENTS: + * Dpc = Initalizes DPC + * SystemArguments[1-2] = Undocumented + * RETURNS: TRUE if the DPC object wasn't already in the queue + * FALSE otherwise + */ +{ + dpc->Number=0; + dpc->Importance=Medium; + dpc->SystemArgument1=SystemArgument1; + dpc->SystemArgument2=SystemArgument2; + if (dpc->Lock) + { + return(FALSE); + } + ExInterlockedInsertHeadList(&DpcQueueHead,&dpc->DpcListEntry,NULL); + dpc->Lock=1; + return(TRUE); +} + +void KeInitDpc(void) +/* + * FUNCTION: Initialize DPC handling + */ +{ + InitializeListHead(&DpcQueueHead); +} + + diff --git a/reactos/ntoskrnl/ke/error.c b/reactos/ntoskrnl/ke/error.c new file mode 100644 index 00000000000..c6d698f3ca1 --- /dev/null +++ b/reactos/ntoskrnl/ke/error.c @@ -0,0 +1,46 @@ +/* + * COPYRIGHT: See COPYING in the top directory + * PROJECT: ReactOS kernel v0.0.2 + * FILE: kernel/error.cc + * PURPOSE: Error reason setting/getting + * PROGRAMMER: David Welch + * UPDATE HISTORY: + * 16/4/98: Created + */ + +/* INCLUDE *****************************************************************/ + +#include + +/* GLOBALS *****************************************************************/ + +/* + * Last error code (this should be per process) + */ +DWORD error_code; + +/* FUNCTIONS ***************************************************************/ + +DWORD STDCALL GetLastError(VOID) +/* + * FUNCTION: Get the detailed error (if any) from the last function + * RECEIVES: Nothing + * RETURNS: + * The error code + */ +{ + return(error_code); +} + + +VOID STDCALL SetLastError(DWORD dwErrCode) +/* + * FUNCTION: Set the last error code + * RECEIVES: + * dwErrCode = the error code to set + * RETURNS: Nothing + */ +{ + error_code=dwErrCode; +} + diff --git a/reactos/ntoskrnl/ke/event.c b/reactos/ntoskrnl/ke/event.c new file mode 100644 index 00000000000..9bd1f98b5d0 --- /dev/null +++ b/reactos/ntoskrnl/ke/event.c @@ -0,0 +1,56 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ke/event.c + * PURPOSE: Implements event + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include + +#include + +#include + +/* FUNCTIONS ****************************************************************/ + +VOID KeClearEvent(PKEVENT Event) +{ + Event->Header.SignalState=FALSE; // (??) Is this atomic +} + +VOID KeInitializeEvent(PKEVENT Event, EVENT_TYPE Type, BOOLEAN State) +{ + Event->Header.Type = Type; + Event->Header.Absolute = 0; + Event->Header.Inserted = 0; + Event->Header.Size = sizeof(KEVENT) / sizeof(ULONG); + Event->Header.SignalState = State; + InitializeListHead(&(Event->Header.WaitListHead)); +} + +LONG KeReadStateEvent(PKEVENT Event) +{ + return(Event->Header.SignalState); +} + +LONG KeResetEvent(PKEVENT Event) +{ + return(InterlockedExchange(&(Event->Header.SignalState),0)); +} + +LONG KeSetEvent(PKEVENT Event, KPRIORITY Increment, BOOLEAN Wait) +{ + int ret; + KIRQL oldlvl; + + KeAcquireSpinLock(&DispatcherDatabaseLock,&oldlvl); + ret = InterlockedExchange(&(Event->Header.SignalState),1); + KeDispatcherObjectWake((DISPATCHER_HEADER *)Event); + KeReleaseSpinLock(&DispatcherDatabaseLock,oldlvl); +} diff --git a/reactos/ntoskrnl/ke/exports.c b/reactos/ntoskrnl/ke/exports.c new file mode 100644 index 00000000000..7bc5f6330b8 --- /dev/null +++ b/reactos/ntoskrnl/ke/exports.c @@ -0,0 +1,748 @@ +/* + * This file was machine generated by export + * Don't edit + * + * +*/ +#include +#ifdef __cplusplus +extern "C" { +#endif +void DbgPrint(void); +void printk(void); +void ExAcquireFastMutex(void); +void ExAcquireFastMutexUnsafe(void); +void ExAcquireResourceExclusive(void); +void ExAcquireResourceExclusiveLite(void); +void ExAcquireResourceSharedLite(void); +void ExAcquireSharedStarveExclusive(void); +void ExAcquireSharedWaitForExclusive(void); +void ExAllocateFromNPagedLookasideList(void); +void ExAllocateFromPagedLookasideList(void); +void ExAllocateFromZone(void); +void ExAllocatePool(void); +void ExAllocatePoolWithQuota(void); +void ExAllocatePoolWithQuotaTag(void); +void ExAllocatePoolWithTag(void); +void ExConvertExclusiveToSharedLite(void); +void ExDeleteNPagedLookasideList(void); +void ExDeletePagedLookasideList(void); +void ExDeleteResource(void); +void ExDeleteResourceLite(void); +void ExExtendZone(void); +void ExFreePool(void); +void ExFreeToNPagedLookasideList(void); +void ExFreeToPagedLookasideList(void); +void ExFreeToZone(void); +void ExGetCurrentResourceThread(void); +void ExGetExclusiveWaiterCount(void); +void ExGetSharedWaiterCount(void); +void ExHookException(void); +void ExInitializeFastMutex(void); +void ExInitializeNPagedLookasideList(void); +void ExInitializePagedLookasideList(void); +void ExInitializeResource(void); +void ExInitializeResourceLite(void); +void ExInitializeSListHead(void); +void ExInitializeWorkItem(void); +void ExInitializeZone(void); +void ExInterlockedAddLargeInteger(void); +void ExInterlockedAddUlong(void); +void ExInterlockedAllocateFromZone(void); +void ExInterlockedDecrementLong(void); +void ExInterlockedExchangeUlong(void); +void ExInterlockedExtendZone(void); +void ExInterlockedFreeToZone(void); +void ExInterlockedIncrementLong(void); +void ExInterlockedInsertHeadList(void); +void ExInterlockedInsertTailList(void); +void ExInterlockedPopEntryList(void); +void ExInterlockedPopEntrySList(void); +void ExInterlockedPushEntryList(void); +void ExInterlockedPushEntrySList(void); +void ExInterlockedRemoveHeadList(void); +void ExIsFullZone(void); +void ExIsObjectInFirstZoneSegment(void); +void ExIsResourceAcquiredExclusiveLite(void); +void ExIsResourceAcquiredSharedLite(void); +void ExLocalTimeToSystemTime(void); +void ExQueryDepthSListHead(void); +void ExQueueWorkItem(void); +void ExRaiseStatus(void); +void ExReinitializeResourceLite(void); +void ExReleaseFastMutex(void); +void ExReleaseFastMutexUnsafe(void); +void ExReleaseResource(void); +void ExReleaseResourceForThread(void); +void ExReleaseResourceForThreadLite(void); +void ExSystemTimeToLocalTime(void); +void ExTryToAcquireFastMutex(void); +void ExTryToAcquireResourceExclusiveLite(void); +void InterlockedCompareExchange(void); +void InterlockedExchange(void); +void InterlockedExchangeAdd(void); +void InterlockedIncrement(void); +void HalAllocateCommonBuffer(void); +void HalAssignSlotResources(void); +void HalExamineMBR(void); +void HalFreeCommonBuffer(void); +void HalGetAdapter(void); +void HalGetBusData(void); +void HalGetBusDataByOffset(void); +void HalGetDmaAlignmentRequirement(void); +void HalGetInterruptVector(void); +void HalQuerySystemInformation(void); +void HalReadDmaCounter(void); +void HalSetBusData(void); +void HalSetBusDataByOffset(void); +void HalTranslateBusAddress(void); +void IoAcquireCancelSpinLock(void); +void IoAllocateAdapterChannel(void); +void IoAllocateController(void); +void IoAllocateErrorLogEntry(void); +void IoAllocateIrp(void); +void IoAllocateMdl(void); +void IoAssignArcName(void); +void IoAssignResources(void); +void IoAttachDevice(void); +void IoAttachDeviceByPointer(void); +void IoAttachDeviceToDeviceStack(void); +void IoBuildAsynchronousFsdRequest(void); +void IoBuildDeviceIoControlRequest(void); +void IoBuildPartialMdl(void); +void IoBuildSynchronousFsdRequest(void); +void IoCallDriver(void); +void IoCancelIrp(void); +void IoCheckShareAccess(void); +void IoCompleteRequest(void); +void IoConnectInterrupt(void); +void IoCreateController(void); +void IoCreateDevice(void); +void IoCreateNotificationEvent(void); +void IoCreateSymbolicLink(void); +void IoCreateSynchronizationEvent(void); +void IoCreateUnprotectedSymbolicLink(void); +void IoDeassignArcName(void); +void IoDeleteController(void); +void IoDeleteDevice(void); +void IoDeleteSymbolicLink(void); +void IoDetachDevice(void); +void IoDisconnectInterrupt(void); +void IoFlushAdapterBuffers(void); +void IoFreeAdapterChannel(void); +void IoFreeController(void); +void IoFreeIrp(void); +void IoFreeMapRegisters(void); +void IoFreeMdl(void); +void IoGetConfigurationInformation(void); +void IoGetCurrentIrpStackLocation(void); +void IoGetCurrentProcess(void); +void IoGetDeviceObjectPointer(void); +void IoGetDeviceToVerify(void); +void IoGetFileObjectGenericMapping(void); +void IoGetFunctionCodeFromCtlCode(void); +void IoGetInitialStack(void); +void IoGetNextIrpStackLocation(void); +void IoGetRelatedDeviceObject(void); +void IoInitializeDpcRequest(void); +void IoInitializeIrp(void); +void IoInitializeTimer(void); +void IoIsErrorUserInduced(void); +void IoIsTotalDeviceFailure(void); +void IoMakeAssociatedIrp(void); +void IoMapTransfer(void); +void IoMarkIrpPending(void); +void IoQueryDeviceDescription(void); +void IoRaiseHardError(void); +void IoRaiseInformationalHardError(void); +void IoReadPartitionTable(void); +void IoRegisterDriverReinitialization(void); +void IoRegisterShutdownNotification(void); +void IoReleaseCancelSpinLock(void); +void IoRemoveShareAccess(void); +void IoReportResourceUsage(void); +void IoRequestDpc(void); +void IoSetCancelRoutine(void); +void IoSetCompletionRoutine(void); +void IoSetHardErrorOrVerifyDevice(void); +void IoSetNextIrpStackLocation(void); +void IoSetPartitionInformation(void); +void IoSetShareAccess(void); +void IoSizeOfIrp(void); +void IoStartNextPacket(void); +void IoStartNextPacketByKey(void); +void IoStartPacket(void); +void IoStartTimer(void); +void IoStopTimer(void); +void IoUnregisterShutdownNotification(void); +void IoUpdateShareAccess(void); +void IoWriteErrorLogEntry(void); +void IoWritePartitionTable(void); +void KeAcquireSpinLock(void); +void KeAcquireSpinLockAtDpcLevel(void); +void KeBugCheck(void); +void KeBugCheckEx(void); +void KeCancelTimer(void); +void KeClearEvent(void); +void KeDelayExecutionThread(void); +void KeDeregisterBugCheckCallback(void); +void KeEnterCriticalRegion(void); +void KeFlushIoBuffers(void); +void KeGetCurrentIrql(void); +void KeGetCurrentProcessorNumber(void); +void KeGetDcacheFillSize(void); +void KeInitializeCallbackRecord(void); +void KeInitializeDeviceQueue(void); +void KeInitializeDpc(void); +void KeInitializeEvent(void); +void KeInitializeMutex(void); +void KeInitializeSemaphore(void); +void KeInitializeSpinLock(void); +void KeInitializeTimer(void); +void KeInitializeTimerEx(void); +void KeInsertByKeyDeviceQueue(void); +void KeInsertDeviceQueue(void); +void KeInsertQueueDpc(void); +void KeLeaveCriticalRegion(void); +void KeLowerIrql(void); +void KeQueryPerformanceCounter(void); +void KeQuerySystemTime(void); +void KeQueryTickCount(void); +void KeQueryTimeIncrement(void); +void KeRaiseIrql(void); +void KeReadStateEvent(void); +void KeReadStateMutex(void); +void KeReadStateSemaphore(void); +void KeReadStateTimer(void); +void KeRegisterBugCheckCallback(void); +void KeReleaseMutex(void); +void KeReleaseSemaphore(void); +void KeReleaseSpinLock(void); +void KeReleaseSpinLockFromDpcLevel(void); +void KeRemoveByKeyDeviceQueue(void); +void KeRemoveDeviceQueue(void); +void KeRemoveQueueDpc(void); +void KeResetEvent(void); +void KeSetBasePriorityThread(void); +void KeSetEvent(void); +void KeSetPriorityThread(void); +void KeSetTimer(void); +void KeSetTimerEx(void); +void KeStallExecutionProcessor(void); +void KeSynchronizeExecution(void); +void KeWaitForMultipleObjects(void); +void KeWaitForMutexObject(void); +void KeWaitForSingleObject(void); +void MmAllocateContiguousMemory(void); +void MmAllocateNonCachedMemory(void); +void MmBuildMdlForNonPagedPool(void); +void MmCreateMdl(void); +void MmFreeContiguousMemory(void); +void MmFreeNonCachedMemory(void); +void MmGetMdlByteCount(void); +void MmGetMdlByteOffset(void); +void MmGetMdlVirtualAddress(void); +void MmGetPhysicalAddress(void); +void MmGetSystemAddressForMdl(void); +void MmInitializeMdl(void); +void MmIsAddressValid(void); +void MmIsNonPagedSystemAddressValid(void); +void MmIsThisAnNtAsSystem(void); +void MmLockPagableCodeSection(void); +void MmLockPagableDataSection(void); +void MmLockPagableSectionByHandle(void); +void MmMapIoSpace(void); +void MmMapLockedPages(void); +void MmPageEntireDriver(void); +void MmResetDriverPaging(void); +void MmPrepareMdlForReuse(void); +void MmProbeAndLockPages(void); +void MmQuerySystemSize(void); +void MmSizeOfMdl(void); +void MmUnlockPages(void); +void MmUnlockPagableImageSection(void); +void MmUnmapIoSpace(void); +void MmUnmapLockedPages(void); +void ObDereferenceObject(void); +void ObReferenceObjectByHandle(void); +void ObReferenceObjectByPointer(void); +void PsCreateSystemThread(void); +void PsGetCurrentProcess(void); +void PsGetCurrentThread(void); +void PsTerminateSystemThread(void); +void InitializeListHead(void); +void InitializeObjectAttributes(void); +void InsertHeadList(void); +void InsertTailList(void); +void PopEntryList(void); +void PushEntryList(void); +void RemoveEntryList(void); +void RemoveHeadList(void); +void RemoveTailList(void); +void RtlAnsiStringToUnicodeSize(void); +void RtlAnsiStringToUnicodeString(void); +void RtlAppendUnicodeStringToString(void); +void RtlAppendUnicodeToString(void); +void RtlCharToInteger(void); +void RtlCheckRegistryKey(void); +void RtlCompareMemory(void); +void RtlCompareString(void); +void RtlCompareUnicodeString(void); +void RtlConvertLongToLargeInteger(void); +void RtlConvertUlongToLargeInteger(void); +void RtlCopyBytes(void); +void RtlCopyMemory(void); +void RtlCopyString(void); +void RtlCopyUnicodeString(void); +void RtlCreateRegistryKey(void); +void RtlCreateSecurityDescriptor(void); +void RtlDeleteRegistryValue(void); +void RtlEnlargedIntegerMultiply(void); +void RtlEnlargedUnsignedDivide(void); +void RtlEnlargedUnsignedMultiply(void); +void RtlEqualString(void); +void RtlEqualUnicodeString(void); +void RtlExtendedIntegerMultiply(void); +void RtlExtendedLargeIntegerDivide(void); +void RtlExtendedMagicDivide(void); +void RtlFillMemory(void); +void RtlFreeAnsiString(void); +void RtlFreeUnicodeString(void); +void RtlInitAnsiString(void); +void RtlInitString(void); +void RtlInitUnicodeString(void); +void RtlIntegerToUnicodeString(void); +void RtlLargeIntegerAdd(void); +void RtlLargeIntegerAnd(void); +void RtlLargeIntegerArithmeticShift(void); +void RtlLargeIntegerDivide(void); +void RtlLargeIntegerEqualTo(void); +void RtlLargeIntegerEqualToZero(void); +void RtlLargeIntegerGreaterThan(void); +void RtlLargeIntegerGreaterThanOrEqualTo(void); +void RtlLargeIntegerGreaterThanOrEqualToZero(void); +void RtlLargeIntegerGreaterThanZero(void); +void RtlLargeIntegerLessThan(void); +void RtlLargeIntegerLessThanOrEqualTo(void); +void RtlLargeIntegerLessThanZero(void); +void RtlLargeIntegerNegate(void); +void RtlLargeIntegerNotEqualTo(void); +void RtlLargeIntegerShiftLeft(void); +void RtlLargeIntegerShiftRight(void); +void RtlLargeIntegerSubtract(void); +void RtlLengthSecurityDescriptor(void); +void RtlMoveMemory(void); +void RtlQueryRegistryValues(void); +void RtlRetrieveUlong(void); +void RtlRetrieveUshort(void); +void RtlSetDaclSecurityDescriptor(void); +void RtlStoreUlong(void); +void RtlStoreUshort(void); +void RtlTimeFieldsToTime(void); +void RtlTimeToTimeFields(void); +void RtlUnicodeStringToAnsiString(void); +void RtlUnicodeStringToInteger(void); +void RtlUpcaseUnicodeString(void); +void RtlUpperString(void); +void RtlValidSecurityDescriptor(void); +void RtlWriteRegistryValue(void); +void RtlZeroMemory(void); +void SeAccessCheck(void); +void SeAssignSecurity(void); +void SeDeassignSecurity(void); +void SeSinglePrivilegeCheck(void); +void ZwClose(void); +void ZwCreateDirectoryObject(void); +void ZwCreateFile(void); +void ZwCreateKey(void); +void ZwDeleteKey(void); +void ZwEnumerateKey(void); +void ZwEnumerateValueKey(void); +void ZwFlushKey(void); +void ZwMakeTemporaryObject(void); +void ZwMapViewOfSection(void); +void ZwOpenFile(void); +void ZwOpenKey(void); +void ZwOpenSection(void); +void ZwQueryInformationFile(void); +void ZwQueryKey(void); +void ZwQueryValueKey(void); +void ZwReadFile(void); +void ZwSetInformationFile(void); +void ZwSetInformationThread(void); +void ZwSetValueKey(void); +void ZwUnmapViewOfSection(void); +void ZwWriteFile(void); +void sprintf(void); +#ifdef __cplusplus +} +#endif +export symbol_table[]={ +{"_DbgPrint",(unsigned int)DbgPrint}, +{"_printk",(unsigned int)printk}, +{"_ExAcquireFastMutex",(unsigned int)ExAcquireFastMutex}, +{"_ExAcquireFastMutexUnsafe",(unsigned int)ExAcquireFastMutexUnsafe}, +{"_ExAcquireResourceExclusive",(unsigned int)ExAcquireResourceExclusive}, +{"_ExAcquireResourceExclusiveLite",(unsigned int)ExAcquireResourceExclusiveLite}, +{"_ExAcquireResourceSharedLite",(unsigned int)ExAcquireResourceSharedLite}, +{"_ExAcquireSharedStarveExclusive",(unsigned int)ExAcquireSharedStarveExclusive}, +{"_ExAcquireSharedWaitForExclusive",(unsigned int)ExAcquireSharedWaitForExclusive}, +{"_ExAllocateFromNPagedLookasideList",(unsigned int)ExAllocateFromNPagedLookasideList}, +{"_ExAllocateFromPagedLookasideList",(unsigned int)ExAllocateFromPagedLookasideList}, +{"_ExAllocateFromZone",(unsigned int)ExAllocateFromZone}, +{"_ExAllocatePool",(unsigned int)ExAllocatePool}, +{"_ExAllocatePoolWithQuota",(unsigned int)ExAllocatePoolWithQuota}, +{"_ExAllocatePoolWithQuotaTag",(unsigned int)ExAllocatePoolWithQuotaTag}, +{"_ExAllocatePoolWithTag",(unsigned int)ExAllocatePoolWithTag}, +{"_ExConvertExclusiveToSharedLite",(unsigned int)ExConvertExclusiveToSharedLite}, +{"_ExDeleteNPagedLookasideList",(unsigned int)ExDeleteNPagedLookasideList}, +{"_ExDeletePagedLookasideList",(unsigned int)ExDeletePagedLookasideList}, +{"_ExDeleteResource",(unsigned int)ExDeleteResource}, +{"_ExDeleteResourceLite",(unsigned int)ExDeleteResourceLite}, +{"_ExExtendZone",(unsigned int)ExExtendZone}, +{"_ExFreePool",(unsigned int)ExFreePool}, +{"_ExFreeToNPagedLookasideList",(unsigned int)ExFreeToNPagedLookasideList}, +{"_ExFreeToPagedLookasideList",(unsigned int)ExFreeToPagedLookasideList}, +{"_ExFreeToZone",(unsigned int)ExFreeToZone}, +{"_ExGetCurrentResourceThread",(unsigned int)ExGetCurrentResourceThread}, +{"_ExGetExclusiveWaiterCount",(unsigned int)ExGetExclusiveWaiterCount}, +{"_ExGetSharedWaiterCount",(unsigned int)ExGetSharedWaiterCount}, +{"_ExHookException",(unsigned int)ExHookException}, +{"_ExInitializeFastMutex",(unsigned int)ExInitializeFastMutex}, +{"_ExInitializeNPagedLookasideList",(unsigned int)ExInitializeNPagedLookasideList}, +{"_ExInitializePagedLookasideList",(unsigned int)ExInitializePagedLookasideList}, +{"_ExInitializeResource",(unsigned int)ExInitializeResource}, +{"_ExInitializeResourceLite",(unsigned int)ExInitializeResourceLite}, +{"_ExInitializeSListHead",(unsigned int)ExInitializeSListHead}, +{"_ExInitializeWorkItem",(unsigned int)ExInitializeWorkItem}, +{"_ExInitializeZone",(unsigned int)ExInitializeZone}, +{"_ExInterlockedAddLargeInteger",(unsigned int)ExInterlockedAddLargeInteger}, +{"_ExInterlockedAddUlong",(unsigned int)ExInterlockedAddUlong}, +{"_ExInterlockedAllocateFromZone",(unsigned int)ExInterlockedAllocateFromZone}, +{"_ExInterlockedDecrementLong",(unsigned int)ExInterlockedDecrementLong}, +{"_ExInterlockedExchangeUlong",(unsigned int)ExInterlockedExchangeUlong}, +{"_ExInterlockedExtendZone",(unsigned int)ExInterlockedExtendZone}, +{"_ExInterlockedFreeToZone",(unsigned int)ExInterlockedFreeToZone}, +{"_ExInterlockedIncrementLong",(unsigned int)ExInterlockedIncrementLong}, +{"_ExInterlockedInsertHeadList",(unsigned int)ExInterlockedInsertHeadList}, +{"_ExInterlockedInsertTailList",(unsigned int)ExInterlockedInsertTailList}, +{"_ExInterlockedPopEntryList",(unsigned int)ExInterlockedPopEntryList}, +{"_ExInterlockedPopEntrySList",(unsigned int)ExInterlockedPopEntrySList}, +{"_ExInterlockedPushEntryList",(unsigned int)ExInterlockedPushEntryList}, +{"_ExInterlockedPushEntrySList",(unsigned int)ExInterlockedPushEntrySList}, +{"_ExInterlockedRemoveHeadList",(unsigned int)ExInterlockedRemoveHeadList}, +{"_ExIsFullZone",(unsigned int)ExIsFullZone}, +{"_ExIsObjectInFirstZoneSegment",(unsigned int)ExIsObjectInFirstZoneSegment}, +{"_ExIsResourceAcquiredExclusiveLite",(unsigned int)ExIsResourceAcquiredExclusiveLite}, +{"_ExIsResourceAcquiredSharedLite",(unsigned int)ExIsResourceAcquiredSharedLite}, +{"_ExLocalTimeToSystemTime",(unsigned int)ExLocalTimeToSystemTime}, +{"_ExQueryDepthSListHead",(unsigned int)ExQueryDepthSListHead}, +{"_ExQueueWorkItem",(unsigned int)ExQueueWorkItem}, +{"_ExRaiseStatus",(unsigned int)ExRaiseStatus}, +{"_ExReinitializeResourceLite",(unsigned int)ExReinitializeResourceLite}, +{"_ExReleaseFastMutex",(unsigned int)ExReleaseFastMutex}, +{"_ExReleaseFastMutexUnsafe",(unsigned int)ExReleaseFastMutexUnsafe}, +{"_ExReleaseResource",(unsigned int)ExReleaseResource}, +{"_ExReleaseResourceForThread",(unsigned int)ExReleaseResourceForThread}, +{"_ExReleaseResourceForThreadLite",(unsigned int)ExReleaseResourceForThreadLite}, +{"_ExSystemTimeToLocalTime",(unsigned int)ExSystemTimeToLocalTime}, +{"_ExTryToAcquireFastMutex",(unsigned int)ExTryToAcquireFastMutex}, +{"_ExTryToAcquireResourceExclusiveLite",(unsigned int)ExTryToAcquireResourceExclusiveLite}, +{"_InterlockedCompareExchange",(unsigned int)InterlockedCompareExchange}, +{"_InterlockedExchange",(unsigned int)InterlockedExchange}, +{"_InterlockedExchangeAdd",(unsigned int)InterlockedExchangeAdd}, +{"_InterlockedIncrement",(unsigned int)InterlockedIncrement}, +{"_HalAllocateCommonBuffer",(unsigned int)HalAllocateCommonBuffer}, +{"_HalAssignSlotResources",(unsigned int)HalAssignSlotResources}, +{"_HalExamineMBR",(unsigned int)HalExamineMBR}, +{"_HalFreeCommonBuffer",(unsigned int)HalFreeCommonBuffer}, +{"_HalGetAdapter",(unsigned int)HalGetAdapter}, +{"_HalGetBusData",(unsigned int)HalGetBusData}, +{"_HalGetBusDataByOffset",(unsigned int)HalGetBusDataByOffset}, +{"_HalGetDmaAlignmentRequirement",(unsigned int)HalGetDmaAlignmentRequirement}, +{"_HalGetInterruptVector",(unsigned int)HalGetInterruptVector}, +{"_HalQuerySystemInformation",(unsigned int)HalQuerySystemInformation}, +{"_HalReadDmaCounter",(unsigned int)HalReadDmaCounter}, +{"_HalSetBusData",(unsigned int)HalSetBusData}, +{"_HalSetBusDataByOffset",(unsigned int)HalSetBusDataByOffset}, +{"_HalTranslateBusAddress",(unsigned int)HalTranslateBusAddress}, +{"_IoAcquireCancelSpinLock",(unsigned int)IoAcquireCancelSpinLock}, +{"_IoAllocateAdapterChannel",(unsigned int)IoAllocateAdapterChannel}, +{"_IoAllocateController",(unsigned int)IoAllocateController}, +{"_IoAllocateErrorLogEntry",(unsigned int)IoAllocateErrorLogEntry}, +{"_IoAllocateIrp",(unsigned int)IoAllocateIrp}, +{"_IoAllocateMdl",(unsigned int)IoAllocateMdl}, +{"_IoAssignArcName",(unsigned int)IoAssignArcName}, +{"_IoAssignResources",(unsigned int)IoAssignResources}, +{"_IoAttachDevice",(unsigned int)IoAttachDevice}, +{"_IoAttachDeviceByPointer",(unsigned int)IoAttachDeviceByPointer}, +{"_IoAttachDeviceToDeviceStack",(unsigned int)IoAttachDeviceToDeviceStack}, +{"_IoBuildAsynchronousFsdRequest",(unsigned int)IoBuildAsynchronousFsdRequest}, +{"_IoBuildDeviceIoControlRequest",(unsigned int)IoBuildDeviceIoControlRequest}, +{"_IoBuildPartialMdl",(unsigned int)IoBuildPartialMdl}, +{"_IoBuildSynchronousFsdRequest",(unsigned int)IoBuildSynchronousFsdRequest}, +{"_IoCallDriver",(unsigned int)IoCallDriver}, +{"_IoCancelIrp",(unsigned int)IoCancelIrp}, +{"_IoCheckShareAccess",(unsigned int)IoCheckShareAccess}, +{"_IoCompleteRequest",(unsigned int)IoCompleteRequest}, +{"_IoConnectInterrupt",(unsigned int)IoConnectInterrupt}, +{"_IoCreateController",(unsigned int)IoCreateController}, +{"_IoCreateDevice",(unsigned int)IoCreateDevice}, +{"_IoCreateNotificationEvent",(unsigned int)IoCreateNotificationEvent}, +{"_IoCreateSymbolicLink",(unsigned int)IoCreateSymbolicLink}, +{"_IoCreateSynchronizationEvent",(unsigned int)IoCreateSynchronizationEvent}, +{"_IoCreateUnprotectedSymbolicLink",(unsigned int)IoCreateUnprotectedSymbolicLink}, +{"_IoDeassignArcName",(unsigned int)IoDeassignArcName}, +{"_IoDeleteController",(unsigned int)IoDeleteController}, +{"_IoDeleteDevice",(unsigned int)IoDeleteDevice}, +{"_IoDeleteSymbolicLink",(unsigned int)IoDeleteSymbolicLink}, +{"_IoDetachDevice",(unsigned int)IoDetachDevice}, +{"_IoDisconnectInterrupt",(unsigned int)IoDisconnectInterrupt}, +{"_IoFlushAdapterBuffers",(unsigned int)IoFlushAdapterBuffers}, +{"_IoFreeAdapterChannel",(unsigned int)IoFreeAdapterChannel}, +{"_IoFreeController",(unsigned int)IoFreeController}, +{"_IoFreeIrp",(unsigned int)IoFreeIrp}, +{"_IoFreeMapRegisters",(unsigned int)IoFreeMapRegisters}, +{"_IoFreeMdl",(unsigned int)IoFreeMdl}, +{"_IoGetConfigurationInformation",(unsigned int)IoGetConfigurationInformation}, +{"_IoGetCurrentIrpStackLocation",(unsigned int)IoGetCurrentIrpStackLocation}, +{"_IoGetCurrentProcess",(unsigned int)IoGetCurrentProcess}, +{"_IoGetDeviceObjectPointer",(unsigned int)IoGetDeviceObjectPointer}, +{"_IoGetDeviceToVerify",(unsigned int)IoGetDeviceToVerify}, +{"_IoGetFileObjectGenericMapping",(unsigned int)IoGetFileObjectGenericMapping}, +{"_IoGetFunctionCodeFromCtlCode",(unsigned int)IoGetFunctionCodeFromCtlCode}, +{"_IoGetInitialStack",(unsigned int)IoGetInitialStack}, +{"_IoGetNextIrpStackLocation",(unsigned int)IoGetNextIrpStackLocation}, +{"_IoGetRelatedDeviceObject",(unsigned int)IoGetRelatedDeviceObject}, +{"_IoInitializeDpcRequest",(unsigned int)IoInitializeDpcRequest}, +{"_IoInitializeIrp",(unsigned int)IoInitializeIrp}, +{"_IoInitializeTimer",(unsigned int)IoInitializeTimer}, +{"_IoIsErrorUserInduced",(unsigned int)IoIsErrorUserInduced}, +{"_IoIsTotalDeviceFailure",(unsigned int)IoIsTotalDeviceFailure}, +{"_IoMakeAssociatedIrp",(unsigned int)IoMakeAssociatedIrp}, +{"_IoMapTransfer",(unsigned int)IoMapTransfer}, +{"_IoMarkIrpPending",(unsigned int)IoMarkIrpPending}, +{"_IoQueryDeviceDescription",(unsigned int)IoQueryDeviceDescription}, +{"_IoRaiseHardError",(unsigned int)IoRaiseHardError}, +{"_IoRaiseInformationalHardError",(unsigned int)IoRaiseInformationalHardError}, +{"_IoReadPartitionTable",(unsigned int)IoReadPartitionTable}, +{"_IoRegisterDriverReinitialization",(unsigned int)IoRegisterDriverReinitialization}, +{"_IoRegisterShutdownNotification",(unsigned int)IoRegisterShutdownNotification}, +{"_IoReleaseCancelSpinLock",(unsigned int)IoReleaseCancelSpinLock}, +{"_IoRemoveShareAccess",(unsigned int)IoRemoveShareAccess}, +{"_IoReportResourceUsage",(unsigned int)IoReportResourceUsage}, +{"_IoRequestDpc",(unsigned int)IoRequestDpc}, +{"_IoSetCancelRoutine",(unsigned int)IoSetCancelRoutine}, +{"_IoSetCompletionRoutine",(unsigned int)IoSetCompletionRoutine}, +{"_IoSetHardErrorOrVerifyDevice",(unsigned int)IoSetHardErrorOrVerifyDevice}, +{"_IoSetNextIrpStackLocation",(unsigned int)IoSetNextIrpStackLocation}, +{"_IoSetPartitionInformation",(unsigned int)IoSetPartitionInformation}, +{"_IoSetShareAccess",(unsigned int)IoSetShareAccess}, +{"_IoSizeOfIrp",(unsigned int)IoSizeOfIrp}, +{"_IoStartNextPacket",(unsigned int)IoStartNextPacket}, +{"_IoStartNextPacketByKey",(unsigned int)IoStartNextPacketByKey}, +{"_IoStartPacket",(unsigned int)IoStartPacket}, +{"_IoStartTimer",(unsigned int)IoStartTimer}, +{"_IoStopTimer",(unsigned int)IoStopTimer}, +{"_IoUnregisterShutdownNotification",(unsigned int)IoUnregisterShutdownNotification}, +{"_IoUpdateShareAccess",(unsigned int)IoUpdateShareAccess}, +{"_IoWriteErrorLogEntry",(unsigned int)IoWriteErrorLogEntry}, +{"_IoWritePartitionTable",(unsigned int)IoWritePartitionTable}, +{"_KeAcquireSpinLock",(unsigned int)KeAcquireSpinLock}, +{"_KeAcquireSpinLockAtDpcLevel",(unsigned int)KeAcquireSpinLockAtDpcLevel}, +{"_KeBugCheck",(unsigned int)KeBugCheck}, +{"_KeBugCheckEx",(unsigned int)KeBugCheckEx}, +{"_KeCancelTimer",(unsigned int)KeCancelTimer}, +{"_KeClearEvent",(unsigned int)KeClearEvent}, +{"_KeDelayExecutionThread",(unsigned int)KeDelayExecutionThread}, +{"_KeDeregisterBugCheckCallback",(unsigned int)KeDeregisterBugCheckCallback}, +{"_KeEnterCriticalRegion",(unsigned int)KeEnterCriticalRegion}, +{"_KeFlushIoBuffers",(unsigned int)KeFlushIoBuffers}, +{"_KeGetCurrentIrql",(unsigned int)KeGetCurrentIrql}, +{"_KeGetCurrentProcessorNumber",(unsigned int)KeGetCurrentProcessorNumber}, +{"_KeGetDcacheFillSize",(unsigned int)KeGetDcacheFillSize}, +{"_KeInitializeCallbackRecord",(unsigned int)KeInitializeCallbackRecord}, +{"_KeInitializeDeviceQueue",(unsigned int)KeInitializeDeviceQueue}, +{"_KeInitializeDpc",(unsigned int)KeInitializeDpc}, +{"_KeInitializeEvent",(unsigned int)KeInitializeEvent}, +{"_KeInitializeMutex",(unsigned int)KeInitializeMutex}, +{"_KeInitializeSemaphore",(unsigned int)KeInitializeSemaphore}, +{"_KeInitializeSpinLock",(unsigned int)KeInitializeSpinLock}, +{"_KeInitializeTimer",(unsigned int)KeInitializeTimer}, +{"_KeInitializeTimerEx",(unsigned int)KeInitializeTimerEx}, +{"_KeInsertByKeyDeviceQueue",(unsigned int)KeInsertByKeyDeviceQueue}, +{"_KeInsertDeviceQueue",(unsigned int)KeInsertDeviceQueue}, +{"_KeInsertQueueDpc",(unsigned int)KeInsertQueueDpc}, +{"_KeLeaveCriticalRegion",(unsigned int)KeLeaveCriticalRegion}, +{"_KeLowerIrql",(unsigned int)KeLowerIrql}, +{"_KeQueryPerformanceCounter",(unsigned int)KeQueryPerformanceCounter}, +{"_KeQuerySystemTime",(unsigned int)KeQuerySystemTime}, +{"_KeQueryTickCount",(unsigned int)KeQueryTickCount}, +{"_KeQueryTimeIncrement",(unsigned int)KeQueryTimeIncrement}, +{"_KeRaiseIrql",(unsigned int)KeRaiseIrql}, +{"_KeReadStateEvent",(unsigned int)KeReadStateEvent}, +{"_KeReadStateMutex",(unsigned int)KeReadStateMutex}, +{"_KeReadStateSemaphore",(unsigned int)KeReadStateSemaphore}, +{"_KeReadStateTimer",(unsigned int)KeReadStateTimer}, +{"_KeRegisterBugCheckCallback",(unsigned int)KeRegisterBugCheckCallback}, +{"_KeReleaseMutex",(unsigned int)KeReleaseMutex}, +{"_KeReleaseSemaphore",(unsigned int)KeReleaseSemaphore}, +{"_KeReleaseSpinLock",(unsigned int)KeReleaseSpinLock}, +{"_KeReleaseSpinLockFromDpcLevel",(unsigned int)KeReleaseSpinLockFromDpcLevel}, +{"_KeRemoveByKeyDeviceQueue",(unsigned int)KeRemoveByKeyDeviceQueue}, +{"_KeRemoveDeviceQueue",(unsigned int)KeRemoveDeviceQueue}, +{"_KeRemoveQueueDpc",(unsigned int)KeRemoveQueueDpc}, +{"_KeResetEvent",(unsigned int)KeResetEvent}, +{"_KeSetBasePriorityThread",(unsigned int)KeSetBasePriorityThread}, +{"_KeSetEvent",(unsigned int)KeSetEvent}, +{"_KeSetPriorityThread",(unsigned int)KeSetPriorityThread}, +{"_KeSetTimer",(unsigned int)KeSetTimer}, +{"_KeSetTimerEx",(unsigned int)KeSetTimerEx}, +{"_KeStallExecutionProcessor",(unsigned int)KeStallExecutionProcessor}, +{"_KeSynchronizeExecution",(unsigned int)KeSynchronizeExecution}, +{"_KeWaitForMultipleObjects",(unsigned int)KeWaitForMultipleObjects}, +{"_KeWaitForMutexObject",(unsigned int)KeWaitForMutexObject}, +{"_KeWaitForSingleObject",(unsigned int)KeWaitForSingleObject}, +{"_MmAllocateContiguousMemory",(unsigned int)MmAllocateContiguousMemory}, +{"_MmAllocateNonCachedMemory",(unsigned int)MmAllocateNonCachedMemory}, +{"_MmBuildMdlForNonPagedPool",(unsigned int)MmBuildMdlForNonPagedPool}, +{"_MmCreateMdl",(unsigned int)MmCreateMdl}, +{"_MmFreeContiguousMemory",(unsigned int)MmFreeContiguousMemory}, +{"_MmFreeNonCachedMemory",(unsigned int)MmFreeNonCachedMemory}, +{"_MmGetMdlByteCount",(unsigned int)MmGetMdlByteCount}, +{"_MmGetMdlByteOffset",(unsigned int)MmGetMdlByteOffset}, +{"_MmGetMdlVirtualAddress",(unsigned int)MmGetMdlVirtualAddress}, +{"_MmGetPhysicalAddress",(unsigned int)MmGetPhysicalAddress}, +{"_MmGetSystemAddressForMdl",(unsigned int)MmGetSystemAddressForMdl}, +{"_MmInitializeMdl",(unsigned int)MmInitializeMdl}, +{"_MmIsAddressValid",(unsigned int)MmIsAddressValid}, +{"_MmIsNonPagedSystemAddressValid",(unsigned int)MmIsNonPagedSystemAddressValid}, +{"_MmIsThisAnNtAsSystem",(unsigned int)MmIsThisAnNtAsSystem}, +{"_MmLockPagableCodeSection",(unsigned int)MmLockPagableCodeSection}, +{"_MmLockPagableDataSection",(unsigned int)MmLockPagableDataSection}, +{"_MmLockPagableSectionByHandle",(unsigned int)MmLockPagableSectionByHandle}, +{"_MmMapIoSpace",(unsigned int)MmMapIoSpace}, +{"_MmMapLockedPages",(unsigned int)MmMapLockedPages}, +{"_MmPageEntireDriver",(unsigned int)MmPageEntireDriver}, +{"_MmResetDriverPaging",(unsigned int)MmResetDriverPaging}, +{"_MmPrepareMdlForReuse",(unsigned int)MmPrepareMdlForReuse}, +{"_MmProbeAndLockPages",(unsigned int)MmProbeAndLockPages}, +{"_MmQuerySystemSize",(unsigned int)MmQuerySystemSize}, +{"_MmSizeOfMdl",(unsigned int)MmSizeOfMdl}, +{"_MmUnlockPages",(unsigned int)MmUnlockPages}, +{"_MmUnlockPagableImageSection",(unsigned int)MmUnlockPagableImageSection}, +{"_MmUnmapIoSpace",(unsigned int)MmUnmapIoSpace}, +{"_MmUnmapLockedPages",(unsigned int)MmUnmapLockedPages}, +{"_ObDereferenceObject",(unsigned int)ObDereferenceObject}, +{"_ObReferenceObjectByHandle",(unsigned int)ObReferenceObjectByHandle}, +{"_ObReferenceObjectByPointer",(unsigned int)ObReferenceObjectByPointer}, +{"_PsCreateSystemThread",(unsigned int)PsCreateSystemThread}, +{"_PsGetCurrentProcess",(unsigned int)PsGetCurrentProcess}, +{"_PsGetCurrentThread",(unsigned int)PsGetCurrentThread}, +{"_PsTerminateSystemThread",(unsigned int)PsTerminateSystemThread}, +{"_InitializeListHead",(unsigned int)InitializeListHead}, +{"_InitializeObjectAttributes",(unsigned int)InitializeObjectAttributes}, +{"_InsertHeadList",(unsigned int)InsertHeadList}, +{"_InsertTailList",(unsigned int)InsertTailList}, +{"_PopEntryList",(unsigned int)PopEntryList}, +{"_PushEntryList",(unsigned int)PushEntryList}, +{"_RemoveEntryList",(unsigned int)RemoveEntryList}, +{"_RemoveHeadList",(unsigned int)RemoveHeadList}, +{"_RemoveTailList",(unsigned int)RemoveTailList}, +{"_RtlAnsiStringToUnicodeSize",(unsigned int)RtlAnsiStringToUnicodeSize}, +{"_RtlAnsiStringToUnicodeString",(unsigned int)RtlAnsiStringToUnicodeString}, +{"_RtlAppendUnicodeStringToString",(unsigned int)RtlAppendUnicodeStringToString}, +{"_RtlAppendUnicodeToString",(unsigned int)RtlAppendUnicodeToString}, +{"_RtlCharToInteger",(unsigned int)RtlCharToInteger}, +{"_RtlCheckRegistryKey",(unsigned int)RtlCheckRegistryKey}, +{"_RtlCompareMemory",(unsigned int)RtlCompareMemory}, +{"_RtlCompareString",(unsigned int)RtlCompareString}, +{"_RtlCompareUnicodeString",(unsigned int)RtlCompareUnicodeString}, +{"_RtlConvertLongToLargeInteger",(unsigned int)RtlConvertLongToLargeInteger}, +{"_RtlConvertUlongToLargeInteger",(unsigned int)RtlConvertUlongToLargeInteger}, +{"_RtlCopyBytes",(unsigned int)RtlCopyBytes}, +{"_RtlCopyMemory",(unsigned int)RtlCopyMemory}, +{"_RtlCopyString",(unsigned int)RtlCopyString}, +{"_RtlCopyUnicodeString",(unsigned int)RtlCopyUnicodeString}, +{"_RtlCreateRegistryKey",(unsigned int)RtlCreateRegistryKey}, +{"_RtlCreateSecurityDescriptor",(unsigned int)RtlCreateSecurityDescriptor}, +{"_RtlDeleteRegistryValue",(unsigned int)RtlDeleteRegistryValue}, +{"_RtlEnlargedIntegerMultiply",(unsigned int)RtlEnlargedIntegerMultiply}, +{"_RtlEnlargedUnsignedDivide",(unsigned int)RtlEnlargedUnsignedDivide}, +{"_RtlEnlargedUnsignedMultiply",(unsigned int)RtlEnlargedUnsignedMultiply}, +{"_RtlEqualString",(unsigned int)RtlEqualString}, +{"_RtlEqualUnicodeString",(unsigned int)RtlEqualUnicodeString}, +{"_RtlExtendedIntegerMultiply",(unsigned int)RtlExtendedIntegerMultiply}, +{"_RtlExtendedLargeIntegerDivide",(unsigned int)RtlExtendedLargeIntegerDivide}, +{"_RtlExtendedMagicDivide",(unsigned int)RtlExtendedMagicDivide}, +{"_RtlFillMemory",(unsigned int)RtlFillMemory}, +{"_RtlFreeAnsiString",(unsigned int)RtlFreeAnsiString}, +{"_RtlFreeUnicodeString",(unsigned int)RtlFreeUnicodeString}, +{"_RtlInitAnsiString",(unsigned int)RtlInitAnsiString}, +{"_RtlInitString",(unsigned int)RtlInitString}, +{"_RtlInitUnicodeString",(unsigned int)RtlInitUnicodeString}, +{"_RtlIntegerToUnicodeString",(unsigned int)RtlIntegerToUnicodeString}, +{"_RtlLargeIntegerAdd",(unsigned int)RtlLargeIntegerAdd}, +{"_RtlLargeIntegerAnd",(unsigned int)RtlLargeIntegerAnd}, +{"_RtlLargeIntegerArithmeticShift",(unsigned int)RtlLargeIntegerArithmeticShift}, +{"_RtlLargeIntegerDivide",(unsigned int)RtlLargeIntegerDivide}, +{"_RtlLargeIntegerEqualTo",(unsigned int)RtlLargeIntegerEqualTo}, +{"_RtlLargeIntegerEqualToZero",(unsigned int)RtlLargeIntegerEqualToZero}, +{"_RtlLargeIntegerGreaterThan",(unsigned int)RtlLargeIntegerGreaterThan}, +{"_RtlLargeIntegerGreaterThanOrEqualTo",(unsigned int)RtlLargeIntegerGreaterThanOrEqualTo}, +{"_RtlLargeIntegerGreaterThanOrEqualToZero",(unsigned int)RtlLargeIntegerGreaterThanOrEqualToZero}, +{"_RtlLargeIntegerGreaterThanZero",(unsigned int)RtlLargeIntegerGreaterThanZero}, +{"_RtlLargeIntegerLessThan",(unsigned int)RtlLargeIntegerLessThan}, +{"_RtlLargeIntegerLessThanOrEqualTo",(unsigned int)RtlLargeIntegerLessThanOrEqualTo}, +{"_RtlLargeIntegerLessThanZero",(unsigned int)RtlLargeIntegerLessThanZero}, +{"_RtlLargeIntegerNegate",(unsigned int)RtlLargeIntegerNegate}, +{"_RtlLargeIntegerNotEqualTo",(unsigned int)RtlLargeIntegerNotEqualTo}, +{"_RtlLargeIntegerShiftLeft",(unsigned int)RtlLargeIntegerShiftLeft}, +{"_RtlLargeIntegerShiftRight",(unsigned int)RtlLargeIntegerShiftRight}, +{"_RtlLargeIntegerSubtract",(unsigned int)RtlLargeIntegerSubtract}, +{"_RtlLengthSecurityDescriptor",(unsigned int)RtlLengthSecurityDescriptor}, +{"_RtlMoveMemory",(unsigned int)RtlMoveMemory}, +{"_RtlQueryRegistryValues",(unsigned int)RtlQueryRegistryValues}, +{"_RtlRetrieveUlong",(unsigned int)RtlRetrieveUlong}, +{"_RtlRetrieveUshort",(unsigned int)RtlRetrieveUshort}, +{"_RtlSetDaclSecurityDescriptor",(unsigned int)RtlSetDaclSecurityDescriptor}, +{"_RtlStoreUlong",(unsigned int)RtlStoreUlong}, +{"_RtlStoreUshort",(unsigned int)RtlStoreUshort}, +{"_RtlTimeFieldsToTime",(unsigned int)RtlTimeFieldsToTime}, +{"_RtlTimeToTimeFields",(unsigned int)RtlTimeToTimeFields}, +{"_RtlUnicodeStringToAnsiString",(unsigned int)RtlUnicodeStringToAnsiString}, +{"_RtlUnicodeStringToInteger",(unsigned int)RtlUnicodeStringToInteger}, +{"_RtlUpcaseUnicodeString",(unsigned int)RtlUpcaseUnicodeString}, +{"_RtlUpperString",(unsigned int)RtlUpperString}, +{"_RtlValidSecurityDescriptor",(unsigned int)RtlValidSecurityDescriptor}, +{"_RtlWriteRegistryValue",(unsigned int)RtlWriteRegistryValue}, +{"_RtlZeroMemory",(unsigned int)RtlZeroMemory}, +{"_SeAccessCheck",(unsigned int)SeAccessCheck}, +{"_SeAssignSecurity",(unsigned int)SeAssignSecurity}, +{"_SeDeassignSecurity",(unsigned int)SeDeassignSecurity}, +{"_SeSinglePrivilegeCheck",(unsigned int)SeSinglePrivilegeCheck}, +{"_ZwClose",(unsigned int)ZwClose}, +{"_ZwCreateDirectoryObject",(unsigned int)ZwCreateDirectoryObject}, +{"_ZwCreateFile",(unsigned int)ZwCreateFile}, +{"_ZwCreateKey",(unsigned int)ZwCreateKey}, +{"_ZwDeleteKey",(unsigned int)ZwDeleteKey}, +{"_ZwEnumerateKey",(unsigned int)ZwEnumerateKey}, +{"_ZwEnumerateValueKey",(unsigned int)ZwEnumerateValueKey}, +{"_ZwFlushKey",(unsigned int)ZwFlushKey}, +{"_ZwMakeTemporaryObject",(unsigned int)ZwMakeTemporaryObject}, +{"_ZwMapViewOfSection",(unsigned int)ZwMapViewOfSection}, +{"_ZwOpenFile",(unsigned int)ZwOpenFile}, +{"_ZwOpenKey",(unsigned int)ZwOpenKey}, +{"_ZwOpenSection",(unsigned int)ZwOpenSection}, +{"_ZwQueryInformationFile",(unsigned int)ZwQueryInformationFile}, +{"_ZwQueryKey",(unsigned int)ZwQueryKey}, +{"_ZwQueryValueKey",(unsigned int)ZwQueryValueKey}, +{"_ZwReadFile",(unsigned int)ZwReadFile}, +{"_ZwSetInformationFile",(unsigned int)ZwSetInformationFile}, +{"_ZwSetInformationThread",(unsigned int)ZwSetInformationThread}, +{"_ZwSetValueKey",(unsigned int)ZwSetValueKey}, +{"_ZwUnmapViewOfSection",(unsigned int)ZwUnmapViewOfSection}, +{"_ZwWriteFile",(unsigned int)ZwWriteFile}, +{"_sprintf",(unsigned int)sprintf}, +{NULL,NULL}, +}; diff --git a/reactos/ntoskrnl/ke/kqueue.c b/reactos/ntoskrnl/ke/kqueue.c new file mode 100644 index 00000000000..2b372af0bd0 --- /dev/null +++ b/reactos/ntoskrnl/ke/kqueue.c @@ -0,0 +1,180 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PURPOSE: ReactOS kernel + * FILE: ntoskrnl/ke/device.c + * PURPOSE: Implement device queues + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 08/07/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID InsertBeforeEntryInList(PLIST_ENTRY Head, PLIST_ENTRY After, + PLIST_ENTRY Entry) +{ + if (After->Blink!=NULL) + { + After->Blink->Flink = Entry; + } + else + { + Head->Flink = Entry; + } + Entry->Blink = After->Blink; + Entry->Flink = After; + After->Blink = Entry; +} + +BOOLEAN KeInsertByKeyDeviceQueue(PKDEVICE_QUEUE DeviceQueue, + PKDEVICE_QUEUE_ENTRY DeviceQueueEntry, + ULONG SortKey) +{ + KIRQL oldlvl; + PLIST_ENTRY current; + PKDEVICE_QUEUE_ENTRY entry; + + DeviceQueueEntry->Key=SortKey; + + KeAcquireSpinLock(&DeviceQueue->Lock,&oldlvl); + + if (!DeviceQueue->Busy) + { + DeviceQueue->Busy=TRUE; + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(FALSE); + } + + current=DeviceQueue->ListHead.Flink; + while (current!=NULL) + { + entry = CONTAINING_RECORD(current,KDEVICE_QUEUE_ENTRY,Entry); + if (entry->Key < SortKey) + { + InsertBeforeEntryInList(&DeviceQueue->ListHead, + &DeviceQueueEntry->Entry,current); + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(TRUE); + } + current = current->Flink; + } + InsertTailList(&DeviceQueue->ListHead,&DeviceQueueEntry->Entry); + + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(TRUE); +} + +PKDEVICE_QUEUE_ENTRY KeRemoveByKeyDeviceQueue(PKDEVICE_QUEUE DeviceQueue, + ULONG SortKey) +{ + KIRQL oldlvl; + PLIST_ENTRY current; + PKDEVICE_QUEUE_ENTRY entry; + + assert_irql(DISPATCH_LEVEL); + assert(DeviceQueue!=NULL); + assert(DeviceQueue->Busy); + + KeAcquireSpinLock(&DeviceQueue->Lock,&oldlvl); + + if (IsListEmpty(&DeviceQueue->ListHead)) + { + DeviceQueue->Busy=FALSE; + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(NULL); + } + + current = DeviceQueue->ListHead.Flink; + for(;;) + { + entry = CONTAINING_RECORD(current,KDEVICE_QUEUE_ENTRY,Entry); + if (entry->Key < SortKey || current->Flink == NULL) + { + RemoveEntryFromList(&DeviceQueue->ListHead,current); + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(entry); + } + current = current->Flink; + } +} + +PKDEVICE_QUEUE_ENTRY KeRemoveDeviceQueue(PKDEVICE_QUEUE DeviceQueue) +/* + * FUNCTION: Removes an entry from a device queue + * ARGUMENTS: + * DeviceQueue = Queue to remove the entry + * RETURNS: The removed entry + */ +{ + KIRQL oldlvl; + PLIST_ENTRY list_entry; + PKDEVICE_QUEUE_ENTRY entry; + + assert_irql(DISPATCH_LEVEL); + assert(DeviceQueue!=NULL); + assert(DeviceQueue->Busy); + + KeAcquireSpinLock(&DeviceQueue->Lock,&oldlvl); + + list_entry = RemoveHeadList(&DeviceQueue->ListHead); + if (list_entry==NULL) + { + DeviceQueue->Busy=FALSE; + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(NULL); + } + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + + entry = CONTAINING_RECORD(list_entry,KDEVICE_QUEUE_ENTRY,Entry); + return(entry); +} + +VOID KeInitializeDeviceQueue(PKDEVICE_QUEUE DeviceQueue) +/* + * FUNCTION: Intializes a device queue + * ARGUMENTS: + * DeviceQueue = Device queue to initialize + */ +{ + assert(DeviceQueue!=NULL); + InitializeListHead(&DeviceQueue->ListHead); + DeviceQueue->Busy=FALSE; + KeInitializeSpinLock(&DeviceQueue->Lock); +} + +BOOLEAN KeInsertDeviceQueue(PKDEVICE_QUEUE DeviceQueue, + PKDEVICE_QUEUE_ENTRY DeviceQueueEntry) +/* + * FUNCTION: Inserts an entry in a device queue + * ARGUMENTS: + * DeviceQueue = Queue to insert the entry in + * DeviceQueueEntry = Entry to insert + * RETURNS: False is the device queue wasn't busy + * True otherwise + */ +{ + KIRQL oldlvl; + + KeAcquireSpinLock(&DeviceQueue->Lock,&oldlvl); + + if (!DeviceQueue->Busy) + { + DeviceQueue->Busy=TRUE; + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(FALSE); + } + + InsertTailList(&DeviceQueue->ListHead,&DeviceQueueEntry->Entry); + DeviceQueueEntry->Key=0; + + KeReleaseSpinLock(&DeviceQueue->Lock,oldlvl); + return(TRUE); +} diff --git a/reactos/ntoskrnl/ke/main.c b/reactos/ntoskrnl/ke/main.c new file mode 100644 index 00000000000..201fa386a8f --- /dev/null +++ b/reactos/ntoskrnl/ke/main.c @@ -0,0 +1,175 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ke/main.c + * PURPOSE: Initalizes the kernel + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 28/05/98: Created + */ + +/* INCLUDES *****************************************************************/ + +#include +#include + +#include +#include +#include +#include +#include +#include + +#include +#include + +#define NDEBUG +#include + +/* FUNCTIONS ****************************************************************/ + +void set_breakpoint(unsigned int i, unsigned int addr, unsigned int type, + unsigned int len) +/* + * FUNCTION: Sets a hardware breakpoint + * ARGUMENTS: + * i = breakpoint to set (0 to 3) + * addr = linear address to break on + * type = Type of access to break on + * len = length of the variable to watch + * NOTES: + * The variable to watch must be aligned to its length (i.e. a dword + * breakpoint must be aligned to a dword boundary) + * + * A fatal exception will be generated on the access to the variable. + * It is (at the moment) only really useful for catching undefined + * pointers if you know the variable effected but not the buggy + * routine. + * + * FIXME: Extend to call out to kernel debugger on breakpoint + * Add support for I/O breakpoints + * REFERENCES: See the i386 programmer manual for more details + */ +{ + unsigned int mask; + + if (i>3) + { + printk("Invalid breakpoint index at %s:%d\n",__FILE__,__LINE__); + return; + } + + /* + * Load the linear address + */ + switch (i) + { + case 0: + __asm("movl %0,%%db0\n\t" + : /* no outputs */ + : "d" (addr)); + break; + + case 1: + __asm__("movl %0,%%db1\n\t" + : /* no outputs */ + : "d" (addr)); + break; + + case 2: + __asm__("movl %0,%%db2\n\t" + : /* no outputs */ + : "d" (addr)); + break; + + case 3: + __asm__("movl %0,%%db3\n\t" + : /* no outputs */ + : "d" (addr)); + break; + } + + /* + * Setup mask for dr7 + */ + mask = (len<<(16 + 2 + i*4)) + (type<<(16 + i*4)) + (1<<(i*2)); + __asm__("movl %%db7,%%eax\n\t" + "orl %0,%%eax\n\t" + "movl %%eax,%%db7\n\t" + : /* no outputs */ + : "d" (mask) + : "ax"); +} + +asmlinkage void _main(boot_param* _bp) +/* + * FUNCTION: Called by the boot loader to start the kernel + * ARGUMENTS: + * _bp = Pointer to boot parameters initialized by the boot loader + * NOTE: The boot parameters are stored in low memory which will become + * invalid after the memory managment is initialized so we make a local copy. + */ +{ + unsigned int i; + unsigned int start; + + /* + * Copy the parameters to a local buffer because lowmem will go away + */ + boot_param bp; + memcpy(&bp,_bp,sizeof(bp)); + + /* + * Initalize the console (before printing anything) + */ + InitConsole(&bp); + + printk("Starting ReactOS "KERNEL_VERSION"\n"); + + /* + * Initalize various critical subsystems + */ + HalInit(&bp); + MmInitalize(&bp); + KeInitDpc(); + KeInitializeBugCheck(); + KeInitializeDispatcher(); + InitializeTimer(); + + /* + * Allow interrupts + */ + KeLowerIrql(PASSIVE_LEVEL); + + KeCalibrateTimerLoop(); + ObjNamespcInit(); + PsMgrInit(); + IoInit(); + + /* + * Initalize loaded modules + */ + DPRINT("%d files loaded\n",bp.nr_files); + + + start = KERNEL_BASE + PAGE_ROUND_UP(bp.module_length[0]) + + PAGESIZE; + for (i=1;i +#include + +#include + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* FUNCTIONS **************************************************************/ + +static unsigned int get_kernel_symbol_addr(char* name) +/* + * FUNCTION: Get the address of a kernel symbol + * ARGUMENTS: + * name = symbol name + * RETURNS: The address of the symbol on success + * NULL on failure + */ +{ + int i=0; + while (symbol_table[i].name!=NULL) + { + if (strcmp(symbol_table[i].name,name)==0) + { + return(symbol_table[i].value); + } + i++; + } + return(0); +} + +static void get_symbol_name(module* mod, unsigned int i, char* name) +/* + * FUNCTION: Get the name of a symbol from a loaded module by ordinal + * ARGUMENTS: + * mod = module + * i = index of symbol + * name (OUT) = pointer to a string where the symbol name will be + * stored + */ +{ + if (mod->sym_list[i].e.e_name[0]!=0) + { + strncpy(name,mod->sym_list[i].e.e_name,8); + } + else + { + strcpy(name,&mod->str_tab[mod->sym_list[i].e.e.e_offset]); + } +} + +static unsigned int get_symbol_value(module* mod, unsigned int i) +/* + * FUNCTION: Get the value of a module defined symbol + * ARGUMENTS: + * mod = module + * i = index of symbol + * RETURNS: The value of the symbol + * NOTE: This fixes up references to known sections + */ +{ + char name[255]; + get_symbol_name(mod,i,name); + // DPRINT("name %s ",name); + + /* + * Check if the symbol is a section we have relocated + */ + if (strcmp(name,".text")==0) + { + return(mod->text_base); + } + if (strcmp(name,".data")==0) + { + return(mod->data_base); + } + if (strcmp(name,".bss")==0) + { + return(mod->bss_base); + } + return(mod->sym_list[i].e_value); +} + +static int do_reloc32_reloc(module* mod, SCNHDR* scn, RELOC* reloc) +/* + * FUNCTION: Performs a reloc32 relocation on a loaded module + * ARGUMENTS: + * mod = module to perform the relocation on + * scn = Section to perform the relocation in + * reloc = Pointer to a data structure describing the relocation + * RETURNS: Success or failure + * NOTE: This fixes up an undefined reference to a kernel function in a module + */ +{ + char name[255]; + unsigned int val; + unsigned int * loc; + + memset(name,0,255); + get_symbol_name(mod,reloc->r_symndx,name); + val = get_kernel_symbol_addr(name); + if (val==0) + { + printk("Undefined symbol %s in module\n",name); + return(0); + } + // DPRINT("REL32 value %x name %s\n",val,name); + // printk("value %x\n",val); + loc=(unsigned int *)(mod->base+reloc->r_vaddr); + // printk("old %x ",*loc); + (*loc) = (*loc) + val - mod->base + scn->s_vaddr; + + // printk("new %x\n",*loc); + + return(1); +} + +static int do_addr32_reloc(module* mod, SCNHDR* scn, RELOC* reloc) +/* + * FUNCTION: Performs a addr32 relocation on a loaded module + * ARGUMENTS: + * mod = module to perform the relocation on + * scn = Section to perform the relocation in + * reloc = Pointer to a data structure describing the relocation + * RETURNS: Success or failure + * NOTE: This fixes up a relocation needed when changing the base address of a + * module + */ +{ + unsigned int value; + unsigned int * loc; + // printk("ADDR32 "); + + + value=get_symbol_value(mod,reloc->r_symndx); + + // printk("value %x\n",value); + + loc=(unsigned int *)(mod->base+reloc->r_vaddr); +// DPRINT("ADDR32 loc %x value %x *loc %x ",loc,value,*loc); + *loc=(*loc)+mod->base; + // *loc = value; + // *loc=(*loc)+value + +// DPRINT("*loc %x\n",*loc); + + return(1); +} + +static BOOLEAN do_reloc(module* mod, unsigned int scn_idx) +/* + * FUNCTION: Do the relocations for a module section + * ARGUMENTS: + * mod = Pointer to the module + * scn_idx = Index of the section to be relocated + * RETURNS: Success or failure + */ +{ + SCNHDR* scn = &mod->scn_list[scn_idx]; + RELOC* reloc = (RELOC *)(mod->raw_data_off + scn->s_relptr); + int j; + + DPRINT("scn_idx %d name %.8s relocs %d\n",scn_idx, + mod->scn_list[scn_idx].s_name,scn->s_nreloc); + + for (j=0;js_nreloc;j++) + { + // printk("vaddr %x ",reloc->r_vaddr); + // printk("symndex %x ",reloc->r_symndx); + + switch(reloc->r_type) + { + case RELOC_ADDR32: + if (!do_addr32_reloc(mod,scn,reloc)) + { + return(0); + } + break; + + case RELOC_REL32: + if (!do_reloc32_reloc(mod,scn,reloc)) + { + return(0); + } + break; + + default: + printk("Unknown relocation type %x at %d in module\n", + reloc->r_type,j); + return(0); + } + + reloc = (RELOC *)(((unsigned int)reloc) + sizeof(RELOC)); + } + + DPRINT("Done relocations for %.8s\n",mod->scn_list[scn_idx].s_name); + + return(1); +} + +BOOLEAN process_boot_module(unsigned int start) +/* + * FUNCTION: Processes and initializes a module whose disk image has been + * loaded + * ARGUMENTS: + * start = start of the module in memory + * RETURNS: Success or failure + */ +{ + FILHDR hdr; + AOUTHDR ohdr; + module* mod; + unsigned int entry=0; + unsigned int found_entry=0; + PDRIVER_INITIALIZE func; + int i; + + DPRINT("n = %x\n",*((unsigned int *)start)); + + mod=(module *)ExAllocatePool(NonPagedPool,sizeof(module)); + + DPRINT("magic %x\n",((FILHDR *)start)->f_magic); + + memcpy(&hdr,(void *)start,FILHSZ); + + if (I386BADMAG(hdr)) + { + printk("(%s:%d) Module has bad magic value (%x)\n",__FILE__, + __LINE__,hdr.f_magic); + return(0); + } + + memcpy(&ohdr,(void *)(start+FILHSZ),AOUTSZ); + + mod->sym_list = (SYMENT *)(start + hdr.f_symptr); + + mod->str_tab = (char *)(start + hdr.f_symptr + + hdr.f_nsyms * SYMESZ); + + mod->scn_list = (SCNHDR *)(start+FILHSZ+hdr.f_opthdr); + mod->size=0; + mod->raw_data_off = start; + + /* + * Determine the length of the module + */ + for (i=0;iscn_list[i].s_name); + DPRINT("size %x vaddr %x size %x\n",mod->size, + mod->scn_list[i].s_vaddr,mod->scn_list[i].s_size); + if (mod->scn_list[i].s_flags & STYP_TEXT) + { + mod->text_base=mod->scn_list[i].s_vaddr; + } + if (mod->scn_list[i].s_flags & STYP_DATA) + { + mod->data_base=mod->scn_list[i].s_vaddr; + } + if (mod->scn_list[i].s_flags & STYP_BSS) + { + mod->bss_base=mod->scn_list[i].s_vaddr; + } + if (mod->size < + (mod->scn_list[i].s_vaddr + mod->scn_list[i].s_size)) + { + mod->size = mod->size + mod->scn_list[i].s_vaddr + + mod->scn_list[i].s_size; + } + } + + mod->base = (unsigned int)VirtualAlloc((LPVOID)0,mod->size,MEM_COMMIT, + PAGE_SYSTEM + PAGE_EXECUTE_READWRITE); + if (mod->base == 0) + { + printk("Failed to allocated section for module\n"); + return(0); + } + + + /* + * Adjust section vaddrs for allocated area + */ + mod->data_base=mod->data_base+mod->base; + mod->text_base=mod->text_base+mod->base; + mod->bss_base=mod->bss_base+mod->base; + + /* + * Relocate module and fixup imports + */ + for (i=0;iscn_list[i].s_flags & STYP_TEXT || + mod->scn_list[i].s_flags & STYP_DATA) + { + memcpy((void *)(mod->base + mod->scn_list[i].s_vaddr), + (void *)(start + mod->scn_list[i].s_scnptr), + mod->scn_list[i].s_size); + if (!do_reloc(mod,i)) + { + DPRINT("Relocation failed for section %s\n", + mod->scn_list[i].s_name); + return(0); + } + } + if (mod->scn_list[i].s_flags & STYP_BSS) + { + memset((void *)(mod->base + mod->scn_list[i].s_vaddr),0, + mod->scn_list[i].s_size); + } + } + + DPRINT("Allocate base: %x\n",mod->base); + + /* + * Find the entry point + */ + + for (i=0;isym_list[i].e_value; + found_entry=1; + DPRINT("Found entry at %x\n",entry); + } + } + + if (!found_entry) + { + printk("No module entry point defined\n"); + return(0); + } + + /* + * Call the module initalization routine + */ + func = (PDRIVER_INITIALIZE)(mod->base + entry); + return(InitalizeLoadedDriver(func)); +} diff --git a/reactos/ntoskrnl/ke/mutex.c b/reactos/ntoskrnl/ke/mutex.c new file mode 100644 index 00000000000..dbc9250c413 --- /dev/null +++ b/reactos/ntoskrnl/ke/mutex.c @@ -0,0 +1,49 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/mutex.c + * PURPOSE: Implements mutex + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID KeInitializeMutex(PKMUTEX Mutex, ULONG Level) +{ + Mutex->Header.Type=2; + Mutex->Header.SignalState=TRUE; + Mutex->Header.Size = 8; + Mutex->OwnerThread = NULL; + Mutex->ApcDisable = 0; + InitializeListHead(&Mutex->Header.WaitListHead); +} + +LONG KeReadStateMutex(PKMUTEX Mutex) +{ + return(Mutex->Header.SignalState); +} + +LONG KeReleaseMutex(PKMUTEX Mutex, BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + +NTSTATUS KeWaitForMutexObject(PKMUTEX Mutex, + KWAIT_REASON WaitReason, + KPROCESSOR_MODE WaitMode, + BOOLEAN Alertable, + PLARGE_INTEGER Timeout) +{ + return(KeWaitForSingleObject(Mutex,WaitReason,WaitMode,Alertable,Timeout)); +} + diff --git a/reactos/ntoskrnl/ke/sem.c b/reactos/ntoskrnl/ke/sem.c new file mode 100644 index 00000000000..ac76acbce4c --- /dev/null +++ b/reactos/ntoskrnl/ke/sem.c @@ -0,0 +1,40 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/sem.c + * PURPOSE: Implements kernel semaphores + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID KeInitializeSemaphore(PKSEMAPHORE Semaphore, + LONG Count, + LONG Limit) +{ + UNIMPLEMENTED; +} + +LONG KeReadStateSemaphore(PKSEMAPHORE Semaphore) +{ + UNIMPLEMENTED; +} + +LONG KeReleaseSemaphore(PKSEMAPHORE Semaphore, + KPRIORITY Increment, + LONG Adjustment, + BOOLEAN Wait) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/ke/timer.c b/reactos/ntoskrnl/ke/timer.c new file mode 100644 index 00000000000..4f887c54bfd --- /dev/null +++ b/reactos/ntoskrnl/ke/timer.c @@ -0,0 +1,407 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ke/timer.c + * PURPOSE: Handle timers + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 28/05/98: Created + */ + +/* NOTES ******************************************************************/ +/* + * System time units are 100-nanosecond intervals + */ + +/* INCLUDES ***************************************************************/ + +#include + +#include +#include +#include +#include +#include +#include + +#include + +/* TYPES *****************************************************************/ + +#define TIMER_IRQ 0 + + +/* GLOBALS ****************************************************************/ + +/* + * Current time + */ +static unsigned long long system_time = 0; + +/* + * Number of timer interrupts since initialisation + */ +static volatile unsigned long long ticks=0; + +/* + * The increment in the system clock every timer tick (in system time units) + * + * = (1/18.2)*10^9 + * + */ +#define CLOCK_INCREMENT (54945055) + +/* + * PURPOSE: List of timers + */ +static LIST_ENTRY timer_list_head = {NULL,NULL}; +static KSPIN_LOCK timer_list_lock; + + +#define MICROSECONDS_TO_CALIBRATE (1000000) +#define MICROSECONDS_PER_TICK (54945) +#define MICROSECONDS_IN_A_SECOND (10000000) +#define TICKS_PER_SECOND_APPROX (18) + +static unsigned int loops_per_microsecond = 17; + +/* FUNCTIONS **************************************************************/ + +void KeCalibrateTimerLoop() +{ + unsigned int start_tick; + unsigned int end_tick; + unsigned int nr_ticks; + unsigned int i; + + return; + + for (i=0;i<5;i++) + { + + start_tick = ticks; + while (start_tick==ticks); + KeStallExecutionProcessor(MICROSECONDS_TO_CALIBRATE); + end_tick = ticks; + while (end_tick==ticks); + + nr_ticks = end_tick - start_tick; + loops_per_microsecond = (loops_per_microsecond * MICROSECONDS_TO_CALIBRATE) + / (nr_ticks*MICROSECONDS_PER_TICK); + + printk("nr_ticks %d\n",nr_ticks); + printk("loops_per_microsecond %d\n",loops_per_microsecond); + printk("Processor speed (approx) %d\n", + (6*loops_per_microsecond)/1000); + + if (nr_ticks == (TICKS_PER_SECOND_APPROX * MICROSECONDS_TO_CALIBRATE) + / MICROSECONDS_IN_A_SECOND) + { + printk("Testing loop\n"); + KeStallExecutionProcessor(10000); + printk("Finished loop\n"); + return; + } + } +} + +NTSTATUS KeDelayExecutionThread(KPROCESSOR_MODE WaitMode, + BOOLEAN Alertable, + PLARGE_INTEGER Interval) +{ + UNIMPLEMENTED; +} + +VOID KeStallExecutionProcessor(ULONG MicroSeconds) +{ + unsigned int i; + for (i=0; i<(loops_per_microsecond*MicroSeconds) ;i++) + { + __asm__("nop\n\t"); + } +} + +static inline void ULLToLargeInteger(unsigned long long src, + PLARGE_INTEGER dest) +{ + dest->LowPart = src & 0xffffffff; + dest->HighPart = (src>>32); +} + +static inline void SLLToLargeInteger(signed long long src, + PLARGE_INTEGER dest) +{ + if (src > 0) + { + dest->LowPart = src & 0xffffffff; + dest->HighPart = (src>>32); + } + else + { + src = -src; + dest->LowPart = src & 0xffffffff; + dest->HighPart = -(src>>32); + } +} + +static inline signed long long LargeIntegerToSLL(PLARGE_INTEGER src) +{ + signed long long r; + + r = src->LowPart; + if (src->HighPart >= 0) + { + r = r | (((unsigned long long)src->HighPart)<<32); + } + else + { + r = r | (((unsigned long long)(-(src->HighPart)))<<32); + r = -r; + } + return(r); +} + + +LARGE_INTEGER KeQueryPerformanceCounter(PLARGE_INTEGER PerformanceFreq) +/* + * FUNCTION: Queries the finest grained running count avaiable in the system + * ARGUMENTS: + * PerformanceFreq (OUT) = The routine stores the number of + * performance counters tick per second here + * RETURNS: The performance counter value in HERTZ + * NOTE: Returns the system tick count or the time-stamp on the pentium + */ +{ + PerformanceFreq->HighPart=0; + PerformanceFreq->LowPart=0; +} + +ULONG KeQueryTimeIncrement(VOID) +/* + * FUNCTION: Gets the increment (in 100-nanosecond units) that is added to + * the system clock every time the clock interrupts + * RETURNS: The increment + */ +{ + return(CLOCK_INCREMENT); +} + +VOID KeQuerySystemTime(PLARGE_INTEGER CurrentTime) +/* + * FUNCTION: Gets the current system time + * ARGUMENTS: + * CurrentTime (OUT) = The routine stores the current time here + * NOTE: The time is the number of 100-nanosecond intervals since the + * 1st of January, 1601. + */ +{ + ULLToLargeInteger(system_time,CurrentTime); +} + + +BOOLEAN KeSetTimer(PKTIMER Timer, LARGE_INTEGER DueTime, PKDPC Dpc) +/* + * FUNCTION: Sets the absolute or relative interval at which a timer object + * is to be set to the signaled state and optionally supplies a + * CustomTimerDpc to be executed when the timer expires. + * ARGUMENTS: + * Timer = Points to a previously initialized timer object + * DueTimer = If positive then absolute time to expire at + * If negative then the relative time to expire at + * Dpc = If non-NULL then a dpc to be called when the timer expires + * RETURNS: True if the timer was already in the system timer queue + * False otherwise + */ +{ + return(KeSetTimerEx(Timer,DueTime,0,Dpc)); +} + +BOOLEAN KeSetTimerEx(PKTIMER Timer, LARGE_INTEGER DueTime, LONG Period, + PKDPC Dpc) +/* + * FUNCTION: Sets the absolute or relative interval at which a timer object + * is to be set to the signaled state and optionally supplies a + * CustomTimerDpc to be executed when the timer expires. + * ARGUMENTS: + * Timer = Points to a previously initialized timer object + * DueTimer = If positive then absolute time to expire at + * If negative then the relative time to expire at + * Dpc = If non-NULL then a dpc to be called when the timer expires + * RETURNS: True if the timer was already in the system timer queue + * False otherwise + */ +{ + KIRQL oldlvl; + + KeAcquireSpinLock(&timer_list_lock,&oldlvl); + + Timer->dpc=Dpc; + Timer->period=Period; + Timer->expire_time = LargeIntegerToSLL(&DueTime); + if (Timer->expire_time < 0) + { + Timer->expire_time = system_time - Timer->expire_time; + Timer->signaled = FALSE; + } + if (Timer->running) + { + KeReleaseSpinLock(&timer_list_lock,oldlvl); + return(TRUE); + } + InsertTailList(&timer_list_head,&Timer->entry); + KeReleaseSpinLock(&timer_list_lock,oldlvl); + return(FALSE); +} + +BOOLEAN KeCancelTimer(PKTIMER Timer) +/* + * FUNCTION: Removes a timer from the system timer list + * ARGUMENTS: + * Timer = timer to cancel + * RETURNS: True if the timer was running + * False otherwise + */ +{ + KIRQL oldlvl; + + KeAcquireSpinLock(&timer_list_lock,&oldlvl); + + if (!Timer->running) + { + return(FALSE); + } + RemoveEntryFromList(&timer_list_head,&Timer->entry); + KeReleaseSpinLock(&timer_list_lock,oldlvl); + return(TRUE); +} + +BOOLEAN KeReadStateTimer(PKTIMER Timer) +{ + return(Timer->signaled); +} + +VOID KeInitializeTimer(PKTIMER Timer) +/* + * FUNCTION: Initalizes a kernel timer object + * ARGUMENTS: + * Timer = caller supplied storage for the timer + * NOTE: This function initializes a notification timer + */ +{ + KeInitializeTimerEx(Timer,NotificationTimer); +} + +VOID KeInitializeTimerEx(PKTIMER Timer, TIMER_TYPE Type) +/* + * FUNCTION: Initializes a kernel timer object + * ARGUMENTS: + * Timer = caller supplied storage for the timer + * Type = the type of timer (notification or synchronization) + * NOTE: When a notification type expires all waiting threads are released + * and the timer remains signalled until it is explicitly reset. When a + * syncrhonization timer expires its state is set to signalled until a + * single waiting thread is released and then the timer is reset. + */ +{ + Timer->running=FALSE; + Timer->type=Type; + Timer->signaled=FALSE; +} + +VOID KeQueryTickCount(PLARGE_INTEGER TickCount) +/* + * FUNCTION: Returns the number of ticks since the system was booted + * ARGUMENTS: + * TickCount (OUT) = Points to storage for the number of ticks + */ +{ + ULLToLargeInteger(ticks,TickCount); +} + +static void HandleExpiredTimer(PKTIMER current) +{ + if (current->dpc!=NULL) + { + current->dpc->DeferredRoutine(current->dpc, + current->dpc->DeferredContext, + current->dpc->SystemArgument1, + current->dpc->SystemArgument2); + } + current->signaled=TRUE; + if (current->period !=0) + { + current->expire_time = current->expire_time + current->period; + } + else + { + RemoveEntryFromList(&timer_list_head,¤t->entry); + current->running=FALSE; + } +} + +void KeExpireTimers(void) +{ + PLIST_ENTRY current_entry = timer_list_head.Flink; + PKTIMER current = CONTAINING_RECORD(current_entry,KTIMER,entry); + KIRQL oldlvl; + + KeAcquireSpinLock(&timer_list_lock,&oldlvl); + + while (current_entry!=NULL) + { + if (system_time == current->expire_time) + { + HandleExpiredTimer(current); + } + + current_entry = current_entry->Flink; + current = CONTAINING_RECORD(current_entry,KTIMER,entry); + } + KeReleaseSpinLock(&timer_list_lock,oldlvl); +} + +VOID KeTimerInterrupt(VOID) +/* + * FUNCTION: Handles a timer interrupt + */ +{ + char str[16]; + char* vidmem=(char *)physical_to_linear(0xb8000 + 160 - 16); + int i; + + /* + * Increment the number of timers ticks + */ + ticks++; + system_time = system_time + CLOCK_INCREMENT; + + /* + * Display the tick count in the top left of the screen as a debugging + * aid + */ + sprintf(str,"%.8u",ticks); + for (i=0;i<8;i++) + { + *vidmem=str[i]; + vidmem++; + *vidmem=0x7; + vidmem++; + } + + return(TRUE); +} + + +void InitializeTimer(void) +/* + * FUNCTION: Initializes timer irq handling + * NOTE: This is only called once from main() + */ +{ + InitializeListHead(&timer_list_head); + KeInitializeSpinLock(&timer_list_lock); + + /* + * Calculate the starting time for the system clock + */ +} diff --git a/reactos/ntoskrnl/ke/wait.c b/reactos/ntoskrnl/ke/wait.c new file mode 100644 index 00000000000..917af040ce8 --- /dev/null +++ b/reactos/ntoskrnl/ke/wait.c @@ -0,0 +1,82 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS project + * FILE: ntoskrnl/ps/wait.c + * PURPOSE: Manages non-busy waiting + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 21/07/98: Created + */ + +/* NOTES ******************************************************************** + * + */ + +/* INCLUDES ******************************************************************/ + +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ******************************************************************/ + +KSPIN_LOCK DispatcherDatabaseLock; +BOOLEAN WaitSet; + +/* FUNCTIONS *****************************************************************/ + +VOID KeDispatcherObjectWake(DISPATCHER_HEADER* hdr) +{ + PKWAIT_BLOCK current; + PLIST_ENTRY current_entry; + + DPRINT("Entering KeDispatcherObjectWake(hdr %x)\n",hdr); + DPRINT("hdr->WaitListHead %x hdr->WaitListHead.Flink %x\n", + &hdr->WaitListHead,hdr->WaitListHead.Flink); + while ((current_entry=RemoveHeadList(&hdr->WaitListHead))!=NULL) + { + current = CONTAINING_RECORD(current_entry,KWAIT_BLOCK, + WaitListEntry); + DPRINT("Waking %x\n",current->Thread); + PsWakeThread(current->Thread); + }; +} + + +NTSTATUS KeWaitForSingleObject(PVOID Object, + KWAIT_REASON WaitReason, + KPROCESSOR_MODE WaitMode, + BOOLEAN Alertable, + PLARGE_INTEGER Timeout) +{ + DISPATCHER_HEADER* hdr = (DISPATCHER_HEADER *)Object; + KWAIT_BLOCK blk; + + DPRINT("Entering KeWaitForSingleObject(Object %x)\n",Object); + + blk.Object=Object; + blk.Thread=KeGetCurrentThread(); + InsertTailList(&hdr->WaitListHead,&blk.WaitListEntry); + PsSuspendThread(); +} + +NTSTATUS KeWaitForMultipleObjects(ULONG Count, + PVOID Object[], + WAIT_TYPE WaitType, + KWAIT_REASON WaitReason, + KPROCESSOR_MODE WaitMode, + BOOLEAN Alertable, + PLARGE_INTEGER Timeout, + PKWAIT_BLOCK WaitBlockArray) +{ + UNIMPLEMENTED; +} + +VOID KeInitializeDispatcher(VOID) +{ + KeInitializeSpinLock(&DispatcherDatabaseLock); +} diff --git a/reactos/ntoskrnl/ldr/pe-bak.h b/reactos/ntoskrnl/ldr/pe-bak.h new file mode 100644 index 00000000000..fb5d64cc589 --- /dev/null +++ b/reactos/ntoskrnl/ldr/pe-bak.h @@ -0,0 +1,281 @@ +/* + * COPYRIGHT: See copying in the top level directory + * PROJECT: ReactOS kernel + * FILE: include/pe.h + * PURPOSE: Contains portable executable format definitions + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 26/05/98: Created + */ + +/* NOTES + * + * This is taken from the Tool Interface Standard (TIS) Formats Specification + * for Windows + */ + +#ifndef __PE_H +#define __PE_H + +/* + * CPU types + */ +enum +{ + CPU_UNKNOWN, + CPU_I386 = 0x14c, + CPU_I486 = 0x14d, + CPU_PENTIUM = 0x14e, + CPU_MIPS_I = 0x162, + CPU_MIPS_II = 0x163, + CPU_MIPS_III = 0x166, +}; + +/* + * Image flags + */ +enum +{ + IMG_PROGRAM = 0, + IMG_EXECUTABLE = 0, + IMG_FIXED = 0x200, + IMG_LIBRARY = 0x2000, +}; + +/* + * Subsystems + */ +enum +{ + SUBSYS_UNKNOWN, + SUBSYS_NATIVE, + SUBSYS_WINDOWS_GUI, + SUBSYS_WINDOWS_CHARACTER, + SUBSYS_OS2_CHARACTER, + SUBSYS_POSIX_CHARACTER, +}; + +enum +{ + DLL_PERPROCESS_LIB_INITIALIZATION, + DLL_PERPROCESS_LIB_TERMINATION, + DLL_PERTHREAD_LIB_INITIALIZATION, + DLL_PERTHREAD_LIB_TERMINATION, +}; + +enum +{ + OBJ_CODE = 0x20, + OBJ_INITIALIZED_DATA = 0x40, + OBJ_UNINITIALIZED_DATA = 0x80, + OBJ_NOCACHE = 0x40000000, + OBJ_NONPAGEABLE = 0x80000000, + OBJ_SHARED = 0x10000000, + OBJ_EXECUTABLE = 0x20000000, + OBJ_READABLE = 0x40000000, + OBJ_WRITEABLE = 0x80000000 +}; + +typedef struct +{ + /* + * PURPOSE: Signature, current value is 'PE' + */ + unsigned char signature[4]; + + /* + * PURPOSE: CPU required for the image to run + */ + unsigned short int cpu; + + /* + * PURPOSE: Number of entries in the object table + */ + unsigned short int nr_objects; + + /* + * PURPOSE: Time and date when image was created + */ + unsigned long int time_date_stamp; + + unsigned short int reserved1; + unsigned short int reserved2; + + /* + * PURPOSE: Number of bytes in the header following the flags field + */ + unsigned short int nt_hdr_size; + + /* + * PURPOSE: Image flags + */ + unsigned short int flags; + + unsigned char reserved3; + + /* + * PURPOSE: Major/minor version number of the linker + */ + unsigned char linker_major_ver; + unsigned char linker_minor_ver; + + unsigned char reserved4; + unsigned long int reserved5; + unsigned long int reserved6; + + /* + * PURPOSE: Entry point relative to the image base + */ + unsigned long int entry; + + unsigned long int reserved7; + unsigned long int reserved8; + + /* + * PURPOSE: Virtual base of image. This will be the virtual address of + * the first byte of file. It must be a multiple of 64k + */ + unsigned long int image_base; + + /* + * PURPOSE: Object alignment factor + */ + unsigned long int object_align; + + /* + * PURPOSE: Alignment factor used to align image pages + */ + unsigned long int file_align; + + /* + * PURPOSE: OS version required to run this image + */ + unsigned short int os_version; + + /* + * PURPOSE: User specified version number + */ + unsigned short int user_version; + + /* + * PURPOSE: Subsystem version required + */ + unsigned short int subsys_version; + + unsigned long int reserved9; + + /* + * PURPOSE: Size of the image in bytes (including all headers) + */ + unsigned long int image_size; + + /* + * PURPOSE: Header size (Total of DOS header, PE header and object table) + */ + unsigned long int hdr_size; + + /* + * PURPOSE: Checksum for entire file + */ + unsigned long int checksum; + + /* + * PURPOSE: Subsystem required to run this image + */ + unsigned short int subsystem; + + /* + * PURPOSE: Special loader requirements + */ + unsigned short int dll_flags; + + /* + * PURPOSE: Stack size needed for image + */ + unsigned long int stack_reserve_size; + + /* + * PURPOSE: Stack size to be committed + */ + unsigned long int stack_commit_size; + + /* + * PURPOSE: Size of local heap to reserve + */ + unsigned long int heap_reserve_size; + + /* + * PURPOSE: Size of local heap to commit + */ + unsigned long int heap_commit_size; + + unsigned long int reserved10; + + /* + * PURPOSE: Size of the array that follows + */ + unsigned long int nr_rvas; + + + unsigned long int export_table_rva; + unsigned long int export_table_size; + unsigned long int import_table_rva; + unsigned long int import_table_size; + unsigned long int resource_tlb_rva; + unsigned long int resource_tlb_size; + unsigned long int exception_table_rva; + unsigned long int exception_table_size; + unsigned long int security_table_rva; + unsigned long int security_table_size; + unsigned long int fixup_table_rva; + unsigned long int fixup_table_size; + unsigned long int debug_table_rva; + unsigned long int debug_table_size; + unsigned long int image_description_rva; + unsigned long int image_description_size; + unsigned long int mach_specific_rva; + unsigned long int mach_specific_size; + unsigned long int tls_rva; + unsigned long int tls_size; +} PE_header; + +typedef struct +/* + * PURPOSE: Defines an entry in the image object table + */ +{ + /* + * PURPOSE: Name of object + */ + unsigned char name[8]; + + /* + * PURPOSE: Size to allocate in memory + */ + unsigned long int virtual_size; + + /* + * PURPOSE: Base address of object relative to the image base + */ + unsigned long int rva; + + /* + * PURPOSE: Size of initialized data + */ + unsigned long int physical_size; + + /* + * PURPOSE: Offset relative to the beginning of the image of the + * data for the object + */ + unsigned long int physical_offset; + + unsigned long int reserved[3]; + + /* + * PURPOSE: Object flags + */ + unsigned long int object_flags; +} PE_ObjectTableEntry; + +#endif /* __PE_H */ diff --git a/reactos/ntoskrnl/ldr/pe.h b/reactos/ntoskrnl/ldr/pe.h new file mode 100644 index 00000000000..7471ab79fd2 --- /dev/null +++ b/reactos/ntoskrnl/ldr/pe.h @@ -0,0 +1,646 @@ +typedef struct _IMAGE_DOS_HEADER { // DOS .EXE header + WORD e_magic; // Magic number + WORD e_cblp; // Bytes on last page of file + WORD e_cp; // Pages in file + WORD e_crlc; // Relocations + WORD e_cparhdr; // Size of header in paragraphs + WORD e_minalloc; // Minimum extra paragraphs needed + WORD e_maxalloc; // Maximum extra paragraphs needed + WORD e_ss; // Initial (relative) SS value + WORD e_sp; // Initial SP value + WORD e_csum; // Checksum + WORD e_ip; // Initial IP value + WORD e_cs; // Initial (relative) CS value + WORD e_lfarlc; // File address of relocation table + WORD e_ovno; // Overlay number + WORD e_res[4]; // Reserved words + WORD e_oemid; // OEM identifier (for e_oeminfo) + WORD e_oeminfo; // OEM information; e_oemid specific + WORD e_res2[10]; // Reserved words + LONG e_lfanew; // File address of new exe header +} IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER; + +typedef struct _IMAGE_FILE_HEADER { + WORD Machine; + WORD NumberOfSections; + DWORD TimeDateStamp; + DWORD PointerToSymbolTable; + DWORD NumberOfSymbols; + WORD SizeOfOptionalHeader; + WORD Characteristics; +} IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER; + +#define IMAGE_SIZEOF_FILE_HEADER 20 + +#define IMAGE_FILE_RELOCS_STRIPPED 0x0001 // Relocation info stripped from file. +#define IMAGE_FILE_EXECUTABLE_IMAGE 0x0002 // File is executable (i.e. no unresolved externel references). +#define IMAGE_FILE_LINE_NUMS_STRIPPED 0x0004 // Line nunbers stripped from file. +#define IMAGE_FILE_LOCAL_SYMS_STRIPPED 0x0008 // Local symbols stripped from file. +#define IMAGE_FILE_BYTES_REVERSED_LO 0x0080 // Bytes of machine word are reversed. +#define IMAGE_FILE_32BIT_MACHINE 0x0100 // 32 bit word machine. +#define IMAGE_FILE_DEBUG_STRIPPED 0x0200 // Debugging info stripped from file in .DBG file +#define IMAGE_FILE_REMOVABLE_RUN_FROM_SWAP 0x0400 // If Image is on removable media, copy and run from the swap file. +#define IMAGE_FILE_NET_RUN_FROM_SWAP 0x0800 // If Image is on Net, copy and run from the swap file. +#define IMAGE_FILE_SYSTEM 0x1000 // System File. +#define IMAGE_FILE_DLL 0x2000 // File is a DLL. +#define IMAGE_FILE_UP_SYSTEM_ONLY 0x4000 // File should only be run on a UP machine +#define IMAGE_FILE_BYTES_REVERSED_HI 0x8000 // Bytes of machine word are reversed. + +#define IMAGE_FILE_MACHINE_UNKNOWN 0 +#define IMAGE_FILE_MACHINE_I386 0x14c // Intel 386. +#define IMAGE_FILE_MACHINE_R3000 0x162 // MIPS little-endian, 0x160 big-endian +#define IMAGE_FILE_MACHINE_R4000 0x166 // MIPS little-endian +#define IMAGE_FILE_MACHINE_R10000 0x168 // MIPS little-endian +#define IMAGE_FILE_MACHINE_ALPHA 0x184 // Alpha_AXP +#define IMAGE_FILE_MACHINE_POWERPC 0x1F0 // IBM PowerPC Little-Endian + + +// +// Directory format. +// + +typedef struct _IMAGE_DATA_DIRECTORY { + DWORD VirtualAddress; + DWORD Size; +} IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY; + +#define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16 + +// +// Optional header format. +// + +typedef struct _IMAGE_OPTIONAL_HEADER { + // + // Standard fields. + // + + WORD Magic; + BYTE MajorLinkerVersion; + BYTE MinorLinkerVersion; + DWORD SizeOfCode; + DWORD SizeOfInitializedData; + DWORD SizeOfUninitializedData; + DWORD AddressOfEntryPoint; + DWORD BaseOfCode; + DWORD BaseOfData; + + // + // NT additional fields. + // + + DWORD ImageBase; + DWORD SectionAlignment; + DWORD FileAlignment; + WORD MajorOperatingSystemVersion; + WORD MinorOperatingSystemVersion; + WORD MajorImageVersion; + WORD MinorImageVersion; + WORD MajorSubsystemVersion; + WORD MinorSubsystemVersion; + DWORD Win32VersionValue; + DWORD SizeOfImage; + DWORD SizeOfHeaders; + DWORD CheckSum; + WORD Subsystem; + WORD DllCharacteristics; + DWORD SizeOfStackReserve; + DWORD SizeOfStackCommit; + DWORD SizeOfHeapReserve; + DWORD SizeOfHeapCommit; + DWORD LoaderFlags; + DWORD NumberOfRvaAndSizes; + IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]; +} IMAGE_OPTIONAL_HEADER, *PIMAGE_OPTIONAL_HEADER; + + +typedef struct _IMAGE_NT_HEADERS { + DWORD Signature; + IMAGE_FILE_HEADER FileHeader; + IMAGE_OPTIONAL_HEADER OptionalHeader; +} IMAGE_NT_HEADERS, *PIMAGE_NT_HEADERS; + + +// Directory Entries + +#define IMAGE_DIRECTORY_ENTRY_EXPORT 0 // Export Directory +#define IMAGE_DIRECTORY_ENTRY_IMPORT 1 // Import Directory +#define IMAGE_DIRECTORY_ENTRY_RESOURCE 2 // Resource Directory +#define IMAGE_DIRECTORY_ENTRY_EXCEPTION 3 // Exception Directory +#define IMAGE_DIRECTORY_ENTRY_SECURITY 4 // Security Directory +#define IMAGE_DIRECTORY_ENTRY_BASERELOC 5 // Base Relocation Table +#define IMAGE_DIRECTORY_ENTRY_DEBUG 6 // Debug Directory +#define IMAGE_DIRECTORY_ENTRY_COPYRIGHT 7 // Description String +#define IMAGE_DIRECTORY_ENTRY_GLOBALPTR 8 // Machine Value (MIPS GP) +#define IMAGE_DIRECTORY_ENTRY_TLS 9 // TLS Directory +#define IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG 10 // Load Configuration Directory +#define IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT 11 // Bound Import Directory in headers +#define IMAGE_DIRECTORY_ENTRY_IAT 12 // Import Address Table + +// +// Section header format. +// + +#define IMAGE_SIZEOF_SHORT_NAME 8 + +typedef struct _IMAGE_SECTION_HEADER { + BYTE Name[IMAGE_SIZEOF_SHORT_NAME]; + union { + DWORD PhysicalAddress; + DWORD VirtualSize; + } Misc; + DWORD VirtualAddress; + DWORD SizeOfRawData; + DWORD PointerToRawData; + DWORD PointerToRelocations; + DWORD PointerToLinenumbers; + WORD NumberOfRelocations; + WORD NumberOfLinenumbers; + DWORD Characteristics; +} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER; + +#define IMAGE_SIZEOF_SECTION_HEADER 40 + + +// +// Export Format +// + +typedef struct _IMAGE_EXPORT_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + DWORD Name; + DWORD Base; + DWORD NumberOfFunctions; + DWORD NumberOfNames; + PDWORD *AddressOfFunctions; + PDWORD *AddressOfNames; + PWORD *AddressOfNameOrdinals; +} IMAGE_EXPORT_DIRECTORY, *PIMAGE_EXPORT_DIRECTORY; + +// +// Import Format +// + +typedef struct _IMAGE_IMPORT_BY_NAME { + WORD Hint; + BYTE Name[1]; +} IMAGE_IMPORT_BY_NAME, *PIMAGE_IMPORT_BY_NAME; + +#define IMAGE_ORDINAL_FLAG 0x80000000 +#define IMAGE_ORDINAL(Ordinal) (Ordinal & 0xffff) + + +// +// Resource Format. +// + +// +// Resource directory consists of two counts, following by a variable length +// array of directory entries. The first count is the number of entries at +// beginning of the array that have actual names associated with each entry. +// The entries are in ascending order, case insensitive strings. The second +// count is the number of entries that immediately follow the named entries. +// This second count identifies the number of entries that have 16-bit integer +// Ids as their name. These entries are also sorted in ascending order. +// +// This structure allows fast lookup by either name or number, but for any +// given resource entry only one form of lookup is supported, not both. +// This is consistant with the syntax of the .RC file and the .RES file. +// + +// Predefined resource types ... there may be some more, but I don't have +// the information yet. .....sang cho..... + +#define RT_NEWRESOURCE 0x2000 +#define RT_ERROR 0x7fff +#define RT_CURSOR 1 +#define RT_BITMAP 2 +#define RT_ICON 3 +#define RT_MENU 4 +#define RT_DIALOG 5 +#define RT_STRING 6 +#define RT_FONTDIR 7 +#define RT_FONT 8 +#define RT_ACCELERATORS 9 +#define RT_RCDATA 10 +#define RT_MESSAGETABLE 11 +#define RT_GROUP_CURSOR 12 +#define RT_GROUP_ICON 14 +#define RT_VERSION 16 +#define NEWBITMAP (RT_BITMAP|RT_NEWRESOURCE) +#define NEWMENU (RT_MENU|RT_NEWRESOURCE) +#define NEWDIALOG (RT_DIALOG|RT_NEWRESOURCE) + + +typedef struct _IMAGE_RESOURCE_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + WORD NumberOfNamedEntries; + WORD NumberOfIdEntries; +// IMAGE_RESOURCE_DIRECTORY_ENTRY DirectoryEntries[1]; +} IMAGE_RESOURCE_DIRECTORY, *PIMAGE_RESOURCE_DIRECTORY; + +#define IMAGE_RESOURCE_NAME_IS_STRING 0x80000000 +#define IMAGE_RESOURCE_DATA_IS_DIRECTORY 0x80000000 + +// +// Each directory contains the 32-bit Name of the entry and an offset, +// relative to the beginning of the resource directory of the data associated +// with this directory entry. If the name of the entry is an actual text +// string instead of an integer Id, then the high order bit of the name field +// is set to one and the low order 31-bits are an offset, relative to the +// beginning of the resource directory of the string, which is of type +// IMAGE_RESOURCE_DIRECTORY_STRING. Otherwise the high bit is clear and the +// low-order 16-bits are the integer Id that identify this resource directory +// entry. If the directory entry is yet another resource directory (i.e. a +// subdirectory), then the high order bit of the offset field will be +// set to indicate this. Otherwise the high bit is clear and the offset +// field points to a resource data entry. +// + +typedef struct _IMAGE_RESOURCE_DIRECTORY_ENTRY { + DWORD Name; + DWORD OffsetToData; +} IMAGE_RESOURCE_DIRECTORY_ENTRY, *PIMAGE_RESOURCE_DIRECTORY_ENTRY; + +// +// For resource directory entries that have actual string names, the Name +// field of the directory entry points to an object of the following type. +// All of these string objects are stored together after the last resource +// directory entry and before the first resource data object. This minimizes +// the impact of these variable length objects on the alignment of the fixed +// size directory entry objects. +// + +typedef struct _IMAGE_RESOURCE_DIRECTORY_STRING { + WORD Length; + CHAR NameString[ 1 ]; +} IMAGE_RESOURCE_DIRECTORY_STRING, *PIMAGE_RESOURCE_DIRECTORY_STRING; + + +typedef struct _IMAGE_RESOURCE_DIR_STRING_U { + WORD Length; + WCHAR NameString[ 1 ]; +} IMAGE_RESOURCE_DIR_STRING_U, *PIMAGE_RESOURCE_DIR_STRING_U; + + +// +// Each resource data entry describes a leaf node in the resource directory +// tree. It contains an offset, relative to the beginning of the resource +// directory of the data for the resource, a size field that gives the number +// of bytes of data at that offset, a CodePage that should be used when +// decoding code point values within the resource data. Typically for new +// applications the code page would be the unicode code page. +// + +typedef struct _IMAGE_RESOURCE_DATA_ENTRY { + DWORD OffsetToData; + DWORD Size; + DWORD CodePage; + DWORD Reserved; +} IMAGE_RESOURCE_DATA_ENTRY, *PIMAGE_RESOURCE_DATA_ENTRY; + + +// Menu Resources ... added by .....sang cho.... + +// Menu resources are composed of a menu header followed by a sequential list +// of menu items. There are two types of menu items: pop-ups and normal menu +// itmes. The MENUITEM SEPARATOR is a special case of a normal menu item with +// an empty name, zero ID, and zero flags. + +typedef struct _IMAGE_MENU_HEADER{ + WORD wVersion; // Currently zero + WORD cbHeaderSize; // Also zero +} IMAGE_MENU_HEADER, *PIMAGE_MENU_HEADER; + +typedef struct _IMAGE_POPUP_MENU_ITEM{ + WORD fItemFlags; + WCHAR szItemText[1]; +} IMAGE_POPUP_MENU_ITEM, *PIMAGE_POPUP_MENU_ITEM; + +typedef struct _IMAGE_NORMAL_MENU_ITEM{ + WORD fItemFlags; + WORD wMenuID; + WCHAR szItemText[1]; +} IMAGE_NORMAL_MENU_ITEM, *PIMAGE_NORMAL_MENU_ITEM; + +#define GRAYED 0x0001 // GRAYED keyword +#define INACTIVE 0x0002 // INACTIVE keyword +#define BITMAP 0x0004 // BITMAP keyword +#define OWNERDRAW 0x0100 // OWNERDRAW keyword +#define CHECKED 0x0008 // CHECKED keyword +#define POPUP 0x0010 // used internally +#define MENUBARBREAK 0x0020 // MENUBARBREAK keyword +#define MENUBREAK 0x0040 // MENUBREAK keyword +#define ENDMENU 0x0080 // used internally + + +// Dialog Box Resources .................. added by sang cho. + +// A dialog box is contained in a single resource and has a header and +// a portion repeated for each control in the dialog box. +// The item DWORD IStyle is a standard window style composed of flags found +// in WINDOWS.H. +// The default style for a dialog box is: +// WS_POPUP | WS_BORDER | WS_SYSMENU +// +// The itme marked "Name or Ordinal" are : +// If the first word is an 0xffff, the next two bytes contain an ordinal ID. +// Otherwise, the first one or more WORDS contain a double-null-terminated string. +// An empty string is represented by a single WORD zero in the first location. +// +// The WORD wPointSize and WCHAR szFontName entries are present if the FONT +// statement was included for the dialog box. This can be detected by checking +// the entry IStyle. If IStyle & DS_SETFONT ( which is 0x40), then these +// entries will be present. + +typedef struct _IMAGE_DIALOG_BOX_HEADER1{ + DWORD IStyle; + DWORD IExtendedStyle; // New for Windows NT + WORD nControls; // Number of Controls + WORD x; + WORD y; + WORD cx; + WORD cy; +// N_OR_O MenuName; // Name or Ordinal ID +// N_OR_O ClassName; // Name or Ordinal ID +// WCHAR szCaption[]; +// WORD wPointSize; // Only here if FONT set for dialog +// WCHAR szFontName[]; // This too +} IMAGE_DIALOG_HEADER, *PIMAGE_DIALOG_HEADER; + +typedef union _NAME_OR_ORDINAL{ // Name or Ordinal ID + struct _ORD_ID{ + WORD flgId; + WORD Id; + } ORD_ID; + WCHAR szName[1]; +} NAME_OR_ORDINAL, *PNAME_OR_ORDINAL; + +// The data for each control starts on a DWORD boundary (which may require +// some padding from the previous control), and its format is as follows: + +typedef struct _IMAGE_CONTROL_DATA{ + DWORD IStyle; + DWORD IExtendedStyle; + WORD x; + WORD y; + WORD cx; + WORD cy; + WORD wId; +// N_OR_O ClassId; +// N_OR_O Text; +// WORD nExtraStuff; +} IMAGE_CONTROL_DATA, *PIMAGE_CONTROL_DATA; + +#define BUTTON 0x80 +#define EDIT 0x81 +#define STATIC 0x82 +#define LISTBOX 0x83 +#define SCROLLBAR 0x84 +#define COMBOBOX 0x85 + +// The various statements used in a dialog script are all mapped to these +// classes along with certain modifying styles. The values for these styles +// can be found in WINDOWS.H. All dialog controls have the default styles +// of WS_CHILD and WS_VISIBLE. A list of the default styles used follows: +// +// Statement Default Class Default Styles +// CONTROL None WS_CHILD|WS_VISIBLE +// LTEXT STATIC ES_LEFT +// RTEXT STATIC ES_RIGHT +// CTEXT STATIC ES_CENTER +// LISTBOX LISTBOX WS_BORDER|LBS_NOTIFY +// CHECKBOX BUTTON BS_CHECKBOX|WS_TABSTOP +// PUSHBUTTON BUTTON BS_PUSHBUTTON|WS_TABSTOP +// GROUPBOX BUTTON BS_GROUPBOX +// DEFPUSHBUTTON BUTTON BS_DFPUSHBUTTON|WS_TABSTOP +// RADIOBUTTON BUTTON BS_RADIOBUTTON +// AUTOCHECKBOX BUTTON BS_AUTOCHECKBOX +// AUTO3STATE BUTTON BS_AUTO3STATE +// AUTORADIOBUTTON BUTTON BS_AUTORADIOBUTTON +// PUSHBOX BUTTON BS_PUSHBOX +// STATE3 BUTTON BS_3STATE +// EDITTEXT EDIT ES_LEFT|WS_BORDER|WS_TABSTOP +// COMBOBOX COMBOBOX None +// ICON STATIC SS_ICON +// SCROLLBAR SCROLLBAR None +/// + +#define WS_OVERLAPPED 0x00000000L +#define WS_POPUP 0x80000000L +#define WS_CHILD 0x40000000L +#define WS_CLIPSIBLINGS 0x04000000L +#define WS_CLIPCHILDREN 0x02000000L +#define WS_VISIBLE 0x10000000L +#define WS_DISABLED 0x08000000L +#define WS_MINIMIZE 0x20000000L +#define WS_MAXIMIZE 0x01000000L +#define WS_CAPTION 0x00C00000L +#define WS_BORDER 0x00800000L +#define WS_DLGFRAME 0x00400000L +#define WS_VSCROLL 0x00200000L +#define WS_HSCROLL 0x00100000L +#define WS_SYSMENU 0x00080000L +#define WS_THICKFRAME 0x00040000L +#define WS_MINIMIZEBOX 0x00020000L +#define WS_MAXIMIZEBOX 0x00010000L +#define WS_GROUP 0x00020000L +#define WS_TABSTOP 0x00010000L + +// other aliases +#define WS_OVERLAPPEDWINDOW (WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX) +#define WS_POPUPWINDOW (WS_POPUP | WS_BORDER | WS_SYSMENU) +#define WS_CHILDWINDOW (WS_CHILD) +#define WS_TILED WS_OVERLAPPED +#define WS_ICONIC WS_MINIMIZE +#define WS_SIZEBOX WS_THICKFRAME +#define WS_TILEDWINDOW WS_OVERLAPPEDWINDOW + +#define WS_EX_DLGMODALFRAME 0x00000001L +#define WS_EX_NOPARENTNOTIFY 0x00000004L +#define WS_EX_TOPMOST 0x00000008L +#define WS_EX_ACCEPTFILES 0x00000010L +#define WS_EX_TRANSPARENT 0x00000020L + +#define BS_PUSHBUTTON 0x00000000L +#define BS_DEFPUSHBUTTON 0x00000001L +#define BS_CHECKBOX 0x00000002L +#define BS_AUTOCHECKBOX 0x00000003L +#define BS_RADIOBUTTON 0x00000004L +#define BS_3STATE 0x00000005L +#define BS_AUTO3STATE 0x00000006L +#define BS_GROUPBOX 0x00000007L +#define BS_USERBUTTON 0x00000008L +#define BS_AUTORADIOBUTTON 0x00000009L +#define BS_OWNERDRAW 0x0000000BL +#define BS_LEFTTEXT 0x00000020L + +#define ES_LEFT 0x00000000L +#define ES_CENTER 0x00000001L +#define ES_RIGHT 0x00000002L +#define ES_MULTILINE 0x00000004L +#define ES_UPPERCASE 0x00000008L +#define ES_LOWERCASE 0x00000010L +#define ES_PASSWORD 0x00000020L +#define ES_AUTOVSCROLL 0x00000040L +#define ES_AUTOHSCROLL 0x00000080L +#define ES_NOHIDESEL 0x00000100L +#define ES_OEMCONVERT 0x00000400L +#define ES_READONLY 0x00000800L +#define ES_WANTRETURN 0x00001000L + +#define LBS_NOTIFY 0x0001L +#define LBS_SORT 0x0002L +#define LBS_NOREDRAW 0x0004L +#define LBS_MULTIPLESEL 0x0008L +#define LBS_OWNERDRAWFIXED 0x0010L +#define LBS_OWNERDRAWVARIABLE 0x0020L +#define LBS_HASSTRINGS 0x0040L +#define LBS_USETABSTOPS 0x0080L +#define LBS_NOINTEGRALHEIGHT 0x0100L +#define LBS_MULTICOLUMN 0x0200L +#define LBS_WANTKEYBOARDINPUT 0x0400L +#define LBS_EXTENDEDSEL 0x0800L +#define LBS_DISABLENOSCROLL 0x1000L + +#define SS_LEFT 0x00000000L +#define SS_CENTER 0x00000001L +#define SS_RIGHT 0x00000002L +#define SS_ICON 0x00000003L +#define SS_BLACKRECT 0x00000004L +#define SS_GRAYRECT 0x00000005L +#define SS_WHITERECT 0x00000006L +#define SS_BLACKFRAME 0x00000007L +#define SS_GRAYFRAME 0x00000008L +#define SS_WHITEFRAME 0x00000009L +#define SS_SIMPLE 0x0000000BL +#define SS_LEFTNOWORDWRAP 0x0000000CL +#define SS_BITMAP 0x0000000EL + +// +// Debug Format +// + +typedef struct _IMAGE_DEBUG_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + DWORD Type; + DWORD SizeOfData; + DWORD AddressOfRawData; + DWORD PointerToRawData; +} IMAGE_DEBUG_DIRECTORY, *PIMAGE_DEBUG_DIRECTORY; + +#define IMAGE_DEBUG_TYPE_UNKNOWN 0 +#define IMAGE_DEBUG_TYPE_COFF 1 +#define IMAGE_DEBUG_TYPE_CODEVIEW 2 +#define IMAGE_DEBUG_TYPE_FPO 3 +#define IMAGE_DEBUG_TYPE_MISC 4 +#define IMAGE_DEBUG_TYPE_EXCEPTION 5 +#define IMAGE_DEBUG_TYPE_FIXUP 6 +#define IMAGE_DEBUG_TYPE_OMAP_TO_SRC 7 +#define IMAGE_DEBUG_TYPE_OMAP_FROM_SRC 8 + + +typedef struct _IMAGE_DEBUG_MISC { + DWORD DataType; // type of misc data, see defines + DWORD Length; // total length of record, rounded to four + // byte multiple. + BOOLEAN Unicode; // TRUE if data is unicode string + BYTE Reserved[ 3 ]; + BYTE Data[ 1 ]; // Actual data +} IMAGE_DEBUG_MISC, *PIMAGE_DEBUG_MISC; + + +// +// Debugging information can be stripped from an image file and placed +// in a separate .DBG file, whose file name part is the same as the +// image file name part (e.g. symbols for CMD.EXE could be stripped +// and placed in CMD.DBG). This is indicated by the IMAGE_FILE_DEBUG_STRIPPED +// flag in the Characteristics field of the file header. The beginning of +// the .DBG file contains the following structure which captures certain +// information from the image file. This allows a debug to proceed even if +// the original image file is not accessable. This header is followed by +// zero of more IMAGE_SECTION_HEADER structures, followed by zero or more +// IMAGE_DEBUG_DIRECTORY structures. The latter structures and those in +// the image file contain file offsets relative to the beginning of the +// .DBG file. +// +// If symbols have been stripped from an image, the IMAGE_DEBUG_MISC structure +// is left in the image file, but not mapped. This allows a debugger to +// compute the name of the .DBG file, from the name of the image in the +// IMAGE_DEBUG_MISC structure. +// + +typedef struct _IMAGE_SEPARATE_DEBUG_HEADER { + WORD Signature; + WORD Flags; + WORD Machine; + WORD Characteristics; + DWORD TimeDateStamp; + DWORD CheckSum; + DWORD ImageBase; + DWORD SizeOfImage; + DWORD NumberOfSections; + DWORD ExportedNamesSize; + DWORD DebugDirectorySize; + DWORD SectionAlignment; + DWORD Reserved[2]; +} IMAGE_SEPARATE_DEBUG_HEADER, *PIMAGE_SEPARATE_DEBUG_HEADER; + +#define IMAGE_SEPARATE_DEBUG_SIGNATURE 0x4944 + +#define IMAGE_SEPARATE_DEBUG_FLAGS_MASK 0x8000 +#define IMAGE_SEPARATE_DEBUG_MISMATCH 0x8000 // when DBG was updated, the + // old checksum didn't match. + + +// +// End Image Format +// + + +#define SIZE_OF_NT_SIGNATURE sizeof (DWORD) +#define MAXRESOURCENAME 13 + +/* global macros to define header offsets into file */ +/* offset to PE file signature */ +#define NTSIGNATURE(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew)) + +/* DOS header identifies the NT PEFile signature dword + the PEFILE header exists just after that dword */ +#define PEFHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE)) + +/* PE optional header is immediately after PEFile header */ +#define OPTHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE + \ + sizeof (IMAGE_FILE_HEADER))) + +/* section headers are immediately after PE optional header */ +#define SECHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE + \ + sizeof (IMAGE_FILE_HEADER) + \ + sizeof (IMAGE_OPTIONAL_HEADER))) + + +typedef struct tagImportDirectory + { + DWORD dwRVAFunctionNameList; + DWORD dwUseless1; + DWORD dwUseless2; + DWORD dwRVAModuleName; + DWORD dwRVAFunctionAddressList; + }IMAGE_IMPORT_MODULE_DIRECTORY, * PIMAGE_IMPORT_MODULE_DIRECTORY; + diff --git a/reactos/ntoskrnl/ldr/pedump.c b/reactos/ntoskrnl/ldr/pedump.c new file mode 100644 index 00000000000..6e4d8c74ddf --- /dev/null +++ b/reactos/ntoskrnl/ldr/pedump.c @@ -0,0 +1,3490 @@ +// +// +// This program was written by Sang Cho, assistant professor at +// the department of +// computer science and engineering +// chongju university +// this program is based on the program pefile.c +// which is written by Randy Kath(Microsoft Developmer Network Technology Group) +// in june 12, 1993. +// I have investigated P.E. file format as thoroughly as possible, +// but I cannot claim that I am an expert yet, so some of its information +// may give you wrong results. +// +// +// +// language used: djgpp +// date of creation: September 28, 1997 +// +// date of first release: October 15, 1997 +// +// +// you can contact me: e-mail address: sangcho@alpha94.chongju.ac.kr +// hitel id: chokhas +// phone number: (0431) 229-8491 +82-431-229-8491 +// +// real address: Sang Cho +// Computer and Information Engineering +// ChongJu University +// NaeDok-Dong 36 +// ChongJu 360-764 +// South Korea +// +// Copyright (C) 1997. by Sang Cho. +// +// Permission is granted to make and distribute verbatim copies of this +// program provided the copyright notice and this permission notice are +// preserved on all copies. +// +// +// File: pedump.c ( I included header file into source file. ) + +# include "ccx.h" + +//typedef char CHAR; +//typedef short WCHAR; +//typedef short SHORT; +//typedef long LONG; +//typedef unsigned short USHORT; +//typedef unsigned long DWORD; +//typedef int BOOL; +//typedef unsigned char BYTE; +//typedef unsigned short WORD; +//typedef BYTE *PBYTE; +//typedef WORD *PWORD; +//typedef DWORD *PDWORD; +//typedef void *LPVOID; + +#define VOID void +#define BOOLEAN boolean +#define NULL 0 +#define FALSE 0 +#define TRUE 1 +#define CONST const +#define LOWORD(l) ((WORD)(l)) +#define WINAPI + +// +// Image Format +// + +#define IMAGE_DOS_SIGNATURE 0x5A4D // MZ +#define IMAGE_OS2_SIGNATURE 0x454E // NE +#define IMAGE_OS2_SIGNATURE_LE 0x454C // LE +#define IMAGE_VXD_SIGNATURE 0x454C // LE +#define IMAGE_NT_SIGNATURE 0x00004550 // PE00 + +typedef struct _IMAGE_DOS_HEADER { // DOS .EXE header + WORD e_magic; // Magic number + WORD e_cblp; // Bytes on last page of file + WORD e_cp; // Pages in file + WORD e_crlc; // Relocations + WORD e_cparhdr; // Size of header in paragraphs + WORD e_minalloc; // Minimum extra paragraphs needed + WORD e_maxalloc; // Maximum extra paragraphs needed + WORD e_ss; // Initial (relative) SS value + WORD e_sp; // Initial SP value + WORD e_csum; // Checksum + WORD e_ip; // Initial IP value + WORD e_cs; // Initial (relative) CS value + WORD e_lfarlc; // File address of relocation table + WORD e_ovno; // Overlay number + WORD e_res[4]; // Reserved words + WORD e_oemid; // OEM identifier (for e_oeminfo) + WORD e_oeminfo; // OEM information; e_oemid specific + WORD e_res2[10]; // Reserved words + LONG e_lfanew; // File address of new exe header + } IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER; + +// +// File header format. +// + + + +typedef struct _IMAGE_FILE_HEADER { + WORD Machine; + WORD NumberOfSections; + DWORD TimeDateStamp; + DWORD PointerToSymbolTable; + DWORD NumberOfSymbols; + WORD SizeOfOptionalHeader; + WORD Characteristics; +} IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER; + +#define IMAGE_SIZEOF_FILE_HEADER 20 + +#define IMAGE_FILE_RELOCS_STRIPPED 0x0001 // Relocation info stripped from file. +#define IMAGE_FILE_EXECUTABLE_IMAGE 0x0002 // File is executable (i.e. no unresolved externel references). +#define IMAGE_FILE_LINE_NUMS_STRIPPED 0x0004 // Line nunbers stripped from file. +#define IMAGE_FILE_LOCAL_SYMS_STRIPPED 0x0008 // Local symbols stripped from file. +#define IMAGE_FILE_BYTES_REVERSED_LO 0x0080 // Bytes of machine word are reversed. +#define IMAGE_FILE_32BIT_MACHINE 0x0100 // 32 bit word machine. +#define IMAGE_FILE_DEBUG_STRIPPED 0x0200 // Debugging info stripped from file in .DBG file +#define IMAGE_FILE_REMOVABLE_RUN_FROM_SWAP 0x0400 // If Image is on removable media, copy and run from the swap file. +#define IMAGE_FILE_NET_RUN_FROM_SWAP 0x0800 // If Image is on Net, copy and run from the swap file. +#define IMAGE_FILE_SYSTEM 0x1000 // System File. +#define IMAGE_FILE_DLL 0x2000 // File is a DLL. +#define IMAGE_FILE_UP_SYSTEM_ONLY 0x4000 // File should only be run on a UP machine +#define IMAGE_FILE_BYTES_REVERSED_HI 0x8000 // Bytes of machine word are reversed. + +#define IMAGE_FILE_MACHINE_UNKNOWN 0 +#define IMAGE_FILE_MACHINE_I386 0x14c // Intel 386. +#define IMAGE_FILE_MACHINE_R3000 0x162 // MIPS little-endian, 0x160 big-endian +#define IMAGE_FILE_MACHINE_R4000 0x166 // MIPS little-endian +#define IMAGE_FILE_MACHINE_R10000 0x168 // MIPS little-endian +#define IMAGE_FILE_MACHINE_ALPHA 0x184 // Alpha_AXP +#define IMAGE_FILE_MACHINE_POWERPC 0x1F0 // IBM PowerPC Little-Endian + + + +// +// Directory format. +// + +typedef struct _IMAGE_DATA_DIRECTORY { + DWORD VirtualAddress; + DWORD Size; +} IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY; + +#define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16 + +// +// Optional header format. +// + +typedef struct _IMAGE_OPTIONAL_HEADER { + // + // Standard fields. + // + + WORD Magic; + BYTE MajorLinkerVersion; + BYTE MinorLinkerVersion; + DWORD SizeOfCode; + DWORD SizeOfInitializedData; + DWORD SizeOfUninitializedData; + DWORD AddressOfEntryPoint; + DWORD BaseOfCode; + DWORD BaseOfData; + + // + // NT additional fields. + // + + DWORD ImageBase; + DWORD SectionAlignment; + DWORD FileAlignment; + WORD MajorOperatingSystemVersion; + WORD MinorOperatingSystemVersion; + WORD MajorImageVersion; + WORD MinorImageVersion; + WORD MajorSubsystemVersion; + WORD MinorSubsystemVersion; + DWORD Win32VersionValue; + DWORD SizeOfImage; + DWORD SizeOfHeaders; + DWORD CheckSum; + WORD Subsystem; + WORD DllCharacteristics; + DWORD SizeOfStackReserve; + DWORD SizeOfStackCommit; + DWORD SizeOfHeapReserve; + DWORD SizeOfHeapCommit; + DWORD LoaderFlags; + DWORD NumberOfRvaAndSizes; + IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]; +} IMAGE_OPTIONAL_HEADER, *PIMAGE_OPTIONAL_HEADER; + + +typedef struct _IMAGE_NT_HEADERS { + DWORD Signature; + IMAGE_FILE_HEADER FileHeader; + IMAGE_OPTIONAL_HEADER OptionalHeader; +} IMAGE_NT_HEADERS, *PIMAGE_NT_HEADERS; + + +// Directory Entries + +#define IMAGE_DIRECTORY_ENTRY_EXPORT 0 // Export Directory +#define IMAGE_DIRECTORY_ENTRY_IMPORT 1 // Import Directory +#define IMAGE_DIRECTORY_ENTRY_RESOURCE 2 // Resource Directory +#define IMAGE_DIRECTORY_ENTRY_EXCEPTION 3 // Exception Directory +#define IMAGE_DIRECTORY_ENTRY_SECURITY 4 // Security Directory +#define IMAGE_DIRECTORY_ENTRY_BASERELOC 5 // Base Relocation Table +#define IMAGE_DIRECTORY_ENTRY_DEBUG 6 // Debug Directory +#define IMAGE_DIRECTORY_ENTRY_COPYRIGHT 7 // Description String +#define IMAGE_DIRECTORY_ENTRY_GLOBALPTR 8 // Machine Value (MIPS GP) +#define IMAGE_DIRECTORY_ENTRY_TLS 9 // TLS Directory +#define IMAGE_DIRECTORY_ENTRY_LOAD_CONFIG 10 // Load Configuration Directory +#define IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT 11 // Bound Import Directory in headers +#define IMAGE_DIRECTORY_ENTRY_IAT 12 // Import Address Table + +// +// Section header format. +// + +#define IMAGE_SIZEOF_SHORT_NAME 8 + +typedef struct _IMAGE_SECTION_HEADER { + BYTE Name[IMAGE_SIZEOF_SHORT_NAME]; + union { + DWORD PhysicalAddress; + DWORD VirtualSize; + } Misc; + DWORD VirtualAddress; + DWORD SizeOfRawData; + DWORD PointerToRawData; + DWORD PointerToRelocations; + DWORD PointerToLinenumbers; + WORD NumberOfRelocations; + WORD NumberOfLinenumbers; + DWORD Characteristics; +} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER; + +#define IMAGE_SIZEOF_SECTION_HEADER 40 + + +// +// Export Format +// + +typedef struct _IMAGE_EXPORT_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + DWORD Name; + DWORD Base; + DWORD NumberOfFunctions; + DWORD NumberOfNames; + PDWORD *AddressOfFunctions; + PDWORD *AddressOfNames; + PWORD *AddressOfNameOrdinals; +} IMAGE_EXPORT_DIRECTORY, *PIMAGE_EXPORT_DIRECTORY; + +// +// Import Format +// + +typedef struct _IMAGE_IMPORT_BY_NAME { + WORD Hint; + BYTE Name[1]; +} IMAGE_IMPORT_BY_NAME, *PIMAGE_IMPORT_BY_NAME; + +#define IMAGE_ORDINAL_FLAG 0x80000000 +#define IMAGE_ORDINAL(Ordinal) (Ordinal & 0xffff) + + +// +// Resource Format. +// + +// +// Resource directory consists of two counts, following by a variable length +// array of directory entries. The first count is the number of entries at +// beginning of the array that have actual names associated with each entry. +// The entries are in ascending order, case insensitive strings. The second +// count is the number of entries that immediately follow the named entries. +// This second count identifies the number of entries that have 16-bit integer +// Ids as their name. These entries are also sorted in ascending order. +// +// This structure allows fast lookup by either name or number, but for any +// given resource entry only one form of lookup is supported, not both. +// This is consistant with the syntax of the .RC file and the .RES file. +// + +// Predefined resource types ... there may be some more, but I don't have +// the information yet. .....sang cho..... + +#define RT_NEWRESOURCE 0x2000 +#define RT_ERROR 0x7fff +#define RT_CURSOR 1 +#define RT_BITMAP 2 +#define RT_ICON 3 +#define RT_MENU 4 +#define RT_DIALOG 5 +#define RT_STRING 6 +#define RT_FONTDIR 7 +#define RT_FONT 8 +#define RT_ACCELERATORS 9 +#define RT_RCDATA 10 +#define RT_MESSAGETABLE 11 +#define RT_GROUP_CURSOR 12 +#define RT_GROUP_ICON 14 +#define RT_VERSION 16 +#define NEWBITMAP (RT_BITMAP|RT_NEWRESOURCE) +#define NEWMENU (RT_MENU|RT_NEWRESOURCE) +#define NEWDIALOG (RT_DIALOG|RT_NEWRESOURCE) + + +typedef struct _IMAGE_RESOURCE_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + WORD NumberOfNamedEntries; + WORD NumberOfIdEntries; +// IMAGE_RESOURCE_DIRECTORY_ENTRY DirectoryEntries[1]; +} IMAGE_RESOURCE_DIRECTORY, *PIMAGE_RESOURCE_DIRECTORY; + +#define IMAGE_RESOURCE_NAME_IS_STRING 0x80000000 +#define IMAGE_RESOURCE_DATA_IS_DIRECTORY 0x80000000 + +// +// Each directory contains the 32-bit Name of the entry and an offset, +// relative to the beginning of the resource directory of the data associated +// with this directory entry. If the name of the entry is an actual text +// string instead of an integer Id, then the high order bit of the name field +// is set to one and the low order 31-bits are an offset, relative to the +// beginning of the resource directory of the string, which is of type +// IMAGE_RESOURCE_DIRECTORY_STRING. Otherwise the high bit is clear and the +// low-order 16-bits are the integer Id that identify this resource directory +// entry. If the directory entry is yet another resource directory (i.e. a +// subdirectory), then the high order bit of the offset field will be +// set to indicate this. Otherwise the high bit is clear and the offset +// field points to a resource data entry. +// + +typedef struct _IMAGE_RESOURCE_DIRECTORY_ENTRY { + DWORD Name; + DWORD OffsetToData; +} IMAGE_RESOURCE_DIRECTORY_ENTRY, *PIMAGE_RESOURCE_DIRECTORY_ENTRY; + +// +// For resource directory entries that have actual string names, the Name +// field of the directory entry points to an object of the following type. +// All of these string objects are stored together after the last resource +// directory entry and before the first resource data object. This minimizes +// the impact of these variable length objects on the alignment of the fixed +// size directory entry objects. +// + +typedef struct _IMAGE_RESOURCE_DIRECTORY_STRING { + WORD Length; + CHAR NameString[ 1 ]; +} IMAGE_RESOURCE_DIRECTORY_STRING, *PIMAGE_RESOURCE_DIRECTORY_STRING; + + +typedef struct _IMAGE_RESOURCE_DIR_STRING_U { + WORD Length; + WCHAR NameString[ 1 ]; +} IMAGE_RESOURCE_DIR_STRING_U, *PIMAGE_RESOURCE_DIR_STRING_U; + + +// +// Each resource data entry describes a leaf node in the resource directory +// tree. It contains an offset, relative to the beginning of the resource +// directory of the data for the resource, a size field that gives the number +// of bytes of data at that offset, a CodePage that should be used when +// decoding code point values within the resource data. Typically for new +// applications the code page would be the unicode code page. +// + +typedef struct _IMAGE_RESOURCE_DATA_ENTRY { + DWORD OffsetToData; + DWORD Size; + DWORD CodePage; + DWORD Reserved; +} IMAGE_RESOURCE_DATA_ENTRY, *PIMAGE_RESOURCE_DATA_ENTRY; + + +// Menu Resources ... added by .....sang cho.... + +// Menu resources are composed of a menu header followed by a sequential list +// of menu items. There are two types of menu items: pop-ups and normal menu +// itmes. The MENUITEM SEPARATOR is a special case of a normal menu item with +// an empty name, zero ID, and zero flags. + +typedef struct _IMAGE_MENU_HEADER{ + WORD wVersion; // Currently zero + WORD cbHeaderSize; // Also zero +} IMAGE_MENU_HEADER, *PIMAGE_MENU_HEADER; + +typedef struct _IMAGE_POPUP_MENU_ITEM{ + WORD fItemFlags; + WCHAR szItemText[1]; +} IMAGE_POPUP_MENU_ITEM, *PIMAGE_POPUP_MENU_ITEM; + +typedef struct _IMAGE_NORMAL_MENU_ITEM{ + WORD fItemFlags; + WORD wMenuID; + WCHAR szItemText[1]; +} IMAGE_NORMAL_MENU_ITEM, *PIMAGE_NORMAL_MENU_ITEM; + +#define GRAYED 0x0001 // GRAYED keyword +#define INACTIVE 0x0002 // INACTIVE keyword +#define BITMAP 0x0004 // BITMAP keyword +#define OWNERDRAW 0x0100 // OWNERDRAW keyword +#define CHECKED 0x0008 // CHECKED keyword +#define POPUP 0x0010 // used internally +#define MENUBARBREAK 0x0020 // MENUBARBREAK keyword +#define MENUBREAK 0x0040 // MENUBREAK keyword +#define ENDMENU 0x0080 // used internally + + +// Dialog Box Resources .................. added by sang cho. + +// A dialog box is contained in a single resource and has a header and +// a portion repeated for each control in the dialog box. +// The item DWORD IStyle is a standard window style composed of flags found +// in WINDOWS.H. +// The default style for a dialog box is: +// WS_POPUP | WS_BORDER | WS_SYSMENU +// +// The itme marked "Name or Ordinal" are : +// If the first word is an 0xffff, the next two bytes contain an ordinal ID. +// Otherwise, the first one or more WORDS contain a double-null-terminated string. +// An empty string is represented by a single WORD zero in the first location. +// +// The WORD wPointSize and WCHAR szFontName entries are present if the FONT +// statement was included for the dialog box. This can be detected by checking +// the entry IStyle. If IStyle & DS_SETFONT ( which is 0x40), then these +// entries will be present. + +typedef struct _IMAGE_DIALOG_BOX_HEADER1{ + DWORD IStyle; + DWORD IExtendedStyle; // New for Windows NT + WORD nControls; // Number of Controls + WORD x; + WORD y; + WORD cx; + WORD cy; +// N_OR_O MenuName; // Name or Ordinal ID +// N_OR_O ClassName; // Name or Ordinal ID +// WCHAR szCaption[]; +// WORD wPointSize; // Only here if FONT set for dialog +// WCHAR szFontName[]; // This too +} IMAGE_DIALOG_HEADER, *PIMAGE_DIALOG_HEADER; + +typedef union _NAME_OR_ORDINAL{ // Name or Ordinal ID + struct _ORD_ID{ + WORD flgId; + WORD Id; + } ORD_ID; + WCHAR szName[1]; +} NAME_OR_ORDINAL, *PNAME_OR_ORDINAL; + +// The data for each control starts on a DWORD boundary (which may require +// some padding from the previous control), and its format is as follows: + +typedef struct _IMAGE_CONTROL_DATA{ + DWORD IStyle; + DWORD IExtendedStyle; + WORD x; + WORD y; + WORD cx; + WORD cy; + WORD wId; +// N_OR_O ClassId; +// N_OR_O Text; +// WORD nExtraStuff; +} IMAGE_CONTROL_DATA, *PIMAGE_CONTROL_DATA; + +#define BUTTON 0x80 +#define EDIT 0x81 +#define STATIC 0x82 +#define LISTBOX 0x83 +#define SCROLLBAR 0x84 +#define COMBOBOX 0x85 + +// The various statements used in a dialog script are all mapped to these +// classes along with certain modifying styles. The values for these styles +// can be found in WINDOWS.H. All dialog controls have the default styles +// of WS_CHILD and WS_VISIBLE. A list of the default styles used follows: +// +// Statement Default Class Default Styles +// CONTROL None WS_CHILD|WS_VISIBLE +// LTEXT STATIC ES_LEFT +// RTEXT STATIC ES_RIGHT +// CTEXT STATIC ES_CENTER +// LISTBOX LISTBOX WS_BORDER|LBS_NOTIFY +// CHECKBOX BUTTON BS_CHECKBOX|WS_TABSTOP +// PUSHBUTTON BUTTON BS_PUSHBUTTON|WS_TABSTOP +// GROUPBOX BUTTON BS_GROUPBOX +// DEFPUSHBUTTON BUTTON BS_DFPUSHBUTTON|WS_TABSTOP +// RADIOBUTTON BUTTON BS_RADIOBUTTON +// AUTOCHECKBOX BUTTON BS_AUTOCHECKBOX +// AUTO3STATE BUTTON BS_AUTO3STATE +// AUTORADIOBUTTON BUTTON BS_AUTORADIOBUTTON +// PUSHBOX BUTTON BS_PUSHBOX +// STATE3 BUTTON BS_3STATE +// EDITTEXT EDIT ES_LEFT|WS_BORDER|WS_TABSTOP +// COMBOBOX COMBOBOX None +// ICON STATIC SS_ICON +// SCROLLBAR SCROLLBAR None +/// + +#define WS_OVERLAPPED 0x00000000L +#define WS_POPUP 0x80000000L +#define WS_CHILD 0x40000000L +#define WS_CLIPSIBLINGS 0x04000000L +#define WS_CLIPCHILDREN 0x02000000L +#define WS_VISIBLE 0x10000000L +#define WS_DISABLED 0x08000000L +#define WS_MINIMIZE 0x20000000L +#define WS_MAXIMIZE 0x01000000L +#define WS_CAPTION 0x00C00000L +#define WS_BORDER 0x00800000L +#define WS_DLGFRAME 0x00400000L +#define WS_VSCROLL 0x00200000L +#define WS_HSCROLL 0x00100000L +#define WS_SYSMENU 0x00080000L +#define WS_THICKFRAME 0x00040000L +#define WS_MINIMIZEBOX 0x00020000L +#define WS_MAXIMIZEBOX 0x00010000L +#define WS_GROUP 0x00020000L +#define WS_TABSTOP 0x00010000L + +// other aliases +#define WS_OVERLAPPEDWINDOW (WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX) +#define WS_POPUPWINDOW (WS_POPUP | WS_BORDER | WS_SYSMENU) +#define WS_CHILDWINDOW (WS_CHILD) +#define WS_TILED WS_OVERLAPPED +#define WS_ICONIC WS_MINIMIZE +#define WS_SIZEBOX WS_THICKFRAME +#define WS_TILEDWINDOW WS_OVERLAPPEDWINDOW + +#define WS_EX_DLGMODALFRAME 0x00000001L +#define WS_EX_NOPARENTNOTIFY 0x00000004L +#define WS_EX_TOPMOST 0x00000008L +#define WS_EX_ACCEPTFILES 0x00000010L +#define WS_EX_TRANSPARENT 0x00000020L + +#define BS_PUSHBUTTON 0x00000000L +#define BS_DEFPUSHBUTTON 0x00000001L +#define BS_CHECKBOX 0x00000002L +#define BS_AUTOCHECKBOX 0x00000003L +#define BS_RADIOBUTTON 0x00000004L +#define BS_3STATE 0x00000005L +#define BS_AUTO3STATE 0x00000006L +#define BS_GROUPBOX 0x00000007L +#define BS_USERBUTTON 0x00000008L +#define BS_AUTORADIOBUTTON 0x00000009L +#define BS_OWNERDRAW 0x0000000BL +#define BS_LEFTTEXT 0x00000020L + +#define ES_LEFT 0x00000000L +#define ES_CENTER 0x00000001L +#define ES_RIGHT 0x00000002L +#define ES_MULTILINE 0x00000004L +#define ES_UPPERCASE 0x00000008L +#define ES_LOWERCASE 0x00000010L +#define ES_PASSWORD 0x00000020L +#define ES_AUTOVSCROLL 0x00000040L +#define ES_AUTOHSCROLL 0x00000080L +#define ES_NOHIDESEL 0x00000100L +#define ES_OEMCONVERT 0x00000400L +#define ES_READONLY 0x00000800L +#define ES_WANTRETURN 0x00001000L + +#define LBS_NOTIFY 0x0001L +#define LBS_SORT 0x0002L +#define LBS_NOREDRAW 0x0004L +#define LBS_MULTIPLESEL 0x0008L +#define LBS_OWNERDRAWFIXED 0x0010L +#define LBS_OWNERDRAWVARIABLE 0x0020L +#define LBS_HASSTRINGS 0x0040L +#define LBS_USETABSTOPS 0x0080L +#define LBS_NOINTEGRALHEIGHT 0x0100L +#define LBS_MULTICOLUMN 0x0200L +#define LBS_WANTKEYBOARDINPUT 0x0400L +#define LBS_EXTENDEDSEL 0x0800L +#define LBS_DISABLENOSCROLL 0x1000L + +#define SS_LEFT 0x00000000L +#define SS_CENTER 0x00000001L +#define SS_RIGHT 0x00000002L +#define SS_ICON 0x00000003L +#define SS_BLACKRECT 0x00000004L +#define SS_GRAYRECT 0x00000005L +#define SS_WHITERECT 0x00000006L +#define SS_BLACKFRAME 0x00000007L +#define SS_GRAYFRAME 0x00000008L +#define SS_WHITEFRAME 0x00000009L +#define SS_SIMPLE 0x0000000BL +#define SS_LEFTNOWORDWRAP 0x0000000CL +#define SS_BITMAP 0x0000000EL + +// +// Debug Format +// + +typedef struct _IMAGE_DEBUG_DIRECTORY { + DWORD Characteristics; + DWORD TimeDateStamp; + WORD MajorVersion; + WORD MinorVersion; + DWORD Type; + DWORD SizeOfData; + DWORD AddressOfRawData; + DWORD PointerToRawData; +} IMAGE_DEBUG_DIRECTORY, *PIMAGE_DEBUG_DIRECTORY; + +#define IMAGE_DEBUG_TYPE_UNKNOWN 0 +#define IMAGE_DEBUG_TYPE_COFF 1 +#define IMAGE_DEBUG_TYPE_CODEVIEW 2 +#define IMAGE_DEBUG_TYPE_FPO 3 +#define IMAGE_DEBUG_TYPE_MISC 4 +#define IMAGE_DEBUG_TYPE_EXCEPTION 5 +#define IMAGE_DEBUG_TYPE_FIXUP 6 +#define IMAGE_DEBUG_TYPE_OMAP_TO_SRC 7 +#define IMAGE_DEBUG_TYPE_OMAP_FROM_SRC 8 + + +typedef struct _IMAGE_DEBUG_MISC { + DWORD DataType; // type of misc data, see defines + DWORD Length; // total length of record, rounded to four + // byte multiple. + BOOLEAN Unicode; // TRUE if data is unicode string + BYTE Reserved[ 3 ]; + BYTE Data[ 1 ]; // Actual data +} IMAGE_DEBUG_MISC, *PIMAGE_DEBUG_MISC; + + +// +// Debugging information can be stripped from an image file and placed +// in a separate .DBG file, whose file name part is the same as the +// image file name part (e.g. symbols for CMD.EXE could be stripped +// and placed in CMD.DBG). This is indicated by the IMAGE_FILE_DEBUG_STRIPPED +// flag in the Characteristics field of the file header. The beginning of +// the .DBG file contains the following structure which captures certain +// information from the image file. This allows a debug to proceed even if +// the original image file is not accessable. This header is followed by +// zero of more IMAGE_SECTION_HEADER structures, followed by zero or more +// IMAGE_DEBUG_DIRECTORY structures. The latter structures and those in +// the image file contain file offsets relative to the beginning of the +// .DBG file. +// +// If symbols have been stripped from an image, the IMAGE_DEBUG_MISC structure +// is left in the image file, but not mapped. This allows a debugger to +// compute the name of the .DBG file, from the name of the image in the +// IMAGE_DEBUG_MISC structure. +// + +typedef struct _IMAGE_SEPARATE_DEBUG_HEADER { + WORD Signature; + WORD Flags; + WORD Machine; + WORD Characteristics; + DWORD TimeDateStamp; + DWORD CheckSum; + DWORD ImageBase; + DWORD SizeOfImage; + DWORD NumberOfSections; + DWORD ExportedNamesSize; + DWORD DebugDirectorySize; + DWORD SectionAlignment; + DWORD Reserved[2]; +} IMAGE_SEPARATE_DEBUG_HEADER, *PIMAGE_SEPARATE_DEBUG_HEADER; + +#define IMAGE_SEPARATE_DEBUG_SIGNATURE 0x4944 + +#define IMAGE_SEPARATE_DEBUG_FLAGS_MASK 0x8000 +#define IMAGE_SEPARATE_DEBUG_MISMATCH 0x8000 // when DBG was updated, the + // old checksum didn't match. + + +// +// End Image Format +// + + +#define SIZE_OF_NT_SIGNATURE sizeof (DWORD) +#define MAXRESOURCENAME 13 + +/* global macros to define header offsets into file */ +/* offset to PE file signature */ +#define NTSIGNATURE(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew)) + +/* DOS header identifies the NT PEFile signature dword + the PEFILE header exists just after that dword */ +#define PEFHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE)) + +/* PE optional header is immediately after PEFile header */ +#define OPTHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE + \ + sizeof (IMAGE_FILE_HEADER))) + +/* section headers are immediately after PE optional header */ +#define SECHDROFFSET(a) ((LPVOID)((BYTE *)a + \ + ((PIMAGE_DOS_HEADER)a)->e_lfanew + \ + SIZE_OF_NT_SIGNATURE + \ + sizeof (IMAGE_FILE_HEADER) + \ + sizeof (IMAGE_OPTIONAL_HEADER))) + + +typedef struct tagImportDirectory + { + DWORD dwRVAFunctionNameList; + DWORD dwUseless1; + DWORD dwUseless2; + DWORD dwRVAModuleName; + DWORD dwRVAFunctionAddressList; + }IMAGE_IMPORT_MODULE_DIRECTORY, * PIMAGE_IMPORT_MODULE_DIRECTORY; + + +/* global prototypes for functions in pefile.c */ +/* PE file header info */ +BOOL WINAPI GetDosHeader (LPVOID, PIMAGE_DOS_HEADER); +DWORD WINAPI ImageFileType (LPVOID); +BOOL WINAPI GetPEFileHeader (LPVOID, PIMAGE_FILE_HEADER); + +/* PE optional header info */ +BOOL WINAPI GetPEOptionalHeader (LPVOID, PIMAGE_OPTIONAL_HEADER); +LPVOID WINAPI GetModuleEntryPoint (LPVOID); +int WINAPI NumOfSections (LPVOID); +LPVOID WINAPI GetImageBase (LPVOID); +LPVOID WINAPI ImageDirectoryOffset (LPVOID, DWORD); +LPVOID WINAPI ImageDirectorySection (LPVOID, DWORD); + +/* PE section header info */ +//int WINAPI GetSectionNames (LPVOID, HANDLE, char **); +int WINAPI GetSectionNames (LPVOID, char **); +BOOL WINAPI GetSectionHdrByName (LPVOID, PIMAGE_SECTION_HEADER, char *); + +// +// structur to store string tokens +// +typedef struct _Str_P { + char flag; // string_flag '@' or '%' or '#' + char *pos; // starting postion of string + int length; // length of string + BOOL wasString; // if it were stringMode or not +} Str_P; + +/* import section info */ +int WINAPI GetImportModuleNames (LPVOID, char **); +int WINAPI GetImportFunctionNamesByModule (LPVOID, char *, char **); + +// import function name reporting +int WINAPI GetStringLength (char *); +void WINAPI GetPreviousParamString (char *, char *); +void WINAPI TranslateParameters (char **, char **, char **); +BOOL WINAPI StringExpands (char **, char **, char **, Str_P *); +LPVOID WINAPI TranslateFunctionName (char *); + +/* export section info */ +int WINAPI GetExportFunctionNames (LPVOID, char **); + +/* resource section info */ +int WINAPI GetNumberOfResources (LPVOID); +int WINAPI GetListOfResourceTypes (LPVOID, char **); +int WINAPI MenuScan (int *, WORD **); +int WINAPI MenuFill (char **, WORD **); +void WINAPI StrangeMenuFill (char **, WORD **, int); +int WINAPI GetContentsOfMenu (LPVOID, char **); +int WINAPI PrintMenu (int, char **); +int WINAPI PrintStrangeMenu (char **); + +/* debug section info */ +BOOL WINAPI IsDebugInfoStripped (LPVOID); +int WINAPI RetrieveModuleName (LPVOID, char **); +BOOL WINAPI IsDebugFile (LPVOID); +BOOL WINAPI GetSeparateDebugHeader (LPVOID, PIMAGE_SEPARATE_DEBUG_HEADER); + + +/* copy dos header information to structure */ +BOOL WINAPI GetDosHeader ( + LPVOID lpFile, + PIMAGE_DOS_HEADER pHeader) +{ + /* dos header rpresents first structure of bytes in file */ + if (*(USHORT *)lpFile == IMAGE_DOS_SIGNATURE) + bcopy(lpFile, (LPVOID)pHeader, sizeof (IMAGE_DOS_HEADER)); + else + return FALSE; + + return TRUE; +} + + + + +/* return file signature */ +DWORD WINAPI ImageFileType ( + LPVOID lpFile) +{ + /* dos file signature comes first */ + if (*(USHORT *)lpFile == IMAGE_DOS_SIGNATURE) + { + /* determine location of PE File header from dos header */ + if (LOWORD (*(DWORD *)NTSIGNATURE (lpFile)) == IMAGE_OS2_SIGNATURE || + LOWORD (*(DWORD *)NTSIGNATURE (lpFile)) == IMAGE_OS2_SIGNATURE_LE) + return (DWORD)LOWORD(*(DWORD *)NTSIGNATURE (lpFile)); + + else if (*(DWORD *)NTSIGNATURE (lpFile) == IMAGE_NT_SIGNATURE) + return IMAGE_NT_SIGNATURE; + + else + return IMAGE_DOS_SIGNATURE; + } + + else + /* unknown file type */ + return 0; +} + + + + +/* copy file header information to structure */ +BOOL WINAPI GetPEFileHeader ( + LPVOID lpFile, + PIMAGE_FILE_HEADER pHeader) +{ + /* file header follows dos header */ + if (ImageFileType (lpFile) == IMAGE_NT_SIGNATURE) + bcopy(PEFHDROFFSET (lpFile), (LPVOID)pHeader, sizeof (IMAGE_FILE_HEADER)); + else + return FALSE; + + return TRUE; +} + + + + + +/* copy optional header info to structure */ +BOOL WINAPI GetPEOptionalHeader ( + LPVOID lpFile, + PIMAGE_OPTIONAL_HEADER pHeader) +{ + /* optional header follows file header and dos header */ + if (ImageFileType (lpFile) == IMAGE_NT_SIGNATURE) + bcopy (OPTHDROFFSET (lpFile), (LPVOID)pHeader, sizeof (IMAGE_OPTIONAL_HEADER)); + else + return FALSE; + + return TRUE; +} + + + + +/* function returns the entry point for an exe module lpFile must + be a memory mapped file pointer to the beginning of the image file */ +LPVOID WINAPI GetModuleEntryPoint ( + LPVOID lpFile) +{ + PIMAGE_OPTIONAL_HEADER poh = (PIMAGE_OPTIONAL_HEADER)OPTHDROFFSET (lpFile); + + if (poh != NULL) + return (LPVOID)(poh->AddressOfEntryPoint); + else + return NULL; +} + + + + +/* return the total number of sections in the module */ +int WINAPI NumOfSections ( + LPVOID lpFile) +{ + /* number os sections is indicated in file header */ + return ((int)((PIMAGE_FILE_HEADER)PEFHDROFFSET (lpFile))->NumberOfSections); +} + + + + +/* retrieve entry point */ +LPVOID WINAPI GetImageBase ( + LPVOID lpFile) +{ + PIMAGE_OPTIONAL_HEADER poh = (PIMAGE_OPTIONAL_HEADER)OPTHDROFFSET (lpFile); + + if (poh != NULL) + return (LPVOID)(poh->ImageBase); + else + return NULL; +} + + + +// +// This function is written by sang cho +// .. october 5, 1997 +// +/* function returns the actual address of given RVA, lpFile must + be a memory mapped file pointer to the beginning of the image file */ +LPVOID WINAPI GetActualAddress ( + LPVOID lpFile, + DWORD dwRVA) +{ + PIMAGE_OPTIONAL_HEADER poh = (PIMAGE_OPTIONAL_HEADER)OPTHDROFFSET (lpFile); + PIMAGE_SECTION_HEADER psh = (PIMAGE_SECTION_HEADER)SECHDROFFSET (lpFile); + int nSections = NumOfSections (lpFile); + int i = 0; + + if (dwRVA == NULL) return NULL; + if (dwRVA & 0x80000000) + { + //return (LPVOID)dwRVA; + printf ("\n$$ what is going on $$"); + exit (0); + } + + /* locate section containing image directory */ + while (i++VirtualAddress <= (DWORD)dwRVA && + psh->VirtualAddress + psh->SizeOfRawData > (DWORD)dwRVA) + break; + psh++; + } + + if (i > nSections) + return NULL; + + /* return image import directory offset */ + return (LPVOID)(((int)lpFile + (int)dwRVA - psh->VirtualAddress) + + (int)psh->PointerToRawData); +} + + +// +// This function is modified by sang cho +// +// +/* return offset to specified IMAGE_DIRECTORY entry */ +LPVOID WINAPI ImageDirectoryOffset ( + LPVOID lpFile, + DWORD dwIMAGE_DIRECTORY) +{ + PIMAGE_OPTIONAL_HEADER poh = (PIMAGE_OPTIONAL_HEADER)OPTHDROFFSET (lpFile); + PIMAGE_SECTION_HEADER psh = (PIMAGE_SECTION_HEADER)SECHDROFFSET (lpFile); + int nSections = NumOfSections (lpFile); + int i = 0; + LPVOID VAImageDir; + + /* must be 0 thru (NumberOfRvaAndSizes-1) */ + if (dwIMAGE_DIRECTORY >= poh->NumberOfRvaAndSizes) + return NULL; + + /* locate specific image directory's relative virtual address */ + VAImageDir = (LPVOID)poh->DataDirectory[dwIMAGE_DIRECTORY].VirtualAddress; + + if (VAImageDir == NULL) return NULL; + /* locate section containing image directory */ + while (i++VirtualAddress <= (DWORD)VAImageDir && + psh->VirtualAddress + psh->SizeOfRawData > (DWORD)VAImageDir) + break; + psh++; + } + + if (i > nSections) + return NULL; + + /* return image import directory offset */ + return (LPVOID)(((int)lpFile + (int)VAImageDir - psh->VirtualAddress) + + (int)psh->PointerToRawData); +} + + +/* function retrieve names of all the sections in the file */ +int WINAPI GetSectionNames ( + LPVOID lpFile, + char **pszSections) +{ + int nSections = NumOfSections (lpFile); + int i, nCnt = 0; + PIMAGE_SECTION_HEADER psh; + char *ps; + + + if (ImageFileType (lpFile) != IMAGE_NT_SIGNATURE || + (psh = (PIMAGE_SECTION_HEADER)SECHDROFFSET (lpFile)) == NULL) + return 0; + + /* count the number of chars used in the section names */ + for (i=0; iName, szSection)) + { + /* copy data to header */ + bcopy ((LPVOID)psh, (LPVOID)sh, sizeof (IMAGE_SECTION_HEADER)); + return TRUE; + } + else psh++; + } + } + return FALSE; +} + + + +// +// This function is modified by sang cho +// +// +/* get import modules names separated by null terminators, return module count */ +int WINAPI GetImportModuleNames ( + LPVOID lpFile, + char **pszModules) +{ + PIMAGE_IMPORT_MODULE_DIRECTORY pid = (PIMAGE_IMPORT_MODULE_DIRECTORY) + ImageDirectoryOffset (lpFile, IMAGE_DIRECTORY_ENTRY_IMPORT); + // + // sometimes there may be no section for idata or edata + // instead rdata or data section may contain these sections .. + // or even module names or function names are in different section. + // so that's why we need to get actual address of RVAs each time. + // ...................sang cho.................. + // + // PIMAGE_SECTION_HEADER psh = (PIMAGE_SECTION_HEADER) + // ImageDirectorySection (lpFile, IMAGE_DIRECTORY_ENTRY_IMPORT); + // BYTE *pData = (BYTE *)pid; + DWORD *pdw = (DWORD *)pid; + int nCnt = 0, nSize = 0, i; + char *pModule[1024]; /* hardcoded maximum number of modules?? */ + int pidTab[1024]; + char *psz; + + if (pid == NULL) return 0; + + // pData = (BYTE *)((int)lpFile + psh->PointerToRawData - psh->VirtualAddress); + + /* extract all import modules */ + while (pid->dwRVAModuleName) + { + /* allocate temporary buffer for absolute string offsets */ + //pModule[nCnt] = (char *)(pData + pid->dwRVAModuleName); + pModule[nCnt] = (char *)GetActualAddress (lpFile, pid->dwRVAModuleName); + pidTab[nCnt] = (int)pid; + nSize += strlen (pModule[nCnt]) + 1 + 4; + + /* increment to the next import directory entry */ + pid++; + nCnt++; + } + + /* copy all strings to one chunk of memory */ + *pszModules = (char *)calloc(nSize, 1); + piNameBuffSize = nSize; + psz = *pszModules; + for (i=0; iPointerToRawData - psh->VirtualAddress); + + /* find module's pid */ + //while (pid->dwRVAModuleName && + // strcmp (pszModule, (char *)GetActualAddress(lpFile, pid->dwRVAModuleName))) + //pid++; + + pid = (PIMAGE_IMPORT_MODULE_DIRECTORY)(*(DWORD *)pszModule); + + //fprintf(stderr, "\npid=%08X", pid),getch(); + + /* exit if the module is not found */ + if (!pid->dwRVAModuleName) + return 0; + + // I am doing this to get rid of .dll from module name + strcpy (name, pszModule+4); + mnlength = strlen (pszModule+4); + for (i=0; idwRVAFunctionNameList; + + // IMAGE_IMPORT_BY_NAME OR IMAGE_THUNK_DATA + // modified by Sang Cho + + + //fprintf(stderr,"pid = %08X dwFunctionName = %08X name = %s", + //(int)pid-(int)lpFile, dwFunctionName,name),getch(); + + // modified by sang cho 1998.1.24 + + if (dwFunctionName==0) dwFunctionName = pid->dwRVAFunctionAddressList; + + while (dwFunctionName && + *(pdw=(DWORD *)GetActualAddress (lpFile, dwFunctionName)) ) + { + if ((*pdw) & 0x80000000 ) nSize += mnlength + 11 + 1 + 6; + else nSize += strlen ((char *)GetActualAddress (lpFile, *pdw+2)) + 1+6; + dwFunctionName += 4; + nCnt++; + } + + /* allocate memory for function names */ + *pszFunctions = (char *)calloc (nSize, 1); + psz = *pszFunctions; + + // + // I modified this part to store function address (4 bytes), + // ord number (2 bytes), + // and name strings (which was there originally) + // so that's why there are 6 more bytes...... +6, or +4 and +2 etc. + // these informations are used where they are needed. + // ...........sang cho.................. + // + /* copy function names to mempry pointer */ + dwFunctionName = pid->dwRVAFunctionNameList; + // modified by sang cho 1998.1.24 + if (dwFunctionName==0) dwFunctionName = pid->dwRVAFunctionAddressList; + dwFunctionAddress = pid->dwRVAFunctionAddressList; + while (dwFunctionName && + *(pdw=(DWORD *)GetActualAddress (lpFile, dwFunctionName)) ) + { + if ((*pdw) & 0x80000000) + { + *(int *)psz=(int)(*(DWORD *)GetActualAddress (lpFile, dwFunctionAddress)); + psz += 4; + *(short *)psz=*(short *)pdw; + psz += 2; + sprintf(buff, "%s:NoName%04d", name, nnid++); + strcpy (psz, buff); psz += strlen (buff) + 1; + } + else + { + r=*(int *)psz=(int)(*(DWORD *)GetActualAddress (lpFile, dwFunctionAddress)); + psz += 4; + *(short *)psz=(*(short *)GetActualAddress(lpFile, *pdw)); + psz += 2; rr=(int)GetActualAddress(lpFile, *pdw + 2); + strcpy (psz, (char *)rr); + psz += strlen ((char *)GetActualAddress(lpFile, *pdw + 2)) + 1; + + // this one is needed to link import function names to codes.. + k.class=0; k.c_ref= r; k.c_pos=-rr; + MyBtreeInsert(&k); + k.class=0; k.c_ref=-(rr); k.c_pos=(int)pszModule+4; + MyBtreeInsert(&k); + } + dwFunctionName += 4; + dwFunctionAddress += 4; + } + + return nCnt; +} + + + + +// +// This function is written by sang cho +// October 6, 1997 +// +/* get numerically expressed string length */ +int WINAPI GetStringLength ( + char *psz) +{ + if (!isdigit (*psz)) return 0; + if (isdigit (*(psz+1))) return (*psz - '0')*10 + *(psz+1) - '0'; + else return *psz - '0'; +} + + + + +// +// This function is written by sang cho +// October 12, 1997 +// + +/* translate parameter part of condensed name */ +void WINAPI GetPreviousParamString ( + char *xpin, // read-only source + char *xpout) // translated result +{ + int n=0; + char *pin, *pout; + + pin = xpin; + pout = xpout; + + pin--; + if (*pin == ',') pin--; + else { printf ("\n **error PreviousParamString1 char = %c", *pin); exit(0); } + + while (*pin) + { + if (*pin == '>') n++; + else if (*pin == '<') n--; + else if (*pin == ')') n++; + + if (n > 0) + { + if (*pin == '(') n--; + } + else if (strchr (",(", *pin)) break; + pin--; + } + + //printf("\n ----- %s", pin); + if (strchr (",(", *pin)) {pin++;} // printf("\n %s", pin); } + else { printf ("\n **error PreviousParamString2"); exit(0); } + + n = xpin - pin - 1; + strncpy (pout, pin, n); + *(pout + n) = 0; +} + + + + +// +// This function is written by sang cho +// October 10, 1997 +// + +/* translate parameter part of condensed name */ +void WINAPI TranslateParameters ( + char **ppin, // read-only source + char **ppout, // translated result + char **pps) // parameter stack +{ + int i, n; + char c; + char name[128]; + char *pin, *pout, *ps; + + //printf(" %c ", **in); + pin = *ppin; + pout = *ppout; + ps = *pps; + c = *pin; + switch (c) + { + // types processing + case 'b': strcpy (pout, "byte"); pout += 4; pin++; break; + case 'c': strcpy (pout, "char"); pout += 4; pin++; break; + case 'd': strcpy (pout, "double"); pout += 6; pin++; break; + case 'f': strcpy (pout, "float"); pout += 5; pin++; break; + case 'g': strcpy (pout, "long double");pout += 11; pin++; break; + case 'i': strcpy (pout, "int"); pout += 3; pin++; break; + case 'l': strcpy (pout, "long"); pout += 4; pin++; break; + case 's': strcpy (pout, "short"); pout += 5; pin++; break; + case 'v': strcpy (pout, "void"); pout += 4; pin++; break; + // postfix processing + case 'M': + case 'p': + if (*(pin+1) == 'p') { *ps++ = 'p'; pin += 2; } + else { *ps++ = '*'; pin++; } + *ppin = pin; *ppout = pout; *pps = ps; + return; + case 'q': + *pout++ = '('; pin++; + *ps++ = 'q'; + *ppin = pin; *ppout = pout; *pps = ps; + return; + case 'r': + if (*(pin+1) == 'p') { *ps++ = 'r'; pin += 2; } + else { *ps++ = '&'; pin++; } + *ppin = pin; *ppout = pout; *pps = ps; + return; + // repeat processing + case 't': + if (isdigit(*(pin+1))) + { + n = *(pin+1) - '0'; pin++; pin++; + GetPreviousParamString (pout, name); + strcpy (pout, name); pout += strlen (name); + for (i=1; i>"); pout += 11; pin += 4; } + else if (strncmp (pin, "binc", 4) == 0) + { strcpy (pout, "operator ++"); pout += 11; pin += 4; } + else if (strncmp (pin, "bdec", 4) == 0) + { strcpy (pout, "operator --"); pout += 11; pin += 4; } + else if (strncmp (pin, "badd", 4) == 0) + { strcpy (pout, "operator +"); pout += 10; pin += 4; } + else if (strncmp (pin, "brplu", 5) == 0) + { strcpy (pout, "operator +="); pout += 11; pin += 5; } + else if (strncmp (pin, "bdiv", 4) == 0) + { strcpy (pout, "operator /"); pout += 10; pin += 4; } + else if (strncmp (pin, "brdiv", 5) == 0) + { strcpy (pout, "operator /="); pout += 11; pin += 5; } + else if (strncmp (pin, "bmul", 4) == 0) + { strcpy (pout, "operator *"); pout += 10; pin += 4; } + else if (strncmp (pin, "brmul", 5) == 0) + { strcpy (pout, "operator *="); pout += 11; pin += 5; } + else if (strncmp (pin, "basg", 4) == 0) + { strcpy (pout, "operator ="); pout += 10; pin += 4; } + else if (strncmp (pin, "beql", 4) == 0) + { strcpy (pout, "operator =="); pout += 11; pin += 4; } + else if (strncmp (pin, "bneq", 4) == 0) + { strcpy (pout, "operator !="); pout += 11; pin += 4; } + else if (strncmp (pin, "bor", 3) == 0) + { strcpy (pout, "operator |"); pout += 10; pin += 3; } + else if (strncmp (pin, "bror", 4) == 0) + { strcpy (pout, "operator |="); pout += 11; pin += 4; } + else if (strncmp (pin, "bcmp", 4) == 0) + { strcpy (pout, "operator ~"); pout += 10; pin += 4; } + else if (strncmp (pin, "bnot", 4) == 0) + { strcpy (pout, "operator !"); pout += 10; pin += 4; } + else if (strncmp (pin, "band", 4) == 0) + { strcpy (pout, "operator &"); pout += 10; pin += 4; } + else if (strncmp (pin, "brand", 5) == 0) + { strcpy (pout, "operator &="); pout += 11; pin += 5; } + else if (strncmp (pin, "bxor", 4) == 0) + { strcpy (pout, "operator ^"); pout += 10; pin += 4; } + else if (strncmp (pin, "brxor", 5) == 0) + { strcpy (pout, "operator ^="); pout += 11; pin += 5; } + else + { + strcpy (pout, "!$$$!"); pout += 5; + } + *ppin = pin; *ppout = pout; *pps = ps; + return stringMode; +} // end of '$' processing + + + +//---------------------------------------------------------------------- +// structure to store string tokens +//---------------------------------------------------------------------- +//typedef struct _Str_P { +// char flag; // string_flag '@' or '%' or '#' +// char *pos; // starting postion of string +// int length; // length of string +// BOOL wasString; // if it were stringMode or not +//} Str_P; +//---------------------------------------------------------------------- +// +// I think I knocked it down finally. But who knows? +// october 12, 1997 ... sang +// +// well I have to rewrite whole part of TranslateFunctionName.. +// this time I am a little bit more experienced than 5 days ago. +// or am i??? anyway i use stacks instead of recurcive calls +// and i hope this will take care of every symptoms i have experienced.. +// october 10, 1997 .... sang +// It took a lot of time for me to figure out what is all about.... +// but still some prefixes like z (static) +// -- or some types like b (byte) ,g (long double) ,s (short) -- +// -- or postfix like M ( * ) +// -- or $or ( & ) which is pretty wierd. .. added.. october 12 +// -- also $t business is quite tricky too. (templates) +// there may be a lot of things undiscovered yet.... +// I am not so sure my interpretation is correct or not +// If I am wrong please let me know. +// october 8, 1997 .... sang +// +// +// This function is written by sang cho +// October 5, 1997 +// +/* translate condesed import function name */ +LPVOID WINAPI TranslateFunctionName ( + char *psz) +{ + + + int i, j, n; + char c, cc; + + static char buff[512]; // result of translation + + int is=0; + char pStack[32]; // parameter processing stack + Str_P sStack[32]; // String processing stack + Str_P tok; // String token + Str_P c_str; // current string + + int iend=0; + char *endTab[8]; // end of string position check + + char *ps; + char *pin, *pout; + BOOL stringMode=TRUE; + + if (*psz != '@') return psz; + pin = psz; + pout = buff; + ps = pStack; + + //................................................................ + // serious users may need to run the following code. + // so I may need to include some flag options... + // If you want to know about how translation is done, + // you can just revive following line and you can see it. + // october 6, 1997 ... sang cho + //printf ("\n................................... %s", psz); // for debugging... + + //pa = pb = pout; + pin++; + tok.flag = 'A'; tok.pos = pout; tok.length = 0; tok.wasString = stringMode; + sStack[is++] = tok; // initialize sStack with dummy marker + + while (*pin) + { + while (*pin) + { + c = *pin; + + //--------------------------------------------- + // check for the end of number specified string + //--------------------------------------------- + + if (iend>0) + { + for (i=0;i 1) *pout++ = *pin++; + + //------------------------------------------------ + // parameter part processing: '$' met + //------------------------------------------------ + + else // parameter processing + { + if (!isdigit (c)) TranslateParameters (&pin, &pout, &ps); + else // number specified string processing + { + n = GetStringLength (pin); + if (n<10) pin++; else pin += 2; + + // push '#' token + //if (*pin) + //printf("\n push # token .. char = %c", *pin); + //else printf("\n push percent token..next char = NULL"); + tok.flag = '#'; tok.pos = pout; + tok.length = 0; tok.wasString = stringMode; + sStack[is++] = tok; + + // mark end of input string + endTab[iend++] = pin + n; + stringMode = TRUE; + } + } + } // end of inner while loop + // + // beginning of new string or end of string ( quotation mark ) + // + if (c == '%') + { + pin++; // anyway we have to proceed... + tok = sStack[is-1]; // get top of the sStack + if (tok.flag == '%') + { + // pop '%' token and set c_str + //if (*pin) + //printf("\n pop percent token..next char = %c", *pin); + //else printf("\n pop percent token..next char = NULL"); + is--; + c_str = tok; c_str.length = pout - c_str.pos; + if (*(ps-1) == 't') + { + *pout++ = '>'; ps--; + stringMode = tok.wasString; + } + else { printf("\n**some string error3** stack = %c", *(ps-1)); + exit(0); } + } + else if (tok.flag == 'A' || tok.flag == '#') + { + // push '%' token + //if (*pin) + //printf("\n push percent token..next char = %c", *pin); + //else printf("\n push percent token..next char = NULL"); + tok.flag = '%'; tok.pos = pout; tok.length = 0; + tok.wasString = stringMode; + sStack[is++] = tok; + } + else { printf("\n**some string error5**"); exit(0); } + } + // + // sometimes we need string to use as constructor name or destructor name + // + else if (c == '@') // get string from previous marker upto here. + { + pin++; + tok = sStack[is-1]; + c_str.flag = 'S'; + c_str.pos = tok.pos; + c_str.length = pout - tok.pos; + c_str.wasString = stringMode; + *pout++ = ':'; *pout++ = ':'; + } + // + // we need to take care of parameter control sequence + // + else if (c == '$') // need to precess template or parameter part + { + pin++; + if (stringMode) + stringMode = StringExpands (&pin, &pout, &ps, &c_str); + else + { // template parameter mode I guess "$t" + if (is>1) + { + if (*pin == 't') pin++; + else { printf("\nMYGOODNESS1 %c", *pin); exit(0);} + //ps--; + //if (*ps == 't') *pout++ = '>'; + //else { printf("\nMYGOODNESS2"); exit(0);} + *pout++ = ','; //pin++; ..this almost blowed me.... + } + // real parameter mode I guess + // unexpected case is found ... humm what can I do... + else + { + // this is newly found twist.. it really hurts. + if (ps <= pStack) + { if (*pin == 'q') { *ps++ = 'q'; *pout++ = '('; pin++; } + else {printf("\n** I GIVEUP ***"); exit(0);} + continue; + } + ps--; + while (*ps != 'q') + { if (*ps == '*') *pout++ = '*'; + else if (*ps == '&') *pout++ = '&'; + else if (*ps == 'p'){*pout++ = '*'; *pout++ = '*'; } + else if (*ps == 'r'){*pout++ = '*'; *pout++ = '&'; } + else {printf("\n*** SOMETHING IS WRONG1*** char= %c",*pin); + exit(0);} + ps--; + } + *pout++ = ')'; + ps--; + while (*ps != 'q') + { if (*ps == '*') *pout++ = '*'; + else if (*ps == '&') *pout++ = '&'; + else if (*ps == 'p'){*pout++ = '*'; *pout++ = '*'; } + else if (*ps == 'r'){*pout++ = '*'; *pout++ = '&'; } + else {printf("\n*** SOMETHING IS WRONG2***"); exit(0);} + ps--; + } + ps++; *pout++ = ','; + } + } + } // end of '$' processing + } // end of outer while loop + // + // need to process remaining parameter stack + // + while (ps>pStack) + { + ps--; + switch(*ps) + { + case 't': *pout++ = '>'; break; + case 'q': *pout++ = ')'; break; + case 'x': strcpy (pout, " const"); pout += 6; break; + case 'r': strcpy (pout, "*&"); pout += 2; break; + case 'p': strcpy (pout, "**"); pout += 2; break; + case '&': *pout++ = '&'; break; + case '*': *pout++ = '*'; break; + default: strcpy (pout, "!4!"); pout += 3; *pout++ = *ps; + } + } + *pout = 0; + return buff; +} + + + +// +// This function is written by sang cho +// +// +/* get exported function names separated by null terminators, return count of functions */ +int WINAPI GetExportFunctionNames ( + LPVOID lpFile, + char **pszFunctions) +{ + //PIMAGE_SECTION_HEADER psh; + PIMAGE_EXPORT_DIRECTORY ped; + //DWORD dwBase; + DWORD imageBase; //=========================== + char *pfns[8192]={NULL,}; // maximum number of functions + //============================= + char buff[256]; // enough for any string ?? + char *psz; //=============================== + DWORD *pdwAddress; + DWORD *pdw1; + DWORD *pdwNames; + WORD *pwOrd; + int i, nCnt=0, ntmp=0; + int enid=0, ordBase=1; // usally ordBase is 1.... + int enames=0; + + /* get section header and pointer to data directory for .edata section */ + ped = (PIMAGE_EXPORT_DIRECTORY) + ImageDirectoryOffset(lpFile, IMAGE_DIRECTORY_ENTRY_EXPORT); + + if (ped == NULL) return 0; + + // + // sometimes there may be no section for idata or edata + // instead rdata or data section may contain these sections .. + // or even module names or function names are in different section. + // so that's why we need to get actual address each time. + // ...................sang cho.................. + // + //psh = (PIMAGE_SECTION_HEADER) + //ImageDirectorySection(lpFile, IMAGE_DIRECTORY_ENTRY_EXPORT); + + //if (psh == NULL) return 0; + + //dwBase = (DWORD)((int)lpFile + psh->PointerToRawData - psh->VirtualAddress); + + + /* determine the offset of the export function names */ + + pdwAddress = (DWORD *)GetActualAddress (lpFile, (DWORD)ped->AddressOfFunctions); + + imageBase = (DWORD)GetImageBase (lpFile); + + ordBase = ped->Base; + + if (ped->NumberOfNames > 0) + { + pdwNames = (DWORD *) + GetActualAddress (lpFile, (DWORD)ped->AddressOfNames); + pwOrd = (WORD *) + GetActualAddress (lpFile, (DWORD)ped->AddressOfNameOrdinals); + pdw1 = pdwAddress; + + /* figure out how much memory to allocate for all strings */ + for (i=0; i < (int)ped->NumberOfNames; i++) + { + nCnt += strlen ((char *) + GetActualAddress (lpFile, *(DWORD *)pdwNames)) + 1 + 6; + pdwNames++; + } + // get the number of unnamed functions + for (i=0; i < (int)ped->NumberOfFunctions; i++) + if (*pdw1++) ntmp++; + // add memory required to show unnamed functions. + if (ntmp > (int)ped->NumberOfNames) + nCnt += 18*(ntmp - (int)ped->NumberOfNames); + + /* allocate memory for function names */ + *pszFunctions = (char *)calloc (nCnt, 1); + fprintf(stderr,"GetExportFunctionNames base %p size 0x%08x\n",*pszFunctions,nCnt); + memset(*pszFunctions,0,nCnt); + peNameBuffSize=nCnt; + pdwNames = (DWORD *)GetActualAddress (lpFile, (DWORD)ped->AddressOfNames); + + /* copy string pointer to buffer */ + + for (i=0; i < (int)ped->NumberOfNames; i++) + { + pfns[(int)(*pwOrd)+ordBase] = + (char *)GetActualAddress (lpFile, *(DWORD *)pdwNames); + pdwNames++; + pwOrd++; + } + + psz = *pszFunctions; + } + + for (i=ordBase; i < (int)ped->NumberOfFunctions + ordBase; i++) + { + if (*pdwAddress > 0) + { + *(DWORD *)psz = imageBase + *pdwAddress; + psz += 4; + *(WORD *)psz = (WORD)(i); + psz += 2; + if (pfns[i]) + { + strcpy (psz, pfns[i]); + psz += strlen(psz) + 1; + } + else + { + sprintf (buff, "ExpFn%04d()", enid++); + strcpy (psz, buff); + psz += 12; + } + enames++; + } + pdwAddress++; + } + + return enames; + +} + + +/* determine the total number of resources in the section */ +int WINAPI GetNumberOfResources ( + LPVOID lpFile) +{ + PIMAGE_RESOURCE_DIRECTORY prdRoot, prdType; + PIMAGE_RESOURCE_DIRECTORY_ENTRY prde; + int nCnt=0, i; + + + /* get root directory of resource tree */ + if ((prdRoot = (PIMAGE_RESOURCE_DIRECTORY)ImageDirectoryOffset + (lpFile, IMAGE_DIRECTORY_ENTRY_RESOURCE)) == NULL) + return 0; + + /* set pointer to first resource type entry */ + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY)((DWORD)prdRoot + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + /* loop through all resource directory entry types */ + for (i=0; iNumberOfIdEntries; i++) + { + /* locate directory or each resource type */ + prdType = (PIMAGE_RESOURCE_DIRECTORY)((int)prdRoot + (int)prde->OffsetToData); + + /* mask off most significant bit of the data offset */ + prdType = (PIMAGE_RESOURCE_DIRECTORY)((DWORD)prdType ^ 0x80000000); + + /* increment count of name'd and ID'd resources in directory */ + nCnt += prdType->NumberOfNamedEntries + prdType->NumberOfIdEntries; + + /* increment to next entry */ + prde++; + } + + return nCnt; +} + + + +// +// This function is rewritten by sang cho +// +// +/* name each type of resource in the section */ +int WINAPI GetListOfResourceTypes ( + LPVOID lpFile, + char **pszResTypes) +{ + PIMAGE_RESOURCE_DIRECTORY prdRoot; + PIMAGE_RESOURCE_DIRECTORY_ENTRY prde; + char *pMem; + char buff[32]; + int nCnt, i; + DWORD prdeName; + + + /* get root directory of resource tree */ + if ((prdRoot = (PIMAGE_RESOURCE_DIRECTORY)ImageDirectoryOffset + (lpFile, IMAGE_DIRECTORY_ENTRY_RESOURCE)) == NULL) + return 0; + + /* allocate enuff space to cover all types */ + nCnt = prdRoot->NumberOfIdEntries * (MAXRESOURCENAME + 1); + *pszResTypes = (char *)calloc (nCnt, 1); + if ((pMem = *pszResTypes) == NULL) + return 0; + + /* set pointer to first resource type entry */ + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY)((DWORD)prdRoot + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + /* loop through all resource directory entry types */ + for (i=0; iNumberOfIdEntries; i++) + { + prdeName=prde->Name; + + //if (LoadString (hDll, prde->Name, pMem, MAXRESOURCENAME)) + // pMem += strlen (pMem) + 1; + // + // modified by ...................................Sang Cho.. + // I can't user M/S provied funcitons here so I have to figure out + // how to do above functions. But I can settle down with the following + // code, which works pretty good for me. + // + if (prdeName== 1){strcpy(pMem, "RT_CURSOR"); pMem+=10;} + else if (prdeName== 2){strcpy(pMem, "RT_BITMAP"); pMem+=10;} + else if (prdeName== 3){strcpy(pMem, "RT_ICON "); pMem+=10;} + else if (prdeName== 4){strcpy(pMem, "RT_MENU "); pMem+=10;} + else if (prdeName== 5){strcpy(pMem, "RT_DIALOG"); pMem+=10;} + else if (prdeName== 6){strcpy(pMem, "RT_STRING"); pMem+=10;} + else if (prdeName== 7){strcpy(pMem, "RT_FONTDIR"); pMem+=11;} + else if (prdeName== 8){strcpy(pMem, "RT_FONT "); pMem+=10;} + else if (prdeName== 9){strcpy(pMem, "RT_ACCELERATORS"); pMem+=16;} + else if (prdeName==10){strcpy(pMem, "RT_RCDATA"); pMem+=10;} + else if (prdeName==11){strcpy(pMem, "RT_MESSAGETABLE"); pMem+=16;} + else if (prdeName==12){strcpy(pMem, "RT_GROUP_CURSOR"); pMem+=16;} + else if (prdeName==14){strcpy(pMem, "RT_GROUP_ICON "); pMem+=16;} + else if (prdeName==16){strcpy(pMem, "RT_VERSION"); pMem+=11;} + else if (prdeName==17){strcpy(pMem, "RT_DLGINCLUDE "); pMem+=16;} + else if (prdeName==19){strcpy(pMem, "RT_PLUGPLAY "); pMem+=16;} + else if (prdeName==20){strcpy(pMem, "RT_VXD "); pMem+=10;} + else if (prdeName==21){strcpy(pMem, "RT_ANICURSOR "); pMem+=16;} + else if (prdeName==22){strcpy(pMem, "RT_ANIICON"); pMem+=11;} + else if (prdeName== 0x2002) + {strcpy(pMem, "RT_NEWBITMAP"); pMem+=13;} + else if (prdeName== 0x2004) + {strcpy(pMem, "RT_NEWMENU"); pMem+=11;} + else if (prdeName== 0x2005) + {strcpy(pMem, "RT_NEWDIALOG"); pMem+=13;} + else if (prdeName== 0x7fff) + {strcpy(pMem, "RT_ERROR "); pMem+=10;} + else {sprintf(buff, "RT_UNKNOWN:%08X", prdeName); + strcpy(pMem, buff); pMem+=20;} + prde++; + } + + return prdRoot->NumberOfIdEntries; +} + + + +// +// This function is written by sang cho +// October 12, 1997 +// +/* copy menu information */ +void WINAPI StrangeMenuFill ( + char **psz, // results + WORD **pMenu, // read-only + int size) +{ + WORD *pwd; + WORD *ptr, *pmax; + + pwd = *pMenu; + pmax = (WORD *)((DWORD)pwd + size); + ptr = (WORD *)(*psz); + + while (pwd < pmax) + { + *ptr++=*pwd++; + } + *psz = (char *)ptr; + *pMenu = pwd; +} + + + +// +// This function is written by sang cho +// October 1, 1997 +// +/* obtain menu information */ +int WINAPI MenuScan ( + int *len, + WORD **pMenu) +{ + int num = 0; + int ndetails; + WORD *pwd; + WORD flag, flag1; + WORD id, ispopup; + + + pwd = *pMenu; + + flag = *pwd; // so difficult to correctly code this so let's try this + pwd++; + (*len) += 2; // flag store + if ((flag & 0x0010) == 0) + { + ispopup = flag; + id = *pwd; + pwd++; + (*len) += 2; // id store + } + else + { + ispopup = flag; + } + + while (*pwd) {(*len)++; pwd++;} + (*len)++; // name and null character + pwd++; // skip double null + if ((flag & 0x0010) == 0) // normal node: done + { + *pMenu = pwd; + return (int)flag; + } + // popup node: need to go on... + while (1) + { + *pMenu = pwd; + flag1 = (WORD)MenuScan (len, pMenu); + pwd = *pMenu; + if (flag1 & 0x0080) break; + } +// fill # of details to num above + //(*len) += 2; + *pMenu = pwd; + return flag; +} + + +// +// This function is written by sang cho +// October 2, 1997 +// +/* copy menu information */ +int WINAPI MenuFill ( + char **psz, + WORD **pMenu) +{ + int num = 0; + int ndetails; + char *ptr, *pTemp; + WORD *pwd; + WORD flag, flag1; + WORD id, ispopup; + + ptr = *psz; + pwd = *pMenu; + //flag = (*(PIMAGE_POPUP_MENU_ITEM *)pwd)->fItemFlags; + flag = *pwd; // so difficult to correctly code this so let's try this + pwd++; + if ((flag & 0x0010) == 0) + { + *(WORD *)ptr = flag; // flag store + ptr += 2; + *(WORD *)ptr = id = *pwd; // id store + ptr += 2; + pwd++; + } + else + { + *(WORD *)ptr = flag; // flag store + ptr += 2; + } + + while (*pwd) // name extract + { + *ptr = *(char *)pwd; + ptr++; pwd++; + } //name and null character + *ptr=0; + ptr++; + pwd++; // skip double null + + if ((flag & 0x0010) == 0) // normal node: done + { + *pMenu = pwd; + *psz = ptr; + return (int)flag; + } + //pTemp = ptr; + //ptr += 2; + // popup node: need to go on... + while (1) + { + //num++; + *pMenu = pwd; + *psz = ptr; + flag1 = (WORD)MenuFill (psz, pMenu); + pwd = *pMenu; + ptr = *psz; + if (flag1 & 0x0080) break; + } +// fill # of details to num above + //*(WORD *)pTemp = (WORD)num; + *pMenu = pwd; + *psz = ptr; + return flag; +} + + +// +//============================================================================== +// The following program is based on preorder-tree-traversal. +// once you understand how to traverse..... +// the rest is pretty straight forward. +// still we need to scan it first and fill it next time. +// and finally we can print it. +// +// This function is written by sang cho +// September 29, 1997 +// revised october 2, 1997 +// revised october 12, 1997 +// .............................................................................. +// ------------------------------------------------------------------------------ +// I use same structure - which is used in P.E. programs - for my reporting. +// So, my structure is as follows: +// # of menu name is stored else where ( in directory I suppose ) +// supermenuname null terminated string, only ascii is considered. +// flag tells : node is a leaf or a internal node. +// popupname null terminated string +// +// flag normal menu flag (leaf node) +// id normal menu id +// name normal menu name +// or or +// flag popup menu flag (internal node) +// popupname popup menu name +// +// flag it may folows +// id normal menu id +// name normal menu name +// or or +// flag popup menu +// popupname popup menu name +// ......... +// it goes on like this, +// but usually, it only goes a few steps,... +// ------------------------------------------------------------------------------ +/* scan menu and copy menu */ +int WINAPI GetContentsOfMenu ( + LPVOID lpFile, + char **pszResTypes) +{ + PIMAGE_RESOURCE_DIRECTORY prdType, prdName, prdLanguage; + PIMAGE_RESOURCE_DIRECTORY_ENTRY prde, prde1; + PIMAGE_RESOURCE_DIR_STRING_U pMenuName; + PIMAGE_RESOURCE_DATA_ENTRY prData; + //PIMAGE_SECTION_HEADER psh = (PIMAGE_SECTION_HEADER) + //ImageDirectorySection (lpFile, IMAGE_DIRECTORY_ENTRY_RESOURCE); + PIMAGE_MENU_HEADER pMenuHeader; + PIMAGE_POPUP_MENU_ITEM pPopup; + PIMAGE_NORMAL_MENU_ITEM pNormal; + char buff[32]; + int nCnt=0, i, j; + int num=0; + int size; + int sLength, nMenus; + WORD flag; + WORD *pwd; + DWORD prdeName; + //DWORD dwBase; obsolete + char *pMem, *pTemp; + BOOL isStrange = FALSE; + + + /* get root directory of resource tree */ + if ((prdType = (PIMAGE_RESOURCE_DIRECTORY)ImageDirectoryOffset + (lpFile, IMAGE_DIRECTORY_ENTRY_RESOURCE)) == NULL) + return 0; + + /* set pointer to first resource type entry */ + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdType + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + for (i=0; iNumberOfIdEntries; i++) + { + if (prde->Name == RT_MENU) break; + prde++; + } + if (prde->Name != RT_MENU) return 0; + + prdName = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000) ); + if (prdName == NULL) return 0; + + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdName + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + // sometimes previous code tells you lots of things hidden underneath + // I wish I could save all the revisions I made ... but again .... sigh. + // october 12, 1997 sang + //dwBase = (DWORD)((int)lpFile + psh->PointerToRawData - psh->VirtualAddress); + + nMenus=prdName->NumberOfNamedEntries + prdName->NumberOfIdEntries; + sLength=0; + + for (i=0; iNumberOfNamedEntries; i++) + { + pMenuName = (PIMAGE_RESOURCE_DIR_STRING_U) + ((DWORD)prdType + (prde->Name ^ 0x80000000)); + sLength += pMenuName->Length + 1; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + pMenuHeader = (PIMAGE_MENU_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + + // + // normally wVersion and cbHeaderSize should be zero + // but if it is not then nothing is known to us... + // so let's do our best ... namely guessing .... and trying .... + // ... and suffering ... + // it gave me many sleepless (not exactly but I like to say this) nights. + // + + // strange case + if (pMenuHeader->wVersion | pMenuHeader->cbHeaderSize) + { + //isStrange = TRUE; + pwd = (WORD *)((DWORD)pMenuHeader + 16); + size = prData->Size; + // expect to return the length needed to report. + // sixteen more bytes to do something + sLength += 16+size; + //StrangeMenuScan (&sLength, &pwd, size); + } + // normal case + else + { + pPopup = (PIMAGE_POPUP_MENU_ITEM) + ((DWORD)pMenuHeader + sizeof (IMAGE_MENU_HEADER)); + while (1) + { + flag = (WORD)MenuScan (&sLength, (WORD **)(&pPopup) ); + if (flag & 0x0080) break; + } + } + prde++; + } + for (i=0; iNumberOfIdEntries; i++) + { + sLength += 12; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + pMenuHeader = (PIMAGE_MENU_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + // strange case + if (pMenuHeader->wVersion | pMenuHeader->cbHeaderSize) + { + pwd = (WORD *)((DWORD)pMenuHeader + 16); + size = prData->Size; + // expect to return the length needed to report. + // sixteen more bytes to do something + sLength += 16+size; + //StrangeMenuScan (&sLength, &pwd, size); + } + // normal case + else + { + pPopup = (PIMAGE_POPUP_MENU_ITEM) + ((DWORD)pMenuHeader + sizeof (IMAGE_MENU_HEADER)); + while (1) + { + flag = (WORD)MenuScan (&sLength, (WORD **)(&pPopup) ); + if (flag & 0x0080) break; + } + } + prde++; + } + // + // allocate memory for menu names + // + *pszResTypes = (char *)calloc (sLength, 1); + + pMem = *pszResTypes; + // + // and start all over again + // + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdName + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + for (i=0; iNumberOfNamedEntries; i++) + { + pMenuName = (PIMAGE_RESOURCE_DIR_STRING_U) + ((DWORD)prdType + (prde->Name ^ 0x80000000)); + + + for (j=0; jLength; j++) + *pMem++ = (char)(pMenuName->NameString[j]); + *pMem = 0; + pMem++; + + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + pMenuHeader = (PIMAGE_MENU_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + // strange case + if (pMenuHeader->wVersion | pMenuHeader->cbHeaderSize) + { + pwd = (WORD *)((DWORD)pMenuHeader); + size = prData->Size; + strcpy (pMem, ":::::::::::"); pMem +=12; + *(int *)pMem = size; pMem += 4; + StrangeMenuFill (&pMem, &pwd, size); + } + // normal case + else + { + pPopup = (PIMAGE_POPUP_MENU_ITEM) + ((DWORD)pMenuHeader + sizeof (IMAGE_MENU_HEADER)); + while (1) + { + flag = (WORD)MenuFill (&pMem, (WORD **)(&pPopup) ); + if (flag & 0x0080) break; + } + } + prde++; + } + for (i=0; iNumberOfIdEntries; i++) + { + + sprintf (buff, "MenuId_%04X", (prde->Name)); + strcpy (pMem, buff); + pMem += strlen (buff) + 1; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + pMenuHeader = (PIMAGE_MENU_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + // strange case + if (pMenuHeader->wVersion | pMenuHeader->cbHeaderSize) + { + pwd = (WORD *)((DWORD)pMenuHeader); + size = prData->Size; + strcpy (pMem, ":::::::::::"); pMem +=12; + *(int *)pMem = size; pMem += 4; + StrangeMenuFill (&pMem, &pwd, size); + } + // normal case + else + { + pPopup = (PIMAGE_POPUP_MENU_ITEM) + ((DWORD)pMenuHeader + sizeof (IMAGE_MENU_HEADER)); + while (1) + { + flag = (WORD)MenuFill (&pMem, (WORD **)(&pPopup) ); + if (flag & 0x0080) break; + } + } + prde++; + } + + return nMenus; +} + + +// +// This function is written by sang cho +// October 12, 1997 +// +/* print contents of menu */ +int WINAPI PrintStrangeMenu ( + char **psz) +{ + + int i, j, l; + int num; + WORD flag1, flag2; + char buff[128]; + char *ptr, *pmax; + + //return dumpMenu (psz, size); + + ptr = *psz; + + if(strncmp (ptr, ":::::::::::", 11) != 0) + { + printf ("\n#### I don't know why!!!"); + dumpMenu (psz, 1024); + exit (0); + } + + ptr += 12; + num = *(int *)ptr; + ptr += 4; + pmax = ptr+num; + + *psz = ptr; + return dumpMenu (psz, num); + + // I will write some code later... + +} + + + + +// +// This function is written by sang cho +// October 2, 1997 +// +/* print contents of menu */ +int WINAPI PrintMenu ( + int indent, + char **psz) +{ + + int i, j, k, l; + WORD id, num; + WORD flag; + char buff[128]; + char *ptr; + + + ptr = *psz; + //num = *(WORD *)ptr; + //ptr += 2; + while (1) + { + flag = *(WORD *)ptr; + if (flag & 0x0010) // flag == popup + { + printf ("\n\n"); + for (j=0; j= pmax) break; + n++; + if (n%4 == 0) printf (" "); + } + n++; if (n%4 == 0) printf (" "); + l = j; + j++; + for (; j<16; j++) + { n++; if (n%4 == 0) printf (" "); else printf (" "); } + printf (" "); + for (k=0; k= pmax) break; + } + + *psz = ptr; + +} + + + + +// +// This function is written by sang cho +// October 13, 1997 +// +/* scan dialog box and copy dialog box */ +int WINAPI GetContentsOfDialog ( + LPVOID lpFile, + char **pszResTypes) +{ + PIMAGE_RESOURCE_DIRECTORY prdType, prdName, prdLanguage; + PIMAGE_RESOURCE_DIRECTORY_ENTRY prde, prde1; + PIMAGE_RESOURCE_DIR_STRING_U pDialogName; + PIMAGE_RESOURCE_DATA_ENTRY prData; + PIMAGE_DIALOG_HEADER pDialogHeader; + PIMAGE_CONTROL_DATA pControlData; + char buff[32]; + int nCnt=0, i, j; + int num=0; + int size; + int sLength, nDialogs; + WORD flag; + WORD *pwd; + DWORD prdeName; + char *pMem, *pTemp; + BOOL isStrange = FALSE; + + + /* get root directory of resource tree */ + if ((prdType = (PIMAGE_RESOURCE_DIRECTORY)ImageDirectoryOffset + (lpFile, IMAGE_DIRECTORY_ENTRY_RESOURCE)) == NULL) + return 0; + + /* set pointer to first resource type entry */ + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdType + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + for (i=0; iNumberOfIdEntries; i++) + { + if (prde->Name == RT_DIALOG) break; + prde++; + } + if (prde->Name != RT_DIALOG) return 0; + + prdName = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000) ); + if (prdName == NULL) return 0; + + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdName + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + + nDialogs=prdName->NumberOfNamedEntries + prdName->NumberOfIdEntries; + sLength=0; + + for (i=0; iNumberOfNamedEntries; i++) + { + pDialogName = (PIMAGE_RESOURCE_DIR_STRING_U) + ((DWORD)prdType + (prde->Name ^ 0x80000000)); + sLength += pDialogName->Length + 1; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + size = prData->Size; + sLength += 4+size; + prde++; + } + for (i=0; iNumberOfIdEntries; i++) + { + sLength += 14; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + size = prData->Size; + sLength += 4+size; + prde++; + } + // + // allocate memory for menu names + // + *pszResTypes = (char *)calloc (sLength, 1); + + pMem = *pszResTypes; + // + // and start all over again + // + prde = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdName + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + for (i=0; iNumberOfNamedEntries; i++) + { + pDialogName = (PIMAGE_RESOURCE_DIR_STRING_U) + ((DWORD)prdType + (prde->Name ^ 0x80000000)); + + + for (j=0; jLength; j++) + *pMem++ = (char)(pDialogName->NameString[j]); + *pMem = 0; + pMem++; + + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) continue; + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) continue; + + pDialogHeader = (PIMAGE_DIALOG_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + + + + pwd = (WORD *)((DWORD)pDialogHeader); + size = prData->Size; + *(int *)pMem = size; pMem += 4; + StrangeMenuFill (&pMem, &pwd, size); + + prde++; + } + for (i=0; iNumberOfIdEntries; i++) + { + + sprintf (buff, "DialogId_%04X", (prde->Name)); + strcpy (pMem, buff); + pMem += strlen (buff) + 1; + + prdLanguage = (PIMAGE_RESOURCE_DIRECTORY) + ((DWORD)prdType + (prde->OffsetToData ^ 0x80000000)); + if (prdLanguage == NULL) + { printf ("\nprdLanguage = NULL"); exit (0); } + + prde1 = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) + ((DWORD)prdLanguage + sizeof (IMAGE_RESOURCE_DIRECTORY)); + + prData = (PIMAGE_RESOURCE_DATA_ENTRY) + ((DWORD)prdType + prde1->OffsetToData); + if (prData == NULL) + { printf ("\nprData = NULL"); exit (0); } + + pDialogHeader = (PIMAGE_DIALOG_HEADER) + GetActualAddress (lpFile, prData->OffsetToData); + + + pwd = (WORD *)((DWORD)pDialogHeader); + size = prData->Size; + *(int *)pMem = size; pMem += 4; + StrangeMenuFill (&pMem, &pwd, size); + + prde++; + } + + return nDialogs; +} + + +// +// This function is written by sang cho +// October 14, 1997 +// +/* print contents of dialog */ +int WINAPI PrintNameOrOrdinal ( + char **psz) +{ + char *ptr; + + ptr = *psz; + if (*(WORD *)ptr == 0xFFFF) + { ptr += 2; + printf ("%04X", *(WORD *)ptr); + ptr += 2; + } + else + { + printf ("%c", '"'); + while (*(WORD *)ptr) { printf("%c", *ptr); ptr+= 2; } + ptr += 2; + printf ("%c", '"'); + } + *psz = ptr; +} + + +// +// This function is written by sang cho +// October 14, 1997 +// +/* print contents of dialog */ +int WINAPI PrintDialog ( + char **psz) +{ + int i, j, k, l, n, c; + int num, size; + DWORD flag; + WORD class; + char buff[32]; + char *ptr, *pmax; + BOOL isStrange=FALSE; + + ptr = *psz; + size = *(int *)ptr; + ptr += 4; + pmax = ptr+size; + + // IStype of Dialog Header + flag = *(DWORD *)ptr; + // + // check if flag is right or not + // it has been observed that some dialog information is strange + // and extra work is needed to fix that ... so let's try something + // + + if ((flag & 0xFFFF0000) == 0xFFFF0000) + { + flag = *(DWORD *)(ptr+12); + num = *(short *)(ptr+16); + isStrange = TRUE; + ptr += 26; + } + else + { + num = *(short *)(ptr+8); + ptr += 18; + } + printf (", # of Controls=%03d, Caption:%c", num, '"'); + + // Menu name + if (*(WORD *)ptr == 0xFFFF) ptr += 4; // ordinal + else { while (*(WORD *)ptr) ptr += 2; ptr += 2; } // name + + // Class name + if (*(WORD *)ptr == 0xFFFF) ptr += 4; // ordinal + else { while (*(WORD *)ptr) ptr += 2; ptr += 2; } // name + + // Caption + while (*(WORD *)ptr) { printf("%c", *ptr); ptr+= 2; } + ptr += 2; + printf ("%c", '"'); + + // FONT present + if (flag & 0x00000040) + { + if (isStrange) ptr += 6; else ptr += 2; // FONT size + while (*(WORD *)ptr) ptr += 2; // WCHARs + ptr += 2; // double null + } + + // strange case adjust + if (isStrange) ptr += 8; + + // DWORD padding + if ((ptr-*psz) % 4) ptr += 4 - ((ptr-*psz) % 4); + + // start reporting .. finally + for (i=0; i= pmax) break; + n++; + if (n%4 == 0) printf (" "); + } + n++; if (n%4 == 0) printf (" "); + l = j; + j++; + for (; j<16; j++) + { n++; if (n%4 == 0) printf (" "); else printf (" "); } + printf (" "); + for (k=0; k= pmax) break; + } + */ + + *psz = pmax; + +} + + + + + + +/* function indicates whether debug info has been stripped from file */ +BOOL WINAPI IsDebugInfoStripped ( + LPVOID lpFile) +{ + PIMAGE_FILE_HEADER pfh; + + pfh = (PIMAGE_FILE_HEADER)PEFHDROFFSET (lpFile); + + return (pfh->Characteristics & IMAGE_FILE_DEBUG_STRIPPED); +} + + + + +/* retrieve the module name from the debug misc. structure */ +int WINAPI RetrieveModuleName ( + LPVOID lpFile, + char **pszModule) +{ + + PIMAGE_DEBUG_DIRECTORY pdd; + PIMAGE_DEBUG_MISC pdm = NULL; + int nCnt; + + if (!(pdd = (PIMAGE_DEBUG_DIRECTORY)ImageDirectoryOffset (lpFile, IMAGE_DIRECTORY_ENTRY_DEBUG))) + return 0; + + while (pdd->SizeOfData) + { + if (pdd->Type == IMAGE_DEBUG_TYPE_MISC) + { + pdm = (PIMAGE_DEBUG_MISC)((DWORD)pdd->PointerToRawData + (DWORD)lpFile); + *pszModule = (char *)calloc ((nCnt = (strlen (pdm->Data)))+1, 1); + // may need some unicode business here...above + bcopy (pdm->Data, *pszModule, nCnt); + + break; + } + + pdd ++; + } + + if (pdm != NULL) + return nCnt; + else + return 0; +} + + + + + +/* determine if this is a valid debug file */ +BOOL WINAPI IsDebugFile ( + LPVOID lpFile) +{ + PIMAGE_SEPARATE_DEBUG_HEADER psdh; + + psdh = (PIMAGE_SEPARATE_DEBUG_HEADER)lpFile; + + return (psdh->Signature == IMAGE_SEPARATE_DEBUG_SIGNATURE); +} + + + + +/* copy separate debug header structure from debug file */ +BOOL WINAPI GetSeparateDebugHeader ( + LPVOID lpFile, + PIMAGE_SEPARATE_DEBUG_HEADER psdh) +{ + PIMAGE_SEPARATE_DEBUG_HEADER pdh; + + pdh = (PIMAGE_SEPARATE_DEBUG_HEADER)lpFile; + + if (pdh->Signature == IMAGE_SEPARATE_DEBUG_SIGNATURE) + { + bcopy ((LPVOID)pdh, (LPVOID)psdh, sizeof (IMAGE_SEPARATE_DEBUG_HEADER)); + return TRUE; + } + + return FALSE; +} + + +/* I need to place these data here to keep integrity of codes */ + +LPVOID lpFile; /* pointer to the contents of the input file */ +LPVOID lpMap; /* pointere to the map of codes processed */ +int nSections; // number of sections +int nResources; // number of resources +int nMenus; // number of menus +int nDialogs; // number of dialogs +int nImportedModules; // number of imported modules +int nFunctions; // number of functions in the imported module +int nExportedFunctions; // number of exported funcions +int imageBase; // image base of the file +int entryPoint; // entry point of the file +int imagebaseRVA; /* imagebase + RVA of the code */ +int CodeOffset; /* starting point of code */ +int CodeSize; /* size of code */ +int vCodeOffset; /* starting point of code */ +int vCodeSize; /* size of code */ +int MapSize; /* size of code map */ +int maxRVA; /* the largest RVA of sections */ +int maxRVAsize; /* size of that section */ + +char *piNameBuff; // import module name buffer +char *pfNameBuff; // import functions in the module name buffer +char *peNameBuff; // export function name buffer +char *pmNameBuff; // menu name buffer +char *pdNameBuff; // dialog name buffer +int piNameBuffSize; // import module name buffer +int pfNameBuffSize; // import functions in the module name buffer +int peNameBuffSize; // export function name buffer +int pmNameBuffSize; // menu name buffer +int pdNameBuffSize; // dialog name buffer + +extern Bnode *head; // label data B-Tree header +extern int btn; // label data B-Tree control number + +int AddressCheck(int); + +// +// I tried to immitate the output of w32dasm disassembler. +// which is a pretty good program. +// but I am disappointed with this program and I myself +// am writting a disassembler. +// This PEdump program is a byproduct of that project. +// so enjoy this program and I hope we will have a little more +// knowledge on windows programming world. +// .... sang cho + +#define MAXSECTIONNUMBER 16 +#define MAXNAMESTRNUMBER 40 +int pedump (argc,argv)\ +int argc; char **argv; +{ + DWORD fileType; + + IMAGE_DOS_HEADER dosHdr; + PIMAGE_FILE_HEADER pfh; + PIMAGE_OPTIONAL_HEADER poh; + PIMAGE_SECTION_HEADER psh; + IMAGE_SECTION_HEADER idsh; + IMAGE_SECTION_HEADER shdr [MAXSECTIONNUMBER]; + PIMAGE_IMPORT_MODULE_DIRECTORY pid; + + int i, j, n; + int mnsize; + int nCnt; + int nSize; + + char *pnstr; + char *pst; +// char *piNameBuff; // import module name buffer +// char *pfNameBuff; // import functions in the module name buffer +// char *peNameBuff; // export function name buffer +// char *pmNameBuff; // menu name buffer +// char *pdNameBuff; // dialog name buffer + + unsigned char *p, *q; + _key_ k; + PKEY pk; + + GetDosHeader (lpFile, &dosHdr); + + if (dosHdr.e_magic == IMAGE_DOS_SIGNATURE) + { + if ((dosHdr.e_lfanew > 4096) || (dosHdr.e_lfanew < 64)) + { + printf ("This file is not PE format ... sorry, it looks like DOS format\n"); + exit (0); + } + } + else + { + printf ("This doesn't look like executable file .. sorry, ...\n"); + exit (0); + } + + fileType = ImageFileType (lpFile); + + if (fileType != IMAGE_NT_SIGNATURE) + { + printf ("This file is not PE format ... sorry,\n"); + exit (0); + } + + //===================================== + // now we can really start processing + //===================================== + + pfh = (PIMAGE_FILE_HEADER) PEFHDROFFSET (lpFile); + + poh = (PIMAGE_OPTIONAL_HEADER) OPTHDROFFSET (lpFile); + printf("PIMAGE_OPTIONAL_HEADER:CodeSize 0x%08x\n",poh->SizeOfCode); + printf("PIMAGE_OPTIONAL_HEADER:ImageBase 0x%08x\n",poh->ImageBase); + printf("PIMAGE_OPTIONAL_HEADER:EntryPoint 0x%08x\n",poh->AddressOfEntryPoint); + printf("PIMAGE_OPTIONAL_HEADER:BaseOfCode 0x%08x\n",poh->BaseOfCode); + CodeSize=poh->SizeOfCode; + psh = (PIMAGE_SECTION_HEADER) SECHDROFFSET (lpFile); + + nSections = pfh->NumberOfSections; + + imageBase = poh->ImageBase; + + entryPoint = poh->AddressOfEntryPoint; + + if (psh == NULL) return 0; + + /* store section headers */ + + for (i=0; i < nSections; i++) + { + shdr[i] = *psh++; + } + + // get Code offset and size, Data offset and size + maxRVA = 0; + + for (i=0; i < nSections; i++) + { + if (!strcasecmp(shdr[i].Name,".text")) + { + fprintf(stderr,"Found Code size 0x%08x\n",shdr[i].SizeOfRawData); + if (shdr[i].SizeOfRawData > CodeSize) + CodeSize =shdr[i].SizeOfRawData; + } + else + fprintf(stderr,"Found string '%s'\n",shdr[i].Name); + if (poh->BaseOfCode == shdr[i].VirtualAddress) + { + printf("Code Offset = %08X, Code Size = %08X \n", + shdr[i].PointerToRawData, shdr[i].SizeOfRawData); + CodeOffset = shdr[i].PointerToRawData; + imagebaseRVA = imageBase + shdr[i].VirtualAddress; + } + if (shdr[i].VirtualAddress>maxRVA) + { + maxRVA = shdr[i].VirtualAddress; + maxRVAsize = shdr[i].SizeOfRawData; + } + if (((shdr[i].Characteristics) & 0xC0000040) == 0xC0000040) + //if (poh->BaseOfData == shdr[i].VirtualAddress) + { + printf ("Data Offset = %08X, Data Size = %08X \n", + shdr[i].PointerToRawData, shdr[i].SizeOfRawData); + break; + } + } + for ( ; i < nSections; i++) + { + if (shdr[i].VirtualAddress>maxRVA) + { + maxRVA = shdr[i].VirtualAddress; + maxRVAsize = shdr[i].SizeOfRawData; + } + } + + printf ("\n"); + + printf ("Number of Objects = %04d (dec), Imagebase = %08Xh \n", + nSections, imageBase); + + // object name alignment + for (i=0; i < nSections; i++) + { + for (j=0;j<7;j++) if (shdr[i].Name[j]==0) shdr[i].Name[j]=32; + shdr[i].Name[7]=0; + } + for (i=0; i < nSections; i++) + { + printf ("\n Object%02d: %8s RVA: %08X Offset: %08X Size: %08X Flags: %08X ", + i+1, shdr[i].Name, shdr[i].VirtualAddress, shdr[i].PointerToRawData, + shdr[i].SizeOfRawData, shdr[i].Characteristics); + } + // Get List of Resources + nResources = GetListOfResourceTypes (lpFile, &pnstr); + pst = pnstr; + printf ("\n"); + printf ("\n+++++++++++++++++++ RESOURCE INFORMATION +++++++++++++++++++"); + printf ("\n"); + if (nResources==0) + printf ("\n There are no Resources in This Application.\n"); + else + { + printf ("\nNumber of Resource Types = %4d (decimal)\n", nResources); + for (i=0; i < nResources; i++) + { + printf ("\n Resource Type %03d: %s",i+1, pst); + pst += strlen ((char *)(pst)) + 1; + } + free ((void *)pnstr); + + printf ("\n"); + printf ("\n+++++++++++++++++++ MENU INFORMATION +++++++++++++++++++"); + printf ("\n"); + + nMenus = GetContentsOfMenu (lpFile, &pmNameBuff); + + if (nMenus == 0) + { + printf("\n There are no Menus in This Application."); + } + else + { + pst = pmNameBuff; + printf ("\nNumber of Menus = %4d (decimal)", nMenus); + + //dumpMenu(&pst, 8096); + for (i=0; i < nMenus; i++) + { + // menu ID print + printf ("\n\n%s", pst); + pst += strlen (pst) + 1; + printf ("\n-------------"); + if (strncmp (pst, ":::::::::::", 11) == 0) + { + printf("\n"); + PrintStrangeMenu (&pst); + } + else + { + PrintMenu (6, &pst); + } + //else PrintStrangeMenu(&pst); + } + free ((void *)pmNameBuff); + printf ("\n"); + } + + printf ("\n"); + printf ("\n+++++++++++++++++ DIALOG INFORMATION +++++++++++++++++++"); + printf ("\n"); + + nDialogs = GetContentsOfDialog (lpFile, &pdNameBuff); + + if (nDialogs == 0) + { + printf("\n There are no Dialogs in This Application."); + } + else + { + pst = pdNameBuff; + printf ("\nNumber of Dialogs = %4d (decimal)", nDialogs); + + printf ("\n"); + + for (i=0; i < nDialogs; i++) + { + // Dialog ID print + printf ("\nName: %s", pst); + pst += strlen (pst) + 1; + PrintDialog (&pst); + } + free ((void *)pdNameBuff); + } + printf ("\n"); + } + + printf ("\n+++++++++++++++++++ IMPORTED FUNCTIONS +++++++++++++++++++"); + + nImportedModules = GetImportModuleNames (lpFile, &piNameBuff); + if (nImportedModules == 0) + { + printf("\n There are no imported Functions in This Application.\n"); + } + else + { + pnstr = piNameBuff; + printf ("\nNumber of Imported Modules = %4d (decimal)\n", nImportedModules); + for (i=0; i < nImportedModules; i++) + { + printf ("\n Import Module %03d: %s",i+1, pnstr + 4); + pnstr += strlen ((char *)(pnstr+4)) + 1 + 4; + } + + printf("\n"); + printf("\n+++++++++++++++++++ IMPORT MODULE DETAILS +++++++++++++++++"); + pnstr = piNameBuff; + for (i=0; i < nImportedModules; i++) + { + printf ("\n\n Import Module %03d: %s \n",i+1, pnstr + 4); + nFunctions = GetImportFunctionNamesByModule (lpFile, pnstr, &pfNameBuff); + pnstr += strlen ((char *)(pnstr+4)) + 1 + 4; + pst = pfNameBuff; + for (j=0;j < nFunctions;j++) + { + printf ("\nAddr:%08X hint(%04X) Name: %s", + (*(int *)pst),(*(short *)(pst+4)), + //(pst+6)); + TranslateFunctionName(pst+6)); + pst += strlen ((char *)(pst+6)) + 1 + 6; + } + free ((void *)pfNameBuff); + } + //free ((void *)piNameBuff); + } + + printf("\n"); + printf("\n+++++++++++++++++++ EXPORTED FUNCTIONS +++++++++++++++++++"); + + nExportedFunctions = GetExportFunctionNames (lpFile, &peNameBuff); + printf ("\nNumber of Exported Functions = %4d (decimal)\n", nExportedFunctions); + MapSize = CodeSize + 1; + lpMap = (void *) calloc (MapSize, 1); + printf("lpMap %p max %p\n",imagebaseRVA, + MapSize+1 + imagebaseRVA); + if (nExportedFunctions > 0) + { + pst = peNameBuff; + + for (i=0; i < nExportedFunctions-1; i++) + { + printf ("\nAddr:%08X Ord:%4d (%04Xh) Name: %s", + (*(int *)pst), (*(WORD *)(pst+4)), (*(WORD *)(pst+4)), + //(pst+6)); + TranslateFunctionName(pst+6)); + // this one is needed to link export function names to codes.. + k.class=2048; k.c_ref= *(int *)pst; k.c_pos=0; + if (AddressCheck(k.c_ref)) + { + MyBtreeInsertEx(&k); + p=lpMap+k.c_ref-imagebaseRVA; + if ((p) && (((unsigned int)p -(unsigned int)lpMap) < MapSize)) + { + *p |= 0x60; + k.class=0; k.c_pos=-(int)(pst+6); + MyBtreeInsert(&k); + } + else + fprintf(stderr,"\nerror"); + } + pst += strlen ((char *)(pst+6)) + 6+1; + } + //free ((void *)peNameBuff); + } + // free ((void *)lpFile); +} diff --git a/reactos/ntoskrnl/makefile_rex b/reactos/ntoskrnl/makefile_rex new file mode 100644 index 00000000000..c2e766abcd8 --- /dev/null +++ b/reactos/ntoskrnl/makefile_rex @@ -0,0 +1,59 @@ + +all: kimage + +# +# Defines $(HAL_OBJECTS) +# +include hal/x86/sources + +RTL_OBJECTS = rtl/vsprintf.o rtl/lookas.o rtl/unicode.o rtl/strtok.o \ + rtl/time.o rtl/unalign.o rtl/mem.o rtl/largeint.o rtl/ctype.o \ + rtl/list.o rtl/slist.o rtl/interlck.o + +KE_OBJECTS = ke/main.o ke/timer.o ke/error.o ke/catch.o ke/exports.o \ + ke/module.o ke/dpc.o ke/wait.o ke/kqueue.o ke/dispatch.o \ + ke/sem.o ke/critical.o ke/event.o ke/apc.o ke/bug.o \ + ke/mutex.o + +MM_OBJECTS = mm/mm.o mm/freelist.o mm/pool.o mm/pageflt.o mm/virtual.o \ + mm/mdl.o mm/zone.o mm/cont.o mm/ncache.o mm/iospace.o \ + mm/section.o + + +IO_OBJECTS = io/iomgr.o io/create.o io/irp.o io/device.o io/rw.o \ + io/queue.o io/drvlck.o io/timer.o io/share.o io/errlog.o \ + io/shutdown.o io/fdisk.o io/cancel.o io/error.o io/arc.o \ + io/dpc.o io/symlink.o io/adapter.o io/cntrller.o io/mdl.o \ + io/resource.o io/event.o io/process.o io/file.o io/ioctrl.o + +OB_OBJECTS = ob/object.o ob/handle.o ob/namespc.o + +PS_OBJECTS = ps/psmgr.o ps/thread.o ps/process.o + +EX_OBJECTS = ex/work.o ex/fmutex.o ex/resource.o ex/time.o ex/interlck.o + +SE_OBJECTS = se/semgr.o + +CFG_OBJECTS = cfg/registry.o + +TST_OBJECTS = tst/test.o + +OBJECTS = $(HAL_OBJECTS) $(KE_OBJECTS) $(RTL_OBJECTS) $(MM_OBJECTS) \ + $(IO_OBJECTS) $(OB_OBJECTS) $(PS_OBJECTS) $(EX_OBJECTS) \ + $(SE_OBJECTS) $(CFG_OBJECTS) $(TST_OBJECTS) + +utils/export/export$(EXE_POSTFIX): utils/export/export.c + $(NATIVE_CC) -g utils/export/export.c -o utils/export/export$(EXE_POSTFIX) + +ke/exports.o: exports.lst utils/export/export$(EXE_POSTFIX) + utils/export/export$(EXE_POSTFIX) < exports.lst > ke/exports.c + $(CC) $(CFLAGS) -c ke/exports.c -o ke/exports.o + +kimage: $(OBJECTS) + $(LD) --defsym _end=end --defsym _etext=etext --oformat=$(KERNEL_BFD_TARGET) -Ttext c0000000 $(LDFLAGS) $(OBJECTS) -o kimage + $(NM) --numeric-sort kimage > kernel.sym + $(OBJCOPY) -O binary kimage kimage.bin + +dummy: + +include ../rules.mak diff --git a/reactos/ntoskrnl/mm/cont.c b/reactos/ntoskrnl/mm/cont.c new file mode 100644 index 00000000000..202955f88ae --- /dev/null +++ b/reactos/ntoskrnl/mm/cont.c @@ -0,0 +1,30 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/mm/cont.c + * PURPOSE: Manages continuous memory + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PVOID MmAllocateContiguousMemory(ULONG NumberOfBytes, + PHYSICAL_ADDRESS HighestAcceptableAddress) +{ + UNIMPLEMENTED; +} + +VOID MmFreeContiguousMemory(PVOID BaseAddress) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/mm/freelist.c b/reactos/ntoskrnl/mm/freelist.c new file mode 100644 index 00000000000..b6aa6910141 --- /dev/null +++ b/reactos/ntoskrnl/mm/freelist.c @@ -0,0 +1,205 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/mm/freelist.cc + * PURPOSE: Handle the list of free physical pages + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 27/05/98: Created + * 18/08/98: Added a fix from Robert Bergkvist + */ + +/* + * NOTE: The list of free pages is implemented as an unsorted double linked + * list. This should make added or removing pages fast when you don't care + * about the physical address. Because the entirety of physical memory is + * mapped from 0xd0000000 upwards it is easy to do a mapping between + * physical and linear address. + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* TYPES *******************************************************************/ + +typedef struct _free_page +/* + * PURPOSE: At the start of every region of free physical pages + */ +{ + struct _free_page* next; + struct _free_page* previous; + unsigned int nr_pages; +} free_page_hdr; + +/* GLOBALS ****************************************************************/ + +/* + * PURPOSE: Points to the first page in the free list + */ +free_page_hdr* free_page_list_head=NULL; + +/* FUNCTIONS *************************************************************/ + +void free_page(unsigned int physical_base, unsigned int nr) +/* + * FUNCTION: Add a physically continuous range of pages to the free list + * ARGUMENTS: + * physical_base = The first physical address to free + * nr = the size of the region (in pages) to free + * NOTES: This function attempts to keep the list partially unfragmented + */ +{ + unsigned int eflags; + free_page_hdr* hdr=NULL; + + DPRINT("Freeing %x to %x\n",physical_base,physical_base + + (nr*PAGESIZE)); + + /* + * This must be atomic + */ + __asm__("pushf\n\tpop %0\n\tcli\n\t" + : "=d" (eflags)); + + /* + * + */ + hdr = (free_page_hdr *)physical_to_linear(physical_base); + + DPRINT("free_page_hdr %x\n",hdr); + DPRINT("free_page_list_head %x\n",free_page_list_head); + + if (free_page_list_head!=NULL) + { + free_page_list_head->previous=hdr; + } + hdr->next=free_page_list_head; + hdr->previous=NULL; + hdr->nr_pages = nr; + free_page_list_head=hdr; + + __asm__("push %0\n\tpopf\n\t" + : + : "d" (eflags)); +} + +unsigned int get_dma_page(unsigned int max_address) +/* + * FUNCTION: Gets a page with a restricted max physical address (i.e. + * suitable for dma) + * ARGUMENTS: + * max_address = The maximum address usable by the caller + * RETURNS: + * The physical address of the page if it succeeds + * NULL if it fails. + * NOTES: This is very inefficent because the list isn't sorted. On the + * other hand sorting the list would be quite expensive especially if dma + * is only used infrequently. Perhaps a special cache of dma pages should + * be maintained? + */ +{ + free_page_hdr* current=NULL; + + if (free_page_list_head==NULL) + { + printk("CRITICAL: Unable to allocate page\n"); + KeBugCheck(KBUG_OUT_OF_MEMORY); + } + + /* + * Walk the free page list looking for suitable memory + */ + current = free_page_list_head; + while (current!=NULL) + { + if ( ((int)current) < max_address) + { + /* + * We take the first page from the region + */ + free_page_hdr* nhdr = (free_page_hdr *)(((int)current)+PAGESIZE); + if (current->previous!=NULL) + { + current->previous->next=nhdr; + } + if (current->next!=NULL) + { + current->next->previous=nhdr; + } + nhdr->next=current->next; + nhdr->previous=current->previous; + nhdr->nr_pages=current->nr_pages-1; + if (free_page_list_head==current) + { + free_page_list_head=nhdr; + } + + return ((int)current); + } + + current=current->next; + } + return(NULL); +} + +unsigned int get_free_page(void) +/* + * FUNCTION: Allocates a page + * RETURNS: The physical address of the page allocated + */ +{ + unsigned int addr; + + /* + * This must be atomic wrt everything + */ + unsigned int eflags; + __asm__("pushf\n\tpop %0\n\tcli\n\t" + : "=d" (eflags)); + CHECKPOINT; + /* + * If we are totally out of memory then panic + */ + if (free_page_list_head==NULL) + { + printk("CRITICAL: Unable to allocate page\n"); + KeBugCheck(KBUG_OUT_OF_MEMORY); + } + CHECKPOINT; + addr = 0; + CHECKPOINT; + if (free_page_list_head->nr_pages>1) + { + free_page_list_head->nr_pages--; + addr = ((unsigned int)free_page_list_head) + + (free_page_list_head->nr_pages * PAGESIZE); + } + else + { + addr = (unsigned int)free_page_list_head; + free_page_list_head = free_page_list_head -> next; + } + CHECKPOINT; + __asm__("push %0\n\tpopf\n\t" + : + : "d" (eflags)); + + addr = addr - (IDMAP_BASE); + DPRINT("allocated %x\n",addr); + CHECKPOINT; + return(addr); +} + + + + diff --git a/reactos/ntoskrnl/mm/iospace.c b/reactos/ntoskrnl/mm/iospace.c new file mode 100644 index 00000000000..243212ed101 --- /dev/null +++ b/reactos/ntoskrnl/mm/iospace.c @@ -0,0 +1,31 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PVOID MmMapIoSpace(PHYSICAL_ADDRESS PhysicalAddress, + ULONG NumberOfBytes, + BOOLEAN CacheEnable) +{ + UNIMPLEMENTED; +} + +VOID MmUnmapIoSpace(PVOID BaseAddress, ULONG NumberOfBytes) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/mm/lock.c b/reactos/ntoskrnl/mm/lock.c new file mode 100644 index 00000000000..d3e3aca76f2 --- /dev/null +++ b/reactos/ntoskrnl/mm/lock.c @@ -0,0 +1,127 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/mm/lock.c + * PURPOSE: Locking/unlocking virtual memory areas + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +BOOL VirtualUnlock(LPVOID lpAddress, DWORD cbSize) +/* + * FUNCTION: Unlocks pages from the virtual address space of the current + * process + * ARGUMENTS: + * lpAddress = Beginning of the region to unlock + * cbSize = Size (in bytes) of the region to unlock + * RETURNS: Success or failure + */ +{ + return(FALSE); +} + +BOOL VirtualLock(LPVOID lpvAddress, DWORD cbSize) +/* + * FUNCTION: Prevents range of memory from being swapped out + * RECEIVES: + * lpvAddress - The base of the range to lock + * cbSize - The size of the range to lock + * RETURNS: + * TRUE - the function succeeds + * FALSE - the function failed (use GetLastError for details) + * + * NOTES: I'm guessing the kernel loads every page as well as locking it. + */ +{ + unsigned int first_page = PAGE_ROUND_DOWN((int)lpvAddress); + unsigned int length = PAGE_ROUND_DOWN( ((int)lpvAddress) + cbSize) - + first_page; + memory_area* marea=NULL; + memory_area* current=NULL; + unsigned int i; + + /* + * Check the process isn't trying to lock too much + */ + if ( ((length/PAGESIZE)+1) > 30) + { + SetLastError(0); + return(FALSE); + } + + /* + * Find the corresponding vmarea(s) + */ + marea = find_first_marea(memory_area_list_head,first_page, + length); + if (marea==NULL) + { + SetLastError(0); + return(FALSE); + } + + /* + * Check the memory areas are committed, continuous and not + * PAGE_NOACCESS + */ + current=marea; + if (current->base != first_page) + { + SetLastError(0); + return(FALSE); + } + while (current!=NULL && current->base < (first_page+length) ) + { + if (!(current->state & MEM_COMMIT) || + current->access & PAGE_NOACCESS) + { + SetLastError(0); + return(FALSE); + } + if ( current->next==NULL) + { + if ((current->base + current->length) != + (first_page+length) ) + { + SetLastError(0); + return(FALSE); + } + } + else + { + if ( (current->base+current->length) != + current->next->base) + { + SetLastError(0); + return(FALSE); + } + } + current=current->next; + } + + /* + * Lock/load the areas in memory + * (the pages aren't loaded just by touching them to avoid the + * overhead of a page fault) + */ + current=marea; + while (current!=NULL && current->base < (first_page+length) ) + { + marea->lock = TRUE; + for (i=0; ilength; i++) + { + if (!current->load_page(marea,i)) + { + /* + * If the page couldn't be loaded we unlock + * the locked pages and abort + */ + VirtualUnlock(lpvAddress, + current->base+i-PAGESIZE); + SetLastError(0); + return(FALSE); + } + } + } + + return(TRUE); +} diff --git a/reactos/ntoskrnl/mm/mdl.c b/reactos/ntoskrnl/mm/mdl.c new file mode 100644 index 00000000000..e313418a460 --- /dev/null +++ b/reactos/ntoskrnl/mm/mdl.c @@ -0,0 +1,224 @@ + /* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/mm/mdl.cc + * PURPOSE: Manipulates MDLs + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 27/05/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include + +#include + +/* FUNCTIONS ***************************************************************/ + + +VOID MmUnlockPages(PMDL MemoryDescriptorList) +{ + UNIMPLEMENTED; +} + +PVOID MmMapLockedPages(PMDL MemoryDescriptorList, KPROCESSOR_MODE AccessMode) +{ + UNIMPLEMENTED; +} + +VOID MmUnmapLockedPages(PVOID BaseAddress, PMDL MemoryDescriptorList) +{ + UNIMPLEMENTED; +} + +VOID MmPrepareMdlForReuse(PMDL Mdl) +{ + UNIMPLEMENTED; +} + +VOID KeFlushIoBuffers(PMDL Mdl, BOOLEAN ReadOperation, BOOLEAN DmaOperation) +{ + /* NOP on the x86 */ + /* See ntddk.h from Windows 98 DDK */ +} + +VOID MmProbeAndLockPages(PMDL Mdl, KPROCESSOR_MODE AccessMode, + LOCK_OPERATION Operation) +/* + * FUNCTION: Probes the specified pages, makes them resident and locks them + * ARGUMENTS: + * Mdl = MDL to probe + * AccessMode = Access at which to probe the buffer + * Operation = Operation to probe for + */ +{ + /* + * Find the memory area containing the buffer + */ + ULONG* mdl_pages=NULL; + int i; + memory_area* marea=find_first_marea(memory_area_list_head, + (ULONG)Mdl->StartVa, + Mdl->ByteCount); + + /* + * Check the area is valid + */ + if (marea==NULL || (marea->base+marea->length) < ((ULONG)Mdl->StartVa)) + { + ExRaiseStatus(STATUS_INVALID_PARAMETER); + } + + /* + * Check the permissions + */ + switch(Operation) + { + case IoReadAccess: + if (marea->access&PAGE_GUARD || marea->access&PAGE_NOACCESS) + { + ExRaiseStatus(STATUS_INVALID_PARAMETER); + } + break; + + case IoWriteAccess: + case IoModifyAccess: + if (marea->access&PAGE_GUARD || marea->access&PAGE_READONLY) + { + ExRaiseStatus(STATUS_INVALID_PARAMETER); + } + break; + + default: + printk("Invalid operation type at %s:%d in %s\n",__FILE__,__LINE__, + __FUNCTION__); + KeBugCheck(UNEXPECTED_KERNEL_MODE_TRAP); + } + + /* + * Lock the memory area + * (We can't allow it to be freed while an I/O operation to it is + * ongoing) + */ + + /* + * Lock the pages + */ + mdl_pages = (ULONG *)(Mdl + sizeof(MDL)); + + for (i=0;i<(PAGE_ROUND_UP(Mdl->ByteCount)/PAGESIZE);i++) + { + if (!is_page_present(PAGE_ROUND_DOWN(Mdl->StartVa) + (i*PAGESIZE))) + { + marea->load_page(marea,PAGE_ROUND_DOWN(Mdl->StartVa) + (i*PAGESIZE) + - marea->base); + } + mdl_pages[i]=MmGetPhysicalAddress((PVOID)(PAGE_ROUND_DOWN(Mdl->StartVa) + +(i*PAGESIZE))); + } +} + +ULONG MmGetMdlByteCount(PMDL Mdl) +/* + * + */ +{ + return(Mdl->ByteCount); +} + +ULONG MmGetMdlByteOffset(PMDL Mdl) +/* + * FUNCTION: Returns the byte offset within its page of the buffer described + * by the given MDL + * ARGUMENTS: + * Mdl = the mdl to query + * RETURNS: The offset in bytes + */ +{ + return(Mdl->ByteOffset); +} + +ULONG MmSizeOfMdl(PVOID Base, ULONG Length) +/* + * FUNCTION: Returns the number of bytes to allocate for an MDL describing + * the given address range + * ARGUMENTS: + * Base = base virtual address + * Length = number of bytes to map + */ +{ + unsigned int len=PAGE_ROUND_UP(Length)/PAGESIZE; + + if (!IS_PAGE_ALIGNED(Base)) + { + len++; + } + + return(sizeof(MDL)+(len*sizeof(ULONG))); +} + +PVOID MmGetMdlVirtualAddress(PMDL Mdl) +{ + return(Mdl->StartVa + Mdl->ByteOffset); +} + +PVOID MmGetSystemAddressForMdl(PMDL Mdl) +{ + Mdl->MappedSystemVa = MmMapLockedPages(Mdl,KernelMode); + return(Mdl->MappedSystemVa); +} + +VOID MmBuildMdlForNonPagedPool(PMDL Mdl) +{ + int va; + for (va=0; vaSize; va++) + { + ((PULONG)(Mdl + 1))[va] = MmGetPhysicalAddress( + Mdl->StartVa+ (va * PAGESIZE)); + } +} + +VOID MmInitializeMdl(PMDL MemoryDescriptorList, PVOID Base, ULONG Length) +{ + memset(MemoryDescriptorList,0,sizeof(MDL)); + MemoryDescriptorList->StartVa = PAGE_ROUND_DOWN(Base); + MemoryDescriptorList->ByteOffset = Base - PAGE_ROUND_DOWN(Base); + MemoryDescriptorList->MdlFlags = 0; + MemoryDescriptorList->ByteCount = Length; + MemoryDescriptorList->Size = PAGE_ROUND_UP(Length) / PAGESIZE; + if (!IS_PAGE_ALIGNED(Base)) + { + MemoryDescriptorList->Size = MemoryDescriptorList->Size + + sizeof(ULONG); + } + MemoryDescriptorList->Process = PsGetCurrentProcess(); +} + +PMDL MmCreateMdl(PMDL MemoryDescriptorList, PVOID Base, ULONG Length) +/* + * FUNCTION: Allocates and initalizes an MDL + * ARGUMENTS: + * MemoryDescriptorList = Points to MDL to initalize. If this is + * NULL then one is allocated + * Base = Base virtual address of the buffer + * Length = Length in bytes of the buffer + * RETURNS: A pointer to initalized MDL + */ +{ + if (MemoryDescriptorList == NULL) + { + MemoryDescriptorList = (PMDL)ExAllocatePool(NonPagedPool,sizeof(MDL)); + if (MemoryDescriptorList==NULL) + { + return(NULL); + } + } + + MmInitializeMdl(MemoryDescriptorList,Base,Length); + + return(MemoryDescriptorList); +} diff --git a/reactos/ntoskrnl/mm/mm.c b/reactos/ntoskrnl/mm/mm.c new file mode 100644 index 00000000000..ea6914580b8 --- /dev/null +++ b/reactos/ntoskrnl/mm/mm.c @@ -0,0 +1,173 @@ +/* + * COPYRIGHT: See COPYING in the top directory + * PROJECT: ReactOS kernel + * FILE: mm/mm.c + * PURPOSE: kernel memory managment functions + * PROGRAMMER: David Welch + * UPDATE HISTORY: + * Created 9/4/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include +#include +#include +#include +#include + +#include + +#define NDEBUG +#include + +/* GLOBALS *****************************************************************/ + +/* + * Size of extended memory (kb) (fixed for now) + */ +#define EXTENDED_MEMORY_SIZE (3*1024*1024) + +/* + * Compiler defined symbol + */ +extern unsigned int stext; +extern unsigned int etext; +extern unsigned int end; + +/* FUNCTIONS ****************************************************************/ + +BOOLEAN MmIsThisAnNtAsSystem() +{ + UNIMPLEMENTED +} + +MM_SYSTEM_SIZE MmQuerySystemSize() +{ + UNIMPLEMENTED; +} + +void MmInitalize(boot_param* bp) +/* + * FUNCTION: Initalize memory managment + */ +{ + unsigned int kernel_len = bp->end_mem - bp->start_mem; + unsigned int first_krnl_phys_addr; + unsigned int last_krnl_phys_addr; + int i; + + DPRINT("InitalizeMM()\n"); + + CHECKPOINT; + /* + * Unmap low memory + */ + (get_page_directory())[0]=0; + FLUSH_TLB; + CHECKPOINT; + /* + * Free all pages not used for kernel memory + * (we assume the kernel occupies a continuous range of physical + * memory) + */ + first_krnl_phys_addr = bp->start_mem; + last_krnl_phys_addr = bp->end_mem; + DPRINT("first krnl %x\nlast krnl %x\n",first_krnl_phys_addr, + last_krnl_phys_addr); + + /* + * Free physical memory not used by the kernel + */ + if (first_krnl_phys_addr < 0xa0000) + { + free_page(0x2000,(first_krnl_phys_addr/PAGESIZE)-2); + free_page(last_krnl_phys_addr+PAGESIZE, + (0xa0000 - last_krnl_phys_addr - PAGESIZE)/PAGESIZE); + free_page(1024*1024,EXTENDED_MEMORY_SIZE/4096); + } + else + { + free_page(0x2000,(0xa0000/PAGESIZE)-2); + free_page(1024*1024, + (first_krnl_phys_addr-(1024*1024))/PAGESIZE); + free_page(last_krnl_phys_addr+PAGESIZE, + ((EXTENDED_MEMORY_SIZE+(1024*1024)) + -last_krnl_phys_addr)/PAGESIZE); + } + CHECKPOINT; + + /* + * Create a trap for null pointer references and protect text + * segment + */ + CHECKPOINT; + DPRINT("stext %x etext %x\n",(int)&stext,(int)&etext); + for (i=PAGE_ROUND_UP(((int)&stext)); + inext==NULL || + (current->next->base - (current->base+current->length)) + >= size) + { + new_area->base=current->base+current->length; + new_area->length=size; + new_area->next=current->next; + current->next=new_area; + } + current=current->next; + } + + /* + * Map the desired physical memory + */ + for (int i=0;ibase+i, + PA_READ | PA_WRITE | PA_EXECUTE | PA_SYSTEM, + physical_address+i); + } + + return((void *)new_area->base); +} +#endif diff --git a/reactos/ntoskrnl/mm/ncache.c b/reactos/ntoskrnl/mm/ncache.c new file mode 100644 index 00000000000..0be71ed1916 --- /dev/null +++ b/reactos/ntoskrnl/mm/ncache.c @@ -0,0 +1,29 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/mm/cont.c + * PURPOSE: Manages non-cached memory + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PVOID MmAllocateNonCachedMemory(ULONG NumberOfBytes) +{ + UNIMPLEMENTED; +} + +VOID MmFreeNonCachedMemory(PVOID BaseAddress, ULONG NumberOfBytes) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/mm/pageflt.asm b/reactos/ntoskrnl/mm/pageflt.asm new file mode 100644 index 00000000000..d4192d8d1e8 --- /dev/null +++ b/reactos/ntoskrnl/mm/pageflt.asm @@ -0,0 +1,24 @@ +%include 'internal/hal/segment.inc' + +BITS 32 +GLOBAL _exception_handler14 +EXTERN _exception_handler +EXTERN _page_fault_handler +segment .text + +_exception_handler14: + cli + push ds + push dword 14 + pushad + mov ax,KERNEL_DS + mov ds,ax + call _page_fault_handler + cmp eax,0 + jne _ret_from_exp + call _exception_handler +_ret_from_exp: + popad + add esp,12 + iretd + diff --git a/reactos/ntoskrnl/mm/pool.c b/reactos/ntoskrnl/mm/pool.c new file mode 100644 index 00000000000..75431409939 --- /dev/null +++ b/reactos/ntoskrnl/mm/pool.c @@ -0,0 +1,652 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/mm/pool.c + * PURPOSE: Implements the kernel memory pool + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 27/05/98: Created + * 10/06/98: Bug fixes by Iwan Fatahi (i_fatahi@hotmail.com) + * in take_block (if current bigger than required) + * in remove_from_used_list + * in ExFreePool + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +#include + +/* TYPES *******************************************************************/ + +/* + * fields present at the start of a block (this is for internal use only) + */ +typedef struct _block_hdr +{ + unsigned int size; + struct _block_hdr* previous; + struct _block_hdr* next; +} block_hdr; + +/* GLOBALS *****************************************************************/ + +/* + * Memory managment initalized symbol for the base of the pool + */ +extern unsigned int kernel_pool_base; + +/* + * Pointer to the first block in the free list + */ +static block_hdr* free_list_head = NULL; +static block_hdr* used_list_head = NULL; +static unsigned int nr_free_blocks = 0; +static unsigned int nr_used_blocks = 0; + +#define ALLOC_MAP_SIZE (NONPAGED_POOL_SIZE / PAGESIZE) + +/* + * One bit for each page in the kmalloc region + * If set then the page is used by a kmalloc block + */ +static unsigned int alloc_map[ALLOC_MAP_SIZE/32]={0,}; + +/* FUNCTIONS ***************************************************************/ + +static void validate_free_list(void) +/* + * FUNCTION: Validate the integrity of the list of free blocks + */ +{ + block_hdr* current=free_list_head; + unsigned int blocks_seen=0; + + while (current!=NULL) + { + unsigned int base_addr = (int)current; + if (base_addr < (kernel_pool_base) || + (base_addr+current->size) > + (kernel_pool_base)+NONPAGED_POOL_SIZE) + { + printk("Block %x found outside pool area\n",current); + printk("Size %d\n",current->size); + printk("Limits are %x %x\n",kernel_pool_base, + kernel_pool_base+NONPAGED_POOL_SIZE); + KeBugCheck(KBUG_POOL_FREE_LIST_CORRUPT); + } + blocks_seen++; + if (blocks_seen > nr_free_blocks) + { + printk("Too many blocks on list\n"); + KeBugCheck(KBUG_POOL_FREE_LIST_CORRUPT); + } +// verify_for_write(base_addr,current->size); + if (current->next!=NULL&¤t->next->previous!=current) + { + printk("%s:%d:Break in list (current %x next %x " + "current->next->previous %x)\n", + __FILE__,__LINE__,current,current->next, + current->next->previous); + KeBugCheck(KBUG_POOL_FREE_LIST_CORRUPT); + } + current=current->next; + } +} + +static void validate_used_list(void) +/* + * FUNCTION: Validate the integrity of the list of used blocks + */ +{ + block_hdr* current=used_list_head; + unsigned int blocks_seen=0; + + while (current!=NULL) + { + unsigned int base_addr = (int)current; + if (base_addr < (kernel_pool_base) || + (base_addr+current->size) > + (kernel_pool_base)+NONPAGED_POOL_SIZE) + { + printk("Block %x found outside pool area\n",current); + for(;;); + } + blocks_seen++; + if (blocks_seen > nr_used_blocks) + { + printk("Too many blocks on list\n"); + for(;;); + } +// verify_for_write(base_addr,current->size); + if (current->next!=NULL&¤t->next->previous!=current) + { + printk("Break in list (current %x next %x)\n", + current,current->next); + for(;;); + } + current=current->next; + } + +} + +static void check_duplicates(block_hdr* blk) +/* + * FUNCTION: Check a block has no duplicates + * ARGUMENTS: + * blk = block to check + * NOTE: Bug checks if duplicates are found + */ +{ + unsigned int base = (int)blk; + unsigned int last = ((int)blk) + +sizeof(block_hdr) + blk->size; + + block_hdr* current=free_list_head; + while (current!=NULL) + { + if ( (int)current > base && (int)current < last ) + { + printk("intersecting blocks on list\n"); + for(;;); + } + if ( (int)current < base && + ((int)current + current->size + sizeof(block_hdr)) + > base ) + { + printk("intersecting blocks on list\n"); + for(;;); + } + current=current->next; + } + current=used_list_head; + while (current!=NULL) + { + if ( (int)current > base && (int)current < last ) + { + printk("intersecting blocks on list\n"); + for(;;); + } + if ( (int)current < base && + ((int)current + current->size + sizeof(block_hdr)) + > base ) + { + printk("intersecting blocks on list\n"); + for(;;); + } + current=current->next; + } + +} + +static void validate_kernel_pool(void) +/* + * FUNCTION: Checks the integrity of the kernel memory heap + */ +{ + block_hdr* current=NULL; + + validate_free_list(); + validate_used_list(); + + current=free_list_head; + while (current!=NULL) + { + check_duplicates(current); + current=current->next; + } + current=used_list_head; + while (current!=NULL) + { + check_duplicates(current); + current=current->next; + } +} + +static void add_to_free_list(block_hdr* blk) +/* + * FUNCTION: add the block to the free list (internal) + */ +{ + blk->next=free_list_head; + blk->previous=NULL; + if (free_list_head!=NULL) + { + free_list_head->previous=blk; + } + free_list_head=blk; + nr_free_blocks++; +} + +static void add_to_used_list(block_hdr* blk) +/* + * FUNCTION: add the block to the used list (internal) + */ +{ + blk->next=used_list_head; + blk->previous=NULL; + if (used_list_head!=NULL) + { + used_list_head->previous=blk; + } + used_list_head=blk; + nr_used_blocks++; +} + + +static void remove_from_free_list(block_hdr* current) +{ + if (current->next==NULL&¤t->previous==NULL) + { + free_list_head=NULL; + } + else + { + if (current->previous!=NULL) + { + current->previous->next=current->next; + } + if (current->next!=NULL) + { + DPRINT("current->previous %x\n",current->previous); + current->next->previous=current->previous; + } + } + nr_free_blocks--; +} + +#ifdef BROKEN_VERSION_OF_REMOVE_FROM_FREE_LIST +static void remove_from_free_list(block_hdr* current) +{ + if (current->next==NULL&¤t->previous==NULL) + { + free_list_head=NULL; + } + else + { + if (current->next==NULL) + { + current->previous->next=NULL; + } + else + { + current->previous->next=current->next; + } + if (current->previous==NULL) + { + current->next->previous=NULL; + } + else + { + current->next->previous=current->previous; + } + } + nr_free_blocks--; +} +#endif + +static void remove_from_used_list(block_hdr* current) +{ + if (current->next==NULL&¤t->previous==NULL) + { + used_list_head=NULL; + } + else + { + if (current->previous==NULL) + { + current->next->previous=NULL; + used_list_head=current->next; + } + else + { + current->previous->next=current->next; + } + if (current->next!=NULL) + { + current->next->previous=current->previous; + } + else + { + current->previous->next=NULL; + } + } + nr_used_blocks--; +} + + +inline static void* block_to_address(block_hdr* blk) +/* + * FUNCTION: Translate a block header address to the corresponding block + * address (internal) + */ +{ + return ( (void *) ((int)blk + sizeof(block_hdr)) ); +} + +inline static block_hdr* address_to_block(void* addr) +{ + return (block_hdr *) + ( ((int)addr) - sizeof(block_hdr) ); +} + +static unsigned int alloc_pool_region(unsigned int nr_pages) +/* + * FUNCTION: Allocates a region of pages within the nonpaged pool area + */ +{ + unsigned int start = 0; + unsigned int length = 0; + unsigned int i,j; + + DPRINT("alloc_pool_region(nr_pages = %d)\n",nr_pages); + + for (i=1; i(2*sizeof(block_hdr))) + { + used_blk = (struct _block_hdr *)start; + DPRINT("Creating block at %x\n",start); + used_blk->size = size; + add_to_used_list(used_blk); + + free_blk = (block_hdr *)(start + sizeof(block_hdr) + size); + DPRINT("Creating block at %x\n",free_blk); + free_blk->size = (nr_pages * PAGESIZE) -((sizeof(block_hdr)*2) + size); + add_to_free_list(free_blk); + } + else + { + used_blk = (struct _block_hdr *)start; + used_blk->size = nr_pages * PAGESIZE; + add_to_used_list(used_blk); + } + + validate_kernel_pool(); + return(used_blk); +} + +static void* take_block(block_hdr* current, unsigned int size) +/* + * FUNCTION: Allocate a used block of least 'size' from the specified + * free block + * RETURNS: The address of the created memory block + */ +{ + /* + * If the block is much bigger than required then split it and + * return a pointer to the allocated section. If the difference + * between the sizes is marginal it makes no sense to have the + * extra overhead + */ + if (current->size > (1 + size + sizeof(block_hdr))) + { + /* + * Replace the bigger block with a smaller block in the + * same position in the list + */ + block_hdr* free_blk = (block_hdr *)(((int)current) + + sizeof(block_hdr) + size); + free_blk->next = current->next; + free_blk->previous = current->previous; + if (current->next) + { + current->next->previous = free_blk; + } + if (current->previous) + { + current->previous->next = free_blk; + } + free_blk->size = current->size - (sizeof(block_hdr) + size); + if (current==free_list_head) + { + free_list_head=free_blk; + } + + current->size=size; + add_to_used_list(current); + + validate_kernel_pool(); + return(block_to_address(current)); + } + + /* + * Otherwise allocate the whole block + */ + remove_from_free_list(current); + add_to_used_list(current); + + validate_kernel_pool(); + return(block_to_address(current)); +} + +asmlinkage VOID ExFreePool(PVOID block) +/* + * FUNCTION: Releases previously allocated memory + * ARGUMENTS: + * block = block to free + */ +{ + block_hdr* blk=address_to_block(block); + DPRINT("(%s:%d) freeing block %x\n",__FILE__,__LINE__,blk); + + validate_kernel_pool(); + /* + * Please don't change the order + */ + remove_from_used_list(blk); + add_to_free_list(blk); + + validate_kernel_pool(); +} + +#define CACHE_ALIGNMENT (16) + +PVOID ExAllocatePool(ULONG type, ULONG size) +/* + * FUNCTION: Allocates memory from the pool + * ARGUMENTS: + * size = minimum size of the block to be allocated + * type = the type of memory to use for the block + * RETURNS: + * the address of the block if it succeeds + */ +{ + PVOID Block; + + if (type == NonPagedPoolCacheAligned || + type == NonPagedPoolCacheAlignedMustS) + { + size = size + CACHE_ALIGNMENT; + } + + switch(type) + { + case NonPagedPool: + case NonPagedPoolMustSucceed: + case NonPagedPoolCacheAligned: + case NonPagedPoolCacheAlignedMustS: + Block = ExAllocateNonPagedPool(type,size); + break; + + case PagedPool: + case PagedPoolCacheAligned: + Block = ExAllocatePagedPool(type,size); + break; + + default: + return(NULL); + }; + + if ((type==NonPagedPoolMustSucceed || type==NonPagedPoolCacheAlignedMustS) + && Block==NULL) + { + KeBugCheck(MUST_SUCCEED_POOL_EMPTY); + } + if (type == NonPagedPoolCacheAligned || + type == NonPagedPoolCacheAlignedMustS) + { + Block = Block + CACHE_ALIGNMENT - (((int)Block)%CACHE_ALIGNMENT); + } + return(Block); +} + +static PVOID ExAllocatePagedPool(ULONG type, ULONG size) +{ + UNIMPLEMENTED; +} + +static PVOID ExAllocateNonPagedPool(ULONG type, ULONG size) +{ + block_hdr* current=NULL; + + DPRINT("kmalloc(size %d)\n",size); + validate_kernel_pool(); + + /* + * accomodate this useful idiom + */ + if (size==0) + { + return(NULL); + } + + /* + * Look for an already created block of sufficent size + */ + current=free_list_head; + + while (current!=NULL) + { + DPRINT("current %x size %x next %x\n",current,current->size, + current->next); + if (current->size>=size) + { + DPRINT("found block %x of size %d\n",current,size); + return(take_block(current,size)); + } + current=current->next; + } + + /* + * Otherwise create a new block + */ + return(block_to_address(grow_kernel_pool(size))); +} + +PVOID ExAllocatePoolWithQuota(POOL_TYPE PoolType, ULONG NumberOfBytes) +{ + PVOID Block; + PKTHREAD current = KeGetCurrentThread(); + + Block = ExAllocatePool(PoolType,NumberOfBytes); + switch(PoolType) + { + case NonPagedPool: + case NonPagedPoolMustSucceed: + case NonPagedPoolCacheAligned: + case NonPagedPoolCacheAlignedMustS: +// current->NPagedPoolQuota = current->NPagedPoolQuota - NumberOfBytes; + break; + + case PagedPool: + case PagedPoolCacheAligned: +// current->PagedPoolQuota = current->PagedPoolQuota - NumberOfBytes; + break; + }; + return(Block); +} + +PVOID ExAllocatePoolWithQuotaTag(POOL_TYPE PoolType, ULONG NumberOfBytes, + ULONG Tag) +{ + PVOID Block; + Block=ExAllocatePoolWithQuota(PoolType,NumberOfBytes+sizeof(ULONG)); + ((ULONG *)Block)[0]=Tag; + return(Block+4); +} + +PVOID ExAllocatePoolWithTag(POOL_TYPE PoolType, ULONG NumberOfBytes, + ULONG Tag) +/* + * FUNCTION: Allocates pool memory and inserts a caller supplied tag before + * the block allocated + * ARGUMENTS: + * PoolType = Type of memory to allocate + * NumberOfBytes = Number of bytes to allocate + * Tag = Tag + * RETURNS: The address of the block allocated + */ +{ + PVOID Block; + Block=ExAllocatePool(PoolType,NumberOfBytes+sizeof(ULONG)); + ((ULONG *)Block)[0]=Tag; + return(Block+4); +} diff --git a/reactos/ntoskrnl/mm/section.c b/reactos/ntoskrnl/mm/section.c new file mode 100644 index 00000000000..a6059707913 --- /dev/null +++ b/reactos/ntoskrnl/mm/section.c @@ -0,0 +1,45 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/mm/section.c + * PURPOSE: Implements section objects + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +NTSTATUS ZwOpenSection(PHANDLE SectionHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes) +{ + UNIMPLEMENTED; +} + +NTSTATUS ZwMapViewOfSection(HANDLE SectionHandle, + HANDLE ProcessHandle, + PVOID* BaseAddress, + ULONG ZeroBits, + ULONG CommitSize, + PLARGE_INTEGER SectionOffset, + PULONG ViewSize, + SECTION_INHERIT InheritDisposition, + ULONG AllocationType, + ULONG Protect) +{ + UNIMPLEMENTED; +} + +NTSTATUS ZwUnmapViewOfSection(HANDLE ProcessHandle, PVOID BaseAddress) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/mm/virtual.c b/reactos/ntoskrnl/mm/virtual.c new file mode 100644 index 00000000000..9fbb182a681 --- /dev/null +++ b/reactos/ntoskrnl/mm/virtual.c @@ -0,0 +1,500 @@ +/* + * COPYRIGHT: See COPYING in the top directory + * PROJECT: ReactOS kernel v0.0.2 + * FILE: mm/virtual.cc + * PURPOSE: implementing the Virtualxxx section of the win32 api + * PROGRAMMER: David Welch + * UPDATE HISTORY: + * 09/4/98: Created + * 10/6/98: Corrections from Fatahi (i_fatahi@hotmail.com) + */ + +/* INCLUDE *****************************************************************/ + +#include + +#include +#include +#include + +#define NDEBUG +#include + +/* TYPES *******************************************************************/ + +/* + * These two are statically declared because mm is initalized before the + * memory pool + */ +static memory_area kernel_area_desc; +static memory_area kernel_pool_desc; + +/* + * Head of the list of system memory areas + */ +memory_area* system_memory_area_list_head=&kernel_area_desc; + +/* + * Head of the list of user memory areas (this should be per process) + */ +memory_area* memory_area_list_head=NULL; + +/* + * The base address of the kmalloc region + */ +unsigned int kernel_pool_base = 0; + + +/* FUNCTIONS ****************************************************************/ + +void VirtualInit(boot_param* bp) +/* + * FUNCTION: Intialize the memory areas list + * ARGUMENTS: + * bp = Pointer to the boot parameters + * kernel_len = Length of the kernel + */ +{ + unsigned int kernel_len = bp->end_mem - bp->start_mem; + + DPRINT("VirtualInit() %x\n",bp); + + /* + * Setup the system area descriptor list + */ + kernel_area_desc.base = KERNEL_BASE; + kernel_area_desc.length = kernel_len; + kernel_area_desc.next = &kernel_pool_desc; + kernel_area_desc.load_page=NULL; + + /* + * The kmalloc area starts one page after the kernel area + */ + kernel_pool_desc.base = KERNEL_BASE+ PAGE_ROUND_UP(kernel_len) + PAGESIZE; + kernel_pool_desc.length = NONPAGED_POOL_SIZE; + kernel_pool_desc.next = NULL; + kernel_pool_desc.load_page=NULL; + + kernel_pool_base = kernel_pool_desc.base; + DPRINT("kmalloc_region_base %x\n",kernel_pool_base); +} + + +memory_area* find_first_marea(memory_area* list_head, unsigned int base, + unsigned int length) +/* + * FUNCTION: Returns the first memory area starting in the region or the last + * one before the start of the region + * ARGUMENTS: + * list_head = Head of the list of memory areas to search + * base = base address of the region + * length = length of the region + * RETURNS: A pointer to the area found or + * NULL if the region was before the first region on the list + */ +{ + memory_area* current=list_head; + for (;;) + { + if (current==NULL) + { + return(NULL); + } + if (current->base == base && length==0) + { + return(current); + } + + if (current->base >= base) + { + if (current->base < (base+length)) + { + return(current); + } + else + { + return(current->previous); + } + } + if (current->next==NULL) + { + return(current); + } + current=current->next; + } + return(NULL); +} + +asmlinkage int page_fault_handler(unsigned int edi, + unsigned int esi, unsigned int ebp, + unsigned int esp, unsigned int ebx, + unsigned int edx, unsigned int ecx, + unsigned int eax, + unsigned int type, + unsigned int ds, + unsigned short int error_code, + unsigned int eip, + unsigned int cs, unsigned int eflags, + unsigned int esp0, unsigned int ss0) +/* + * FUNCTION: Handle a page fault + */ +{ + memory_area* marea=NULL; + + /* + * Get the address for the page fault + */ + unsigned int cr2; + __asm__("movl %%cr2,%0\n\t" : "=d" (cr2)); + DPRINT("Page fault at address %x with eip %x\n",cr2,eip); + + cr2 = PAGE_ROUND_DOWN(cr2); + + /* + * Find the memory area for the faulting address + */ + if (cr2>=KERNEL_BASE) + { + /* + * Check permissions + */ + if (cs!=KERNEL_CS) + { + printk("%s:%d\n",__FILE__,__LINE__); + return(0); + } + marea=find_first_marea(system_memory_area_list_head,cr2, + PAGESIZE); + } + else + { + marea=find_first_marea(memory_area_list_head,cr2, + PAGESIZE); + } + + /* + * If the access was to an invalid area of memory raise an exception + */ + if (marea==NULL || marea->load_page==NULL) + { + printk("%s:%d\n",__FILE__,__LINE__); + return(0); + } + + /* + * Check the access was within the area + */ + if (cr2 > (marea->base + marea->length) || cr2 < marea->base) + { + DPRINT("base was %x length %x\n",marea->base,marea->length); + DPRINT("%s:%d\n",__FILE__,__LINE__); + return(0); + } + + /* + * Call the region specific page fault handler + */ + return(marea->load_page(marea,cr2 - marea->base)); +} + + + +static LPVOID allocate_marea(DWORD dwSize, DWORD flAllocationType, + DWORD flProtect, memory_area** list_head, + unsigned int last_addr, + BOOL (*fn)(memory_area* marea, + unsigned int address)) +/* + * FUNCTION: + */ +{ + memory_area* current=*list_head; + memory_area* ndesc=NULL; + + while (current!=NULL) + { + last_addr = PAGE_ROUND_UP(current->base + current->length); + current=current->next; + } + ndesc = ExAllocatePool(NonPagedPool,sizeof(memory_area)); + ndesc->access=flProtect; + ndesc->state=flAllocationType; + ndesc->lock=FALSE; + ndesc->base=last_addr+PAGESIZE; + ndesc->length=dwSize; + ndesc->previous=current; + if (current!=NULL) + { + ndesc->next=current->next; + current->next=ndesc; + if (current->next!=NULL) + { + current->next->previous=ndesc; + } + } + else + { + *list_head=ndesc; + ndesc->next=NULL; + ndesc->previous=NULL; + } + ndesc->load_page=fn; + DPRINT("VirtualAlloc() returning %x\n",ndesc->base); + return((LPVOID)ndesc->base); +} + +void commit_region_free(memory_area* marea) +/* + * FUNCTION: Decommits the region + */ +{ + int i; + for (i=0;ilength;i=i+PAGESIZE) + { + if (is_page_present(marea->base+marea->length)) + { + free_page(MmGetPhysicalAddress(marea->base+marea->length),1); + } + } +} + +BOOL commit_region_load_page(memory_area* marea, unsigned int address) +/* + * FUNCTION: Handles a page fault on a committed region of memory + * ARGUMENTS: + * marea = memory area + * address = address of faulting access + * RETURNS: TRUE if the page was loaded + * FALSE if an exception should be generated + */ +{ + set_page(marea->base+address,0x7,get_free_page()); + return(TRUE); +} + +asmlinkage LPVOID STDCALL VirtualAlloc(LPVOID lpAddress, DWORD dwSize, + DWORD flAllocationType, + DWORD flProtect) +{ +/* + * FUNCTION: Create a memory area + * ARGUMENTS: + * lpAddress = the base address of the area or NULL if the system + * decides the base + * dwSize = the size of the area + * flAllocationType = the type of allocation + * MEM_COMMIT = accessible + * MEM_RESERVE = not accessible but can't be allocated + * flProtect = what protection to give the area + * RETURNS: The base address of the block + */ + DPRINT("VirtualAlloc() lpAddress %x dwSize %x flAllocationType %x ", + lpAddress,dwSize,flAllocationType); + DPRINT("flProtect %x\n",flProtect); + + if (lpAddress==NULL) + { + /* + * We decide the address + */ + if (flProtect & PAGE_SYSTEM) + { + return(allocate_marea(dwSize,flAllocationType, + flProtect,&system_memory_area_list_head, + KERNEL_BASE,commit_region_load_page)); + } + else + { + return(allocate_marea(dwSize,flAllocationType, + flProtect,&memory_area_list_head,PAGESIZE, + commit_region_load_page)); + } + } + else + { + memory_area* marea=NULL; + if (lpAddress < ((PVOID)KERNEL_BASE)) + { + marea=find_first_marea(memory_area_list_head, + (unsigned int)lpAddress,dwSize); + } + else + { + marea=find_first_marea(system_memory_area_list_head, + (unsigned int)lpAddress,dwSize); + } + + /* + * Check someone hasn't already allocated that area + */ + if (marea!=NULL && marea->base <= (unsigned int)lpAddress && + (marea->base + marea->length) > (unsigned int)lpAddress) + { + SetLastError(ERROR_INVALID_DATA); + return(0); + } + + /* + * Grab the area + */ + } +} + +BOOL WINAPI VirtualFreeEx(HANDLE hProcess, LPVOID lpAddress, DWORD dwSize, + DWORD dwFreeType) +/* + * FUNCTION: Releases, decommits or both a region of memory within the + * virtual address of a specified process + * ARGUMENTS: + * hProcess = Process to act on + * lpAddress = starting virtual address to free + * dwSize = Size in bytes of the memory region to free + * dwFreeType = Type of free operation + * RETURNS: On success non-zero + * On failure zero + * NOTE: This tries to optimize for the most common case which is for + * regions to be decommitted in large chunks. If a process alternatedly + * decommitted every other page in a region this function would be extremely + * inefficent. + */ +{ + memory_area* marea = NULL; + + /* + * Check our permissions for hProcess here + */ + + /* + * Get the list of memory areas corresponding to hProcess here + */ + + /* + * Do the business + */ + if (dwFreeType==MEM_RELEASE) + { + if (dwSize!=0) + { + SetLastError(ERROR_INVALID_BLOCK_LENGTH); + return(0); + } + + marea = find_first_marea(memory_area_list_head,(unsigned int)lpAddress, + 1); + + if (marea==NULL || marea->base!=((int)lpAddress)) + { + SetLastError(ERROR_INVALID_BLOCK); + return(0); + } + + /* + * Ask the memory area to destroy itself + */ + marea->free(marea); + + /* + * Change the area attributes + */ + marea->access=PAGE_NOACCESS; + marea->state=MEM_FREE; + marea->type=MEM_PRIVATE; + } + else + { + } +} + +BOOL WINAPI VirtualProtectEx(HANDLE hProcess, LPVOID lpAddress, + DWORD dwSize, DWORD flNewProtect, PDWORD lpflOldProtect) +/* + * FUNCTION: + */ +{ +} + +DWORD WINAPI VirtualQueryEx(HANDLE hProcess, LPCVOID lpAddress, + PMEMORY_BASIC_INFORMATION lpBuffer, DWORD dwLength) +/* + * FUNCTION: Provides information about a range of pages within the virtual + * address space of a specified process. + * ARGUMENTS: + * hProcess = Handle of process + * lpAddress = Address of region + * lpBuffer = Buffer to store information + * dwLength = length of region + * RETURNS: The number of bytes transferred into the buffer + */ +{ + /* + * Find the memory area + */ + memory_area* marea = find_first_marea(memory_area_list_head, + (unsigned int) lpAddress, + dwLength); + + /* + * Check it exists + */ + if (marea==NULL || marea->base!=((int)lpAddress)) + { + SetLastError(0); + return(0); + } + + lpBuffer->BaseAddress = (void *)lpAddress; + lpBuffer->AllocationBase = (void *)marea->base; + lpBuffer->AllocationProtect = marea->initial_access; + lpBuffer->RegionSize = marea->length; + lpBuffer->State = marea->state; + lpBuffer->Protect = marea->access; + lpBuffer->Type = marea->type; + + return(sizeof(MEMORY_BASIC_INFORMATION)); +} + +BOOLEAN MmIsNonPagedSystemAddressValid(PVOID VirtualAddress) +{ + UNIMPLEMENTED; +} + +BOOLEAN MmIsAddressValid(PVOID VirtualAddress) +/* + * FUNCTION: Checks whether the given address is valid for a read or write + * ARGUMENTS: + * VirtualAddress = address to check + * RETURNS: True if the access would be valid + * False if the access would cause a page fault + * NOTES: This function checks whether a byte access to the page would + * succeed. Is this realistic for RISC processors which don't + * allow byte granular access? + */ +{ + memory_area* marea; + + if (VirtualAddress >= (PVOID)KERNEL_BASE) + { + marea = find_first_marea(system_memory_area_list_head, + (unsigned int)VirtualAddress,1); + } + else + { + marea = find_first_marea(memory_area_list_head, + (unsigned int)VirtualAddress,1); + } + + if (marea==NULL) + { + return(FALSE); + } + + if (marea->access == PAGE_NOACCESS || marea->access & PAGE_GUARD || + marea->state == MEM_FREE || marea->state == MEM_RESERVE) + { + return(FALSE); + } + + return(TRUE); +} + diff --git a/reactos/ntoskrnl/mm/zone.c b/reactos/ntoskrnl/mm/zone.c new file mode 100644 index 00000000000..7ee536a1c5e --- /dev/null +++ b/reactos/ntoskrnl/mm/zone.c @@ -0,0 +1,158 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: mkernel/mm/zone.c + * PURPOSE: Implements zone buffers + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include + +/* FUNCTIONS ***************************************************************/ + +inline static PZONE_ENTRY block_to_entry(PVOID Block) +{ + return( (PZONE_ENTRY)(Block - sizeof(ZONE_ENTRY)) ); +} + +inline static PVOID entry_to_block(PZONE_ENTRY Entry) +{ + return( (PVOID)( ((PVOID)Entry) + sizeof(ZONE_ENTRY))); +} + +BOOLEAN ExIsObjectInFirstZoneSegment(PZONE_HEADER Zone, PVOID Object) +{ + PVOID Base = (PVOID)(Zone + sizeof(ZONE_HEADER) + sizeof(ZONE_SEGMENT) + + sizeof(ZONE_ENTRY)); + PZONE_SEGMENT seg = (PZONE_SEGMENT)(Zone + sizeof(ZONE_HEADER)); + ULONG length = seg->size; + return( (Object > Base) && (Object < (Base + length))); +} + +NTSTATUS ExExtendZone(PZONE_HEADER Zone, PVOID Segment, ULONG SegmentSize) +{ + PZONE_ENTRY entry; + PZONE_SEGMENT seg; + unsigned int i; + + seg = (PZONE_SEGMENT)Segment; + seg->size = SegmentSize; + + PushEntryList(&Zone->SegmentList,&seg->Entry); + + entry = (PZONE_ENTRY)( ((PVOID)seg) + sizeof(ZONE_SEGMENT) ); + + for (i=0;i<(SegmentSize / Zone->BlockSize);i++) + { + PushEntryList(&Zone->FreeList,&entry->Entry); + entry = (PZONE_ENTRY)(((PVOID)entry) + sizeof(ZONE_ENTRY) + + Zone->BlockSize); + } + return(STATUS_SUCCESS); +} + +NTSTATUS ExInterlockedExtendZone(PZONE_HEADER Zone, PVOID Segment, + ULONG SegmentSize, PKSPIN_LOCK Lock) +{ + NTSTATUS ret; + KIRQL oldlvl; + + KeAcquireSpinLock(Lock,&oldlvl); + ret = ExExtendZone(Zone,Segment,SegmentSize); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} + +BOOLEAN ExIsFullZone(PZONE_HEADER Zone) +{ + return(Zone->FreeList.Next==NULL); +} + +PVOID ExAllocateFromZone(PZONE_HEADER Zone) +/* + * FUNCTION: Allocate a block from a zone + * ARGUMENTS: + * Zone = Zone to allocate from + * RETURNS: The base address of the block allocated + */ +{ + PSINGLE_LIST_ENTRY list_entry = PopEntryList(&Zone->FreeList); + PZONE_ENTRY entry = CONTAINING_RECORD(list_entry,ZONE_ENTRY,Entry); + return(entry_to_block(entry)); +} + +PVOID ExFreeToZone(PZONE_HEADER Zone, PVOID Block) +/* + * FUNCTION: Frees a block from a zone + * ARGUMENTS: + * Zone = Zone the block was allocated from + * Block = Block to free + */ +{ + PZONE_ENTRY entry = block_to_entry(Block); + PZONE_ENTRY ret = entry_to_block((PZONE_ENTRY)Zone->FreeList.Next); + PushEntryList(&Zone->FreeList,&entry->Entry); + return(ret); +} + +NTSTATUS ExInitializeZone(PZONE_HEADER Zone, ULONG BlockSize, + PVOID InitialSegment, ULONG InitialSegmentSize) +/* + * FUNCTION: Initalizes a zone header + * ARGUMENTS: + * Zone = zone header to be initialized + * BlockSize = Size (in bytes) of the allocation size of the zone + * InitialSegment = Initial segment of storage allocated by the + * caller + * InitialSegmentSize = Initial size of the segment + */ +{ + unsigned int i; + PZONE_SEGMENT seg; + PZONE_ENTRY entry; + + Zone->FreeList.Next=NULL; + Zone->SegmentList.Next=NULL; + Zone->BlockSize=BlockSize; + Zone->TotalSegmentSize = InitialSegmentSize; + + seg = (PZONE_SEGMENT)InitialSegment; + seg->size = InitialSegmentSize; + + PushEntryList(&Zone->SegmentList,&seg->Entry); + + entry = (PZONE_ENTRY)( ((PVOID)seg) + sizeof(ZONE_SEGMENT) ); + + for (i=0;i<(InitialSegmentSize / BlockSize);i++) + { + PushEntryList(&Zone->FreeList,&entry->Entry); + entry = (PZONE_ENTRY)(((PVOID)entry) + sizeof(ZONE_ENTRY) + BlockSize); + } +} + +PVOID ExInterlockedFreeToZone(PZONE_HEADER Zone, PVOID Block, + PKSPIN_LOCK Lock) +{ + KIRQL oldlvl; + PVOID ret; + + KeAcquireSpinLock(Lock,&oldlvl); + ret=ExFreeToZone(Zone,Block); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} + +PVOID ExInterlockedAllocateFromZone(PZONE_HEADER Zone, PKSPIN_LOCK Lock) +{ + PVOID ret; + KIRQL oldlvl; + + KeAcquireSpinLock(Lock,&oldlvl); + ret=ExAllocateFromZone(Zone); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} diff --git a/reactos/ntoskrnl/ntoskrnl.txt b/reactos/ntoskrnl/ntoskrnl.txt new file mode 100644 index 00000000000..1e2399186a4 --- /dev/null +++ b/reactos/ntoskrnl/ntoskrnl.txt @@ -0,0 +1,1084 @@ +Name: Ntoskrnl.exe + +Description: Windows NT Executive + + +Ordinal Exported +Value: Name: +1 ExAcquireFastMutexUnsafe +2 ExInterlockedAddLargeStatistic +3 ExInterlockedCompareExchange64 +4 ExInterlockedPopEntrySList +5 ExInterlockedPushEntrySList +6 ExReleaseFastMutexUnsafe +7 ExReleaseResourceLite +8 ExfInterlockedAddUlong +9 ExfInterlockedInsertHeadList +10 ExfInterlockedInsertTailList +11 ExfInterlockedPopEntryList +12 ExfInterlockedPushEntryList +13 ExfInterlockedRemoveHeadList +14 Exfi386InterlockedDecrementLong +15 Exfi386InterlockedExchangeUlong +16 Exfi386InterlockedIncrementLong +17 InterlockedCompareExchange +18 InterlockedDecrement +19 InterlockedExchange +20 InterlockedExchangeAdd +21 InterlockedIncrement +22 IofCallDriver +23 IofCompleteRequest +24 KeSetSwapContextNotifyRoutine +25 KeSetThreadSelectNotifyRoutine +26 KeSetTimeUpdateNotifyRoutine +27 KefAcquireSpinLockAtDpcLevel +28 KefReleaseSpinLockFromDpcLevel +29 KiAcquireSpinLock +30 KiReleaseSpinLock +31 ObfDereferenceObject +32 ObfReferenceObject +33 Kei386EoiHelper +34 Kii386SpinOnSpinLock +35 CcCanIWrite +36 CcCopyRead +37 CcCopyWrite +38 CcDeferWrite +39 CcFastCopyRead +40 CcFastCopyWrite +41 CcFastMdlReadWait +42 CcFastReadNotPossible +43 CcFastReadWait +44 CcFlushCache +45 CcGetDirtyPages +46 CcGetFileObjectFromBcb +47 CcGetFileObjectFromSectionPtrs +48 CcGetLsnForFileObject +49 CcInitializeCacheMap +50 CcIsThereDirtyData +51 CcMapData +52 CcMdlRead +53 CcMdlReadComplete +54 CcMdlWriteComplete +55 CcPinMappedData +56 CcPinRead +57 CcPrepareMdlWrite +58 CcPreparePinWrite +59 CcPurgeCacheSection +60 CcRepinBcb +61 CcScheduleReadAhead +62 CcSetAdditionalCacheAttributes +63 CcSetBcbOwnerPointer +64 CcSetDirtyPageThreshold +65 CcSetDirtyPinnedData +66 CcSetFileSizes +67 CcSetLogHandleForFile +68 CcSetReadAheadGranularity +69 CcUninitializeCacheMap +70 CcUnpinData +71 CcUnpinDataForThread +72 CcUnpinRepinnedBcb +73 CcZeroData +74 DbgBreakPoint +75 DbgBreakPointWithStatus +76 DbgLoadImageSymbols +77 DbgPrint +78 DbgPrompt +79 ExAcquireResourceExclusive +80 ExAcquireResourceExclusiveLite +81 ExAcquireResourceSharedLite +82 ExAcquireSharedStarveExclusive +83 ExAcquireSharedWaitForExclusive +84 ExAllocateFromPagedLookasideList +85 ExAllocatePool +86 ExAllocatePoolWithQuota +87 ExAllocatePoolWithQuotaTag +88 ExAllocatePoolWithTag +89 ExConvertExclusiveToSharedLite +90 ExCreateCallback +91 ExDeleteNPagedLookasideList +92 ExDeletePagedLookasideList +93 ExDeleteResource +94 ExDeleteResourceLite +95 ExDesktopObjectType +96 ExDisableResourceBoostLite +97 ExEnumHandleTable +98 ExEventObjectType +99 ExExtendZone +100 ExFreePool +101 ExFreeToPagedLookasideList +102 ExGetExclusiveWaiterCount +103 ExGetPreviousMode +104 ExGetSharedWaiterCount +105 ExInitializeNPagedLookasideList +106 ExInitializePagedLookasideList +107 ExInitializeResource +108 ExInitializeResourceLite +109 ExInitializeZone +110 ExInterlockedAddLargeInteger +111 ExInterlockedAddUlong +112 ExInterlockedDecrementLong +113 ExInterlockedExchangeUlong +114 ExInterlockedExtendZone +115 ExInterlockedIncrementLong +116 ExInterlockedInsertHeadList +117 ExInterlockedInsertTailList +118 ExInterlockedPopEntryList +119 ExInterlockedPushEntryList +120 ExInterlockedRemoveHeadList +121 ExIsProcessorFeaturePresent +122 ExIsResourceAcquiredExclusiveLite +123 ExIsResourceAcquiredSharedLite +124 ExLocalTimeToSystemTime +125 ExNotifyCallback +126 ExPostSystemEvent +127 ExQueryPoolBlockSize +128 ExQueueWorkItem +129 ExRaiseAccessViolation +130 ExRaiseDatatypeMisalignment +131 ExRaiseException +132 ExRaiseHardError +133 ExRaiseStatus +134 ExRegisterCallback +135 ExReinitializeResourceLite +136 ExReleaseResourceForThread +137 ExReleaseResourceForThreadLite +138 ExSetResourceOwnerPointer +139 ExSystemExceptionFilter +140 ExSystemTimeToLocalTime +141 ExUnregisterCallback +142 ExWindowStationObjectType +143 Exi386InterlockedDecrementLong +144 Exi386InterlockedExchangeUlong +145 Exi386InterlockedIncrementLong +146 FsRtlAddLargeMcbEntry +147 FsRtlAddMcbEntry +148 FsRtlAddToTunnelCache +149 FsRtlAllocatePool +150 FsRtlAllocatePoolWithQuota +151 FsRtlAllocatePoolWithQuotaTag +152 FsRtlAllocatePoolWithTag +153 FsRtlAllocateResource +154 FsRtlAreNamesEqual +155 FsRtlBalanceReads +156 FsRtlCheckLockForReadAccess +157 FsRtlCheckLockForWriteAccess +158 FsRtlCheckOplock +159 FsRtlCopyRead +160 FsRtlCopyWrite +161 FsRtlCurrentBatchOplock +162 FsRtlDeleteKeyFromTunnelCache +163 FsRtlDeleteTunnelCache +164 FsRtlDeregisterUncProvider +165 FsRtlDissectDbcs +166 FsRtlDissectName +167 FsRtlDoesDbcsContainWildCards +168 FsRtlDoesNameContainWildCards +169 FsRtlFastCheckLockForRead +170 FsRtlFastCheckLockForWrite +171 FsRtlFastUnlockAll +172 FsRtlFastUnlockAllByKey +173 FsRtlFastUnlockSingle +174 FsRtlFindInTunnelCache +175 FsRtlGetFileSize +176 FsRtlGetNextFileLock +177 FsRtlGetNextLargeMcbEntry +178 FsRtlGetNextMcbEntry +179 FsRtlInitializeFileLock +180 FsRtlInitializeLargeMcb +181 FsRtlInitializeMcb +182 FsRtlInitializeOplock +183 FsRtlInitializeTunnelCache +184 FsRtlIsDbcsInExpression +185 FsRtlIsFatDbcsLegal +186 FsRtlIsHpfsDbcsLegal +187 FsRtlIsNameInExpression +188 FsRtlIsNtstatusExpected +189 FsRtlIsTotalDeviceFailure +190 FsRtlLegalAnsiCharacterArray +191 FsRtlLookupLargeMcbEntry +192 FsRtlLookupLastLargeMcbEntry +193 FsRtlLookupLastMcbEntry +194 FsRtlLookupMcbEntry +195 FsRtlMdlRead +196 FsRtlMdlReadComplete +197 FsRtlMdlReadCompleteDev +198 FsRtlMdlReadDev +199 FsRtlMdlWriteComplete +200 FsRtlMdlWriteCompleteDev +201 FsRtlNormalizeNtstatus +202 FsRtlNotifyChangeDirectory +203 FsRtlNotifyCleanup +204 FsRtlNotifyFullChangeDirectory +205 FsRtlNotifyFullReportChange +206 FsRtlNotifyInitializeSync +207 FsRtlNotifyReportChange +208 FsRtlNotifyUninitializeSync +209 FsRtlNumberOfRunsInLargeMcb +210 FsRtlNumberOfRunsInMcb +211 FsRtlOplockFsctrl +212 FsRtlOplockIsFastIoPossible +213 FsRtlPostPagingFileStackOverflow +214 FsRtlPostStackOverflow +215 FsRtlPrepareMdlWrite +216 FsRtlPrepareMdlWriteDev +217 FsRtlPrivateLock +218 FsRtlProcessFileLock +219 FsRtlRegisterUncProvider +220 FsRtlRemoveLargeMcbEntry +221 FsRtlRemoveMcbEntry +222 FsRtlSplitLargeMcb +223 FsRtlSyncVolumes +224 FsRtlTruncateLargeMcb +225 FsRtlTruncateMcb +226 FsRtlUninitializeFileLock +227 FsRtlUninitializeLargeMcb +228 FsRtlUninitializeMcb +229 FsRtlUninitializeOplock +230 HalDispatchTable +231 HalPrivateDispatchTable +232 IoAcquireCancelSpinLock +233 IoAcquireVpbSpinLock +234 IoAdapterObjectType +235 IoAllocateAdapterChannel +236 IoAllocateController +237 IoAllocateErrorLogEntry +238 IoAllocateIrp +239 IoAllocateMdl +240 IoAssignResources +241 IoAttachDevice +242 IoAttachDeviceByPointer +243 IoAttachDeviceToDeviceStack +244 IoBuildAsynchronousFsdRequest +245 IoBuildDeviceIoControlRequest +246 IoBuildPartialMdl +247 IoBuildSynchronousFsdRequest +248 IoCallDriver +249 IoCancelIrp +250 IoCheckDesiredAccess +251 IoCheckEaBufferValidity +252 IoCheckFunctionAccess +253 IoCheckShareAccess +254 IoCompleteRequest +255 IoConnectInterrupt +256 IoCreateController +257 IoCreateDevice +258 IoCreateFile +259 IoCreateNotificationEvent +260 IoCreateStreamFileObject +261 IoCreateSymbolicLink +262 IoCreateSynchronizationEvent +263 IoCreateUnprotectedSymbolicLink +264 IoDeleteController +265 IoDeleteDevice +266 IoDeleteSymbolicLink +267 IoDetachDevice +268 IoDeviceHandlerObjectSize +269 IoDeviceHandlerObjectType +270 IoDeviceObjectType +271 IoDisconnectInterrupt +272 IoDriverObjectType +273 IoEnqueueIrp +274 IoFastQueryNetworkAttributes +275 IoFileObjectType +276 IoFreeController +277 IoFreeIrp +278 IoFreeMdl +279 IoGetAttachedDevice +280 IoGetBaseFileSystemDeviceObject +281 IoGetConfigurationInformation +282 IoGetCurrentProcess +283 IoGetDeviceObjectPointer +284 IoGetDeviceToVerify +285 IoGetFileObjectGenericMapping +286 IoGetInitialStack +287 IoGetRelatedDeviceObject +288 IoGetRequestorProcess +289 IoGetStackLimits +290 IoGetTopLevelIrp +291 IoInitializeIrp +292 IoInitializeTimer +293 IoIsOperationSynchronous +294 IoIsSystemThread +295 IoMakeAssociatedIrp +296 IoOpenDeviceInstanceKey +297 IoPageRead +298 IoQueryDeviceDescription +299 IoQueryDeviceEnumInfo +300 IoQueryFileInformation +301 IoQueryVolumeInformation +302 IoQueueThreadIrp +303 IoRaiseHardError +304 IoRaiseInformationalHardError +305 IoReadOperationCount +306 IoReadTransferCount +307 IoRegisterDriverReinitialization +308 IoRegisterFileSystem +309 IoRegisterFsRegistrationChange +310 IoRegisterShutdownNotification +311 IoReleaseCancelSpinLock +312 IoReleaseVpbSpinLock +313 IoRemoveShareAccess +314 IoReportHalResourceUsage +315 IoReportResourceUsage +316 IoSetDeviceToVerify +317 IoSetHardErrorOrVerifyDevice +318 IoSetInformation +319 IoSetShareAccess +320 IoSetThreadHardErrorMode +321 IoSetTopLevelIrp +322 IoStartNextPacket +323 IoStartNextPacketByKey +324 IoStartPacket +325 IoStartTimer +326 IoStatisticsLock +327 IoStopTimer +328 IoSynchronousPageWrite +329 IoThreadToProcess +330 IoUnregisterFileSystem +331 IoUnregisterFsRegistrationChange +332 IoUnregisterShutdownNotification +333 IoUpdateShareAccess +334 IoVerifyVolume +335 IoWriteErrorLogEntry +336 IoWriteOperationCount +337 IoWriteTransferCount +338 KdDebuggerEnabled +339 KdDebuggerNotPresent +340 KdPollBreakIn +341 Ke386CallBios +342 Ke386IoSetAccessProcess +343 Ke386QueryIoAccessMap +344 Ke386SetIoAccessMap +345 KeAcquireSpinLockAtDpcLevel +346 KeAddSystemServiceTable +347 KeAttachProcess +348 KeBoostCurrentThread +349 KeBugCheck +350 KeBugCheckEx +351 KeCancelTimer +352 KeClearEvent +353 KeConnectInterrupt +354 KeDcacheFlushCount +355 KeDelayExecutionThread +356 KeDeregisterBugCheckCallback +357 KeDetachProcess +358 KeDisconnectInterrupt +359 KeEnterCriticalRegion +360 KeEnterKernelDebugger +361 KeFindConfigurationEntry +362 KeFindConfigurationNextEntry +363 KeFlushEntireTb +364 KeGetCurrentThread +365 KeGetPreviousMode +366 KeI386AbiosCall +367 KeI386AllocateGdtSelectors +368 KeI386Call16BitCStyleFunction +369 KeI386Call16BitFunction +370 KeI386FlatToGdtSelector +371 KeI386GetLid +372 KeI386MachineType +373 KeI386ReleaseGdtSelectors +374 KeI386ReleaseLid +375 KeI386SetGdtSelector +376 KeIcacheFlushCount +377 KeInitializeApc +378 KeInitializeDeviceQueue +379 KeInitializeDpc +380 KeInitializeEvent +381 KeInitializeInterrupt +382 KeInitializeMutant +383 KeInitializeMutex +384 KeInitializeQueue +385 KeInitializeSemaphore +386 KeInitializeSpinLock +387 KeInitializeTimer +388 KeInitializeTimerEx +389 KeInsertByKeyDeviceQueue +390 KeInsertDeviceQueue +391 KeInsertHeadQueue +392 KeInsertQueue +393 KeInsertQueueApc +394 KeInsertQueueDpc +395 KeIsExecutingDpc +396 KeLeaveCriticalRegion +397 KeLoaderBlock +398 KeNumberProcessors +399 KeProfileInterrupt +400 KeProfileInterruptWithSource +401 KePulseEvent +402 KeQuerySystemTime +403 KeQueryTickCount +404 KeQueryTimeIncrement +405 KeRaiseUserException +406 KeReadStateEvent +407 KeReadStateMutant +408 KeReadStateMutex +409 KeReadStateQueue +410 KeReadStateSemaphore +411 KeReadStateTimer +412 KeRegisterBugCheckCallback +413 KeReleaseMutant +414 KeReleaseMutex +415 KeReleaseSemaphore +416 KeReleaseSpinLockFromDpcLevel +417 KeRemoveByKeyDeviceQueue +418 KeRemoveDeviceQueue +419 KeRemoveEntryDeviceQueue +420 KeRemoveQueue +421 KeRemoveQueueDpc +422 KeResetEvent +423 KeRestoreFloatingPointState +424 KeRundownQueue +425 KeSaveFloatingPointState +426 KeServiceDescriptorTable +427 KeSetAffinityThread +428 KeSetBasePriorityThread +429 KeSetDmaIoCoherency +430 KeSetEvent +431 KeSetEventBoostPriority +432 KeSetIdealProcessorThread +433 KeSetImportanceDpc +434 KeSetKernelStackSwapEnable +435 KeSetPriorityThread +436 KeSetProfileIrql +437 KeSetTargetProcessorDpc +438 KeSetTimeIncrement +439 KeSetTimer +440 KeSetTimerEx +441 KeSynchronizeExecution +442 KeTerminateThread +443 KeTickCount +444 KeUpdateRunTime +445 KeUpdateSystemTime +446 KeUserModeCallback +447 KeWaitForMultipleObjects +448 KeWaitForMutexObject +449 KeWaitForSingleObject +450 KiBugCheckData +451 KiCoprocessorError +452 KiDeliverApc +453 KiDispatchInterrupt +454 KiIpiServiceRoutine +455 KiUnexpectedInterrupt +456 LdrAccessResource +457 LdrEnumResources +458 LdrFindResourceDirectory_U +459 LdrFindResource_U +460 LpcRequestPort +461 LsaCallAuthenticationPackage +462 LsaDeregisterLogonProcess +463 LsaFreeReturnBuffer +464 LsaLogonUser +465 LsaLookupAuthenticationPackage +466 LsaRegisterLogonProcess +467 MmAdjustWorkingSetSize +468 MmAllocateContiguousMemory +469 MmAllocateNonCachedMemory +470 MmBuildMdlForNonPagedPool +471 MmCanFileBeTruncated +472 MmCreateMdl +473 MmCreateSection +474 MmDbgTranslatePhysicalAddress +475 MmDisableModifiedWriteOfSection +476 MmFlushImageSection +477 MmForceSectionClosed +478 MmFreeContiguousMemory +479 MmFreeNonCachedMemory +480 MmGetPhysicalAddress +481 MmGrowKernelStack +482 MmIsAddressValid +483 MmIsNonPagedSystemAddressValid +484 MmIsRecursiveIoFault +485 MmIsThisAnNtAsSystem +486 MmLockPagableDataSection +487 MmLockPagableImageSection +488 MmLockPagableSectionByHandle +489 MmMapIoSpace +490 MmMapLockedPages +491 MmMapMemoryDumpMdl +492 MmMapVideoDisplay +493 MmMapViewInSystemSpace +494 MmMapViewOfSection +495 MmPageEntireDriver +496 MmProbeAndLockPages +497 MmQuerySystemSize +498 MmResetDriverPaging +499 MmSectionObjectType +500 MmSecureVirtualMemory +501 MmSetAddressRangeModified +502 MmSetBankedSection +503 MmSizeOfMdl +504 MmUnlockPagableImageSection +505 MmUnlockPages +506 MmUnmapIoSpace +507 MmUnmapLockedPages +508 MmUnmapVideoDisplay +509 MmUnmapViewInSystemSpace +510 MmUnmapViewOfSection +511 MmUnsecureVirtualMemory +512 NlsAnsiCodePage +513 NlsLeadByteInfo +514 NlsMbCodePageTag +515 NlsMbOemCodePageTag +516 NlsOemLeadByteInfo +517 NtAddAtom +518 NtAdjustPrivilegesToken +519 NtAllocateLocallyUniqueId +520 NtAllocateUuids +521 NtAllocateVirtualMemory +522 NtBuildNumber +523 NtClose +524 NtConnectPort +525 NtCreateEvent +526 NtCreateFile +527 NtCreateSection +528 NtDeleteAtom +529 NtDeleteFile +530 NtDeviceIoControlFile +531 NtDuplicateObject +532 NtDuplicateToken +533 NtFindAtom +534 NtFreeVirtualMemory +535 NtFsControlFile +536 NtGlobalFlag +537 NtLockFile +538 NtMapViewOfSection +539 NtNotifyChangeDirectoryFile +540 NtOpenFile +541 NtOpenProcess +542 NtOpenProcessToken +543 NtQueryDirectoryFile +544 NtQueryEaFile +545 NtQueryInformationAtom +546 NtQueryInformationFile +547 NtQueryInformationProcess +548 NtQueryInformationToken +549 NtQueryOleDirectoryFile +550 NtQuerySecurityObject +551 NtQueryVolumeInformationFile +552 NtReadFile +553 NtRequestPort +554 NtRequestWaitReplyPort +555 NtSetEvent +556 NtSetInformationFile +557 NtSetInformationProcess +558 NtSetInformationThread +559 NtSetSecurityObject +560 NtUnlockFile +561 NtVdmControl +562 NtWaitForSingleObject +563 NtWriteFile +564 ObAssignSecurity +565 ObCheckCreateObjectAccess +566 ObCheckObjectAccess +567 ObCreateObject +568 ObDereferenceObject +569 ObFindHandleForObject +570 ObGetObjectPointerCount +571 ObGetObjectSecurity +572 ObInsertObject +573 ObMakeTemporaryObject +574 ObOpenObjectByName +575 ObOpenObjectByPointer +576 ObQueryNameString +577 ObQueryObjectAuditingByHandle +578 ObReferenceObjectByHandle +579 ObReferenceObjectByName +580 ObReferenceObjectByPointer +581 ObReleaseObjectSecurity +582 ObSetSecurityDescriptorInfo +583 PfxFindPrefix +584 PfxInitialize +585 PfxInsertPrefix +586 PfxRemovePrefix +587 PoQueryPowerSequence +588 PoRequestPowerChange +589 PoSetDeviceIdleDetection +590 ProbeForWrite +591 PsAssignImpersonationToken +592 PsChargePoolQuota +593 PsCreateSystemProcess +594 PsCreateSystemThread +595 PsCreateWin32Process +596 PsEstablishWin32Callouts +597 PsGetCurrentProcessId +598 PsGetCurrentThreadId +599 PsGetProcessExitTime +600 PsGetVersion +601 PsImpersonateClient +602 PsInitialSystemProcess +603 PsIsThreadTerminating +604 PsLookupProcessByProcessId +605 PsLookupProcessThreadByCid +606 PsLookupThreadByThreadId +607 PsProcessType +608 PsReferenceImpersonationToken +609 PsReferencePrimaryToken +610 PsReturnPoolQuota +611 PsRevertToSelf +612 PsSetCreateProcessNotifyRoutine +613 PsSetCreateThreadNotifyRoutine +614 PsSetLegoNotifyRoutine +615 PsSetProcessPriorityByClass +616 PsTerminateSystemThread +617 PsThreadType +618 READ_REGISTER_BUFFER_UCHAR +619 READ_REGISTER_BUFFER_ULONG +620 READ_REGISTER_BUFFER_USHORT +621 READ_REGISTER_UCHAR +622 READ_REGISTER_ULONG +623 READ_REGISTER_USHORT +624 RtlAbsoluteToSelfRelativeSD +625 RtlAddAccessAllowedAce +626 RtlAddAce +627 RtlAddAtomToAtomTable +628 RtlAllocateAndInitializeSid +629 RtlAllocateHeap +630 RtlAnsiCharToUnicodeChar +631 RtlAnsiStringToUnicodeSize +632 RtlAnsiStringToUnicodeString +633 RtlAppendAsciizToString +634 RtlAppendStringToString +635 RtlAppendUnicodeStringToString +636 RtlAppendUnicodeToString +637 RtlAreAllAccessesGranted +638 RtlAreAnyAccessesGranted +639 RtlAreBitsClear +640 RtlAreBitsSet +641 RtlAssert +642 RtlCaptureStackBackTrace +643 RtlCharToInteger +644 RtlCheckRegistryKey +645 RtlClearAllBits +646 RtlClearBits +647 RtlCompareMemory +648 RtlCompareMemoryUlong +649 RtlCompareString +650 RtlCompareUnicodeString +651 RtlCompressBuffer +652 RtlCompressChunks +653 RtlConvertLongToLargeInteger +654 RtlConvertSidToUnicodeString +655 RtlConvertUlongToLargeInteger +656 RtlCopyLuid +657 RtlCopySid +658 RtlCopyString +659 RtlCopyUnicodeString +660 RtlCreateAcl +661 RtlCreateAtomTable +662 RtlCreateHeap +663 RtlCreateRegistryKey +664 RtlCreateSecurityDescriptor +665 RtlCreateUnicodeString +666 RtlCustomCPToUnicodeN +667 RtlDecompressBuffer +668 RtlDecompressChunks +669 RtlDecompressFragment +670 RtlDelete +671 RtlDeleteAtomFromAtomTable +672 RtlDeleteElementGenericTable +673 RtlDeleteNoSplay +674 RtlDeleteRegistryValue +675 RtlDescribeChunk +676 RtlDestroyAtomTable +677 RtlDestroyHeap +678 RtlDowncaseUnicodeString +679 RtlEmptyAtomTable +680 RtlEnlargedIntegerMultiply +681 RtlEnlargedUnsignedDivide +682 RtlEnlargedUnsignedMultiply +683 RtlEnumerateGenericTable +684 RtlEnumerateGenericTableWithoutSplaying +685 RtlEqualLuid +686 RtlEqualSid +687 RtlEqualString +688 RtlEqualUnicodeString +689 RtlExtendedIntegerMultiply +690 RtlExtendedLargeIntegerDivide +691 RtlExtendedMagicDivide +692 RtlFillMemory +693 RtlFillMemoryUlong +694 RtlFindClearBits +695 RtlFindClearBitsAndSet +696 RtlFindFirstRunClear +697 RtlFindFirstRunSet +698 RtlFindLongestRunClear +699 RtlFindLongestRunSet +700 RtlFindMessage +701 RtlFindSetBits +702 RtlFindSetBitsAndClear +703 RtlFindUnicodePrefix +704 RtlFormatCurrentUserKeyPath +705 RtlFreeAnsiString +706 RtlFreeHeap +707 RtlFreeOemString +708 RtlFreeUnicodeString +709 RtlGenerate8dot3Name +710 RtlGetCallersAddress +711 RtlGetCompressionWorkSpaceSize +712 RtlGetDaclSecurityDescriptor +713 RtlGetDefaultCodePage +714 RtlGetElementGenericTable +715 RtlGetGroupSecurityDescriptor +716 RtlGetOwnerSecurityDescriptor +717 RtlImageNtHeader +718 RtlInitAnsiString +719 RtlInitCodePageTable +720 RtlInitString +721 RtlInitUnicodeString +722 RtlInitializeBitMap +723 RtlInitializeGenericTable +724 RtlInitializeSid +725 RtlInitializeUnicodePrefix +726 RtlInsertElementGenericTable +727 RtlInsertUnicodePrefix +728 RtlIntegerToChar +729 RtlIntegerToUnicodeString +730 RtlIsNameLegalDOS8Dot3 +731 RtlLargeIntegerAdd +732 RtlLargeIntegerArithmeticShift +733 RtlLargeIntegerDivide +734 RtlLargeIntegerNegate +735 RtlLargeIntegerShiftLeft +736 RtlLargeIntegerShiftRight +737 RtlLargeIntegerSubtract +738 RtlLengthRequiredSid +739 RtlLengthSecurityDescriptor +740 RtlLengthSid +741 RtlLookupAtomInAtomTable +742 RtlLookupElementGenericTable +743 RtlMapGenericMask +744 RtlMoveMemory +745 RtlMultiByteToUnicodeN +746 RtlMultiByteToUnicodeSize +747 RtlNextUnicodePrefix +748 RtlNtStatusToDosError +749 RtlNtStatusToDosErrorNoTeb +750 RtlNumberGenericTableElements +751 RtlNumberOfClearBits +752 RtlNumberOfSetBits +753 RtlOemStringToCountedUnicodeString +754 RtlOemStringToUnicodeSize +755 RtlOemStringToUnicodeString +756 RtlOemToUnicodeN +757 RtlPinAtomInAtomTable +758 RtlPrefixString +759 RtlPrefixUnicodeString +760 RtlQueryAtomInAtomTable +761 RtlQueryRegistryValues +762 RtlQueryTimeZoneInformation +763 RtlRaiseException +764 RtlRandom +765 RtlRemoveUnicodePrefix +766 RtlReserveChunk +767 RtlSecondsSince1970ToTime +768 RtlSecondsSince1980ToTime +769 RtlSetAllBits +770 RtlSetBits +771 RtlSetDaclSecurityDescriptor +772 RtlSetGroupSecurityDescriptor +773 RtlSetOwnerSecurityDescriptor +774 RtlSetSaclSecurityDescriptor +775 RtlSetTimeZoneInformation +776 RtlSplay +777 RtlSubAuthorityCountSid +778 RtlSubAuthoritySid +779 RtlTimeFieldsToTime +780 RtlTimeToSecondsSince1970 +781 RtlTimeToSecondsSince1980 +782 RtlTimeToTimeFields +783 RtlUnicodeStringToAnsiSize +784 RtlUnicodeStringToAnsiString +785 RtlUnicodeStringToCountedOemString +786 RtlUnicodeStringToInteger +787 RtlUnicodeStringToOemSize +788 RtlUnicodeStringToOemString +789 RtlUnicodeToCustomCPN +790 RtlUnicodeToMultiByteN +791 RtlUnicodeToMultiByteSize +792 RtlUnicodeToOemN +793 RtlUnwind +794 RtlUpcaseUnicodeChar +795 RtlUpcaseUnicodeString +796 RtlUpcaseUnicodeStringToAnsiString +797 RtlUpcaseUnicodeStringToCountedOemString +798 RtlUpcaseUnicodeStringToOemString +799 RtlUpcaseUnicodeToCustomCPN +800 RtlUpcaseUnicodeToMultiByteN +801 RtlUpcaseUnicodeToOemN +802 RtlUpperChar +803 RtlUpperString +804 RtlValidSecurityDescriptor +805 RtlValidSid +806 RtlWriteRegistryValue +807 RtlZeroHeap +808 RtlZeroMemory +809 RtlxAnsiStringToUnicodeSize +810 RtlxOemStringToUnicodeSize +811 RtlxUnicodeStringToAnsiSize +812 RtlxUnicodeStringToOemSize +813 SeAccessCheck +814 SeAppendPrivileges +815 SeAssignSecurity +816 SeAuditingFileEvents +817 SeAuditingFileOrGlobalEvents +818 SeCaptureSecurityDescriptor +819 SeCaptureSubjectContext +820 SeCloseObjectAuditAlarm +821 SeCreateAccessState +822 SeCreateClientSecurity +823 SeDeassignSecurity +824 SeDeleteAccessState +825 SeDeleteObjectAuditAlarm +826 SeExports +827 SeFreePrivileges +828 SeImpersonateClient +829 SeLockSubjectContext +830 sionForTerminationNotification +831 SeOpenObjectAuditAlarm +832 SeOpenObjectForDeleteAuditAlarm +833 SePrivilegeCheck +834 SePrivilegeObjectAuditAlarm +835 SePublicDefaultDacl +836 SeQueryAuthenticationIdToken +837 SeQuerySecurityDescriptorInfo +838 SeRegisterLogonSessionTerminatedRoutine +839 SeReleaseSecurityDescriptor +840 SeReleaseSubjectContext +841 SeSetAccessStateGenericMapping +842 SeSetSecurityDescriptorInfo +843 SeSinglePrivilegeCheck +844 SeSystemDefaultDacl +845 SeTokenImpersonationLevel +846 SeTokenType +847 SeUnlockSubjectContext +848 SeUnregisterLogonSessionTerminatedRoutine +849 SeValidSecurityDescriptor +850 WRITE_REGISTER_BUFFER_UCHAR +851 WRITE_REGISTER_BUFFER_ULONG +852 WRITE_REGISTER_BUFFER_USHORT +853 WRITE_REGISTER_UCHAR +854 WRITE_REGISTER_ULONG +855 WRITE_REGISTER_USHORT +856 ZwAccessCheckAndAuditAlarm +857 ZwAlertThread +858 ZwAllocateVirtualMemory +859 ZwClearEvent +860 ZwClose +861 ZwCloseObjectAuditAlarm +862 ZwConnectPort +863 ZwCreateDirectoryObject +864 ZwCreateEvent +865 ZwCreateFile +866 ZwCreateKey +867 ZwCreateSection +868 ZwCreateSymbolicLinkObject +869 ZwDeleteFile +870 ZwDeleteKey +871 ZwDeleteValueKey +872 ZwDeviceIoControlFile +873 ZwDisplayString +874 ZwDuplicateObject +875 ZwDuplicateToken +876 ZwEnumerateKey +877 ZwEnumerateValueKey +878 ZwFlushInstructionCache +879 ZwFlushKey +880 ZwFreeVirtualMemory +881 ZwFsControlFile +882 ZwLoadDriver +883 ZwLoadKey +884 ZwMakeTemporaryObject +885 ZwMapViewOfSection +886 ZwNotifyChangeKey +887 ZwOpenDirectoryObject +888 ZwOpenEvent +889 ZwOpenFile +890 ZwOpenKey +891 ZwOpenProcess +892 ZwOpenProcessToken +893 ZwOpenSection +894 ZwOpenSymbolicLinkObject +895 ZwOpenThread +896 ZwOpenThreadToken +897 ZwPulseEvent +898 ZwQueryDefaultLocale +899 ZwQueryDirectoryFile +900 ZwQueryInformationFile +901 ZwQueryInformationProcess +902 ZwQueryInformationToken +903 ZwQueryKey +904 ZwQueryObject +905 ZwQuerySection +906 ZwQuerySecurityObject +907 ZwQuerySymbolicLinkObject +908 ZwQuerySystemInformation +909 ZwQueryValueKey +910 ZwQueryVolumeInformationFile +911 ZwReadFile +912 ZwReplaceKey +913 ZwRequestWaitReplyPort +914 ZwResetEvent +915 ZwSaveKey +916 ZwSetDefaultLocale +917 ZwSetEvent +918 ZwSetInformationFile +919 ZwSetInformationObject +920 ZwSetInformationProcess +921 ZwSetInformationThread +922 ZwSetSystemInformation +923 ZwSetSystemTime +924 ZwSetValueKey +925 ZwTerminateProcess +926 ZwUnloadDriver +927 ZwUnloadKey +928 ZwUnmapViewOfSection +929 ZwWaitForMultipleObjects +930 ZwWaitForSingleObject +931 ZwWriteFile +932 ZwYieldExecution +933 _abnormal_termination +934 _alldiv +935 _allmul +936 _allrem +937 _allshl +938 _allshr +939 _aulldiv +940 _aullrem +941 _aullshr +942 _except_handler2 +943 _global_unwind2 +944 _itoa +945 _local_unwind2 +946 _purecall +947 _snprintf +948 _snwprintf +949 _stricmp +950 _strlwr +951 _strnicmp +952 _strnset +953 _strrev +954 _strset +955 _strupr +956 _vsnprintf +957 _wcsicmp +958 _wcslwr +959 _wcsnicmp +960 _wcsnset +961 _wcsrev +962 _wcsupr +963 atoi +964 atol +965 isdigit +966 islower +967 isprint +968 isspace +969 isupper +970 isxdigit +971 mbstowcs +972 mbtowc +973 memchr +974 memcpy +975 memmove +976 memset +977 qsort +978 rand +979 sprintf +980 srand +981 strcat +982 strchr +983 strcmp +984 strcpy +985 strlen +986 strncat +987 strncmp +988 strncpy +989 strrchr +990 strspn +991 strstr +992 swprintf +993 tolower +994 toupper +995 towlower +996 towupper +997 vsprintf +998 wcscat +999 wcschr +1000 wcscmp +1001 wcscpy +1002 wcscspn +1003 wcslen +1004 wcsncat +1005 wcsncmp +1006 wcsncpy +1007 wcsrchr +1008 wcsspn +1009 wcsstr +1010 wcstombs +1011 wctomb + + +Import Name: hal.dll + +Hint Exported +Value: Name: +003E KdPortSave +0046 KeRaiseIrqlToDpcLevel +0001 ExReleaseFastMutex +0000 ExAcquireFastMutex +0002 ExTryToAcquireFastMutex +0022 HalRequestSoftwareInterrupt +0023 HalReturnToFirmware +000E HalDisplayString +001E HalQueryRealTimeClock +0029 HalSetRealTimeClock +002A HalSetTimeIncrement +0042 KeGetCurrentIrql +0044 KeQueryPerformanceCounter +0016 HalGetEnvironmentVariable +0027 HalSetEnvironmentVariable +004C KfRaiseIrql +0019 HalInitSystem +0020 HalReportResourceUsage +0005 HalAllProcessorsStarted +0006 HalAllocateAdapterChannel +0017 HalGetInterruptVector +002F HalTranslateBusAddress +0004 HalAdjustResourceList +0030 IoAssignDriveLetters +0035 IoReadPartitionTable +0007 HalAllocateCommonBuffer +003A KdPortInitialize +0039 KdPortGetByte +003C KdPortPutByte +003B KdPortPollByte +004B KfLowerIrql +003D KdPortRestore +0052 READ_PORT_ULONG +0053 READ_PORT_USHORT +0051 READ_PORT_UCHAR +0058 WRITE_PORT_ULONG +0059 WRITE_PORT_USHORT +0057 WRITE_PORT_UCHAR +001A HalInitializeProcessor +001C HalProcessorIdle +000C HalClearSoftwareInterrupt +0047 KeRaiseIrqlToSynchLevel +0018 HalHandleNMI +000A HalBeginSystemInterrupt +0010 HalEndSystemInterrupt +000F HalEnableSystemInterrupt +000D HalDisableSystemInterrupt +002E HalSystemVectorDispatchEntry +0045 KeRaiseIrql +0043 KeLowerIrql +0028 HalSetProfileInterval +002C HalStartProfileInterrupt +002D HalStopProfileInterrupt +001D HalQueryDisplayParameters +004D KfReleaseSpinLock +004A KfAcquireSpinLock +0041 KeFlushWriteBuffer +0049 KeStallExecutionProcessor + +These exported and imported functions might only correspond to Windows NT 4.0 diff --git a/reactos/ntoskrnl/ob/handle.c b/reactos/ntoskrnl/ob/handle.c new file mode 100644 index 00000000000..533014d3d12 --- /dev/null +++ b/reactos/ntoskrnl/ob/handle.c @@ -0,0 +1,174 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ob/handle.c + * PURPOSE: Managing handles + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 17/06/98: Created + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* TYPES *******************************************************************/ + +/* + * PURPOSE: Defines a handle + */ +typedef struct +{ + PVOID obj; +} HANDLE_REP; + +#define HANDLE_BLOCK_ENTRIES ((PAGESIZE-sizeof(LIST_ENTRY))/sizeof(HANDLE_REP)) + +/* + * PURPOSE: Defines a page's worth of handles + */ +typedef struct +{ + LIST_ENTRY entry; + HANDLE_REP handles[HANDLE_BLOCK_ENTRIES]; +} HANDLE_BLOCK; + +/* GLOBALS *****************************************************************/ + +/* + * PURPOSE: Head of the list of handle blocks + */ +LIST_ENTRY handle_list_head = {NULL,NULL}; +KSPIN_LOCK handle_list_lock; + +/* FUNCTIONS ***************************************************************/ + +VOID ObjDestroyHandleTable(VOID) +/* + * FUNCTION: Destroys the current process's handle table + * NOTE: No references to handles in the table should be made during this + * operation + */ +{ + PLIST_ENTRY current=ExInterlockedRemoveHeadList(&handle_list_head, + &handle_list_lock); + unsigned int i; + + while (current!=NULL) + { + HANDLE_BLOCK* blk = (HANDLE_BLOCK *)current; + + /* + * Deference every handle in block + */ + for (i=0;ihandles[i].obj); + } + + /* + * Free the block + */ + ExFreePool(blk); + + current = ExInterlockedRemoveHeadList(&handle_list_head, + &handle_list_lock); + } +} + +VOID ObjInitializeHandleTable(HANDLE parent) +/* + * FUNCTION: Initializes a handle table for the current process + * ARGUMENTS: + * parent = Parent process (or NULL if this is the first process) + */ +{ + InitializeListHead(&handle_list_head); + KeInitializeSpinLock(&handle_list_lock); +} + +PVOID ObGetObjectByHandle(HANDLE h) +/* + * FUNCTION: Translate a handle to the corresponding object + * ARGUMENTS: + * h = Handle to translate + * RETURNS: The object + */ +{ + LIST_ENTRY* current = handle_list_head.Flink; + unsigned int handle = ((unsigned int)h) - 1; + unsigned int count=handle/HANDLE_BLOCK_ENTRIES; + HANDLE_BLOCK* blk = NULL; + unsigned int i; + + for (i=0;iFlink; + if (current==NULL) + { + return(NULL); + } + } + + blk = (HANDLE_BLOCK *)current; + return(blk->handles[handle%HANDLE_BLOCK_ENTRIES].obj); +} + +HANDLE ObAddHandle(PVOID obj) +/* + * FUNCTION: Add a handle referencing an object + * ARGUMENTS: + * obj = Object body that the handle should refer to + * RETURNS: The created handle + * NOTE: THe handle is valid only in the context of the current process + */ +{ + LIST_ENTRY* current = handle_list_head.Flink; + unsigned int handle=1; + unsigned int i; + HANDLE_BLOCK* new_blk = NULL; + + DPRINT("ObAddHandle(obj %)\n",obj); + + /* + * Scan through the currently allocated handle blocks looking for a free + * slot + */ + while (current!=NULL) + { + HANDLE_BLOCK* blk = (HANDLE_BLOCK *)current; + + DPRINT("Current %x\n",current); + + for (i=0;ihandles[i]); + if (blk->handles[i].obj==NULL) + { + blk->handles[i].obj=obj; + return((HANDLE)(handle+i)); + } + } + + handle = handle + HANDLE_BLOCK_ENTRIES; + current = current->Flink; + } + + /* + * Add a new handle block to the end of the list + */ + new_blk = (HANDLE_BLOCK *)ExAllocatePool(NonPagedPool,sizeof(HANDLE_BLOCK)); + memset(new_blk,0,sizeof(HANDLE_BLOCK)); + ExInterlockedInsertTailList(&handle_list_head,&new_blk->entry, + &handle_list_lock); + new_blk->handles[0].obj=obj; + return((HANDLE)handle); +} + diff --git a/reactos/ntoskrnl/ob/namespc.c b/reactos/ntoskrnl/ob/namespc.c new file mode 100644 index 00000000000..aabbda0e05e --- /dev/null +++ b/reactos/ntoskrnl/ob/namespc.c @@ -0,0 +1,363 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ob/namespc.c + * PURPOSE: Manages the system namespace + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 22/05/98: Created + */ + +/* INCLUDES ***************************************************************/ + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ****************************************************************/ + +OBJECT_TYPE DirectoryObjectType = {{0,0,NULL}, + 0, + 0, + ULONG_MAX, + ULONG_MAX, + sizeof(DEVICE_OBJECT), + 0, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + }; + +static struct +{ + OBJECT_HEADER hdr; +// DIRECTORY_OBJECT directory; + LIST_ENTRY head; +} namespc_root; + +/* FUNCTIONS **************************************************************/ + +void ObjNamespcInit(void) +/* + * FUNCTION: Initialize the object manager namespace + */ +{ + ANSI_STRING ansi_str; + + ObInitializeObjectHeader(OBJTYP_DIRECTORY,NULL,&namespc_root.hdr); + InitializeListHead(&namespc_root.head); + + RtlInitAnsiString(&ansi_str,"Directory"); + RtlAnsiStringToUnicodeString(&DirectoryObjectType.TypeName,&ansi_str, + TRUE); + ObRegisterType(OBJTYP_DIRECTORY,&DirectoryObjectType); +} + +NTSTATUS ZwCreateDirectoryObject(PHANDLE DirectoryHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes) +/* + * FUNCTION: Creates or opens a directory object (a container for other + * objects) + * ARGUMENTS: + * DirectoryHandle (OUT) = Caller supplied storage for the handle + * of the directory + * DesiredAccess = Access desired to the directory + * ObjectAttributes = Object attributes initialized with + * InitializeObjectAttributes + * RETURNS: Status + */ +{ + PDIRECTORY_OBJECT dir; + + dir = ObGenericCreateObject(DirectoryHandle,DesiredAccess,ObjectAttributes, + OBJTYP_DIRECTORY); + + /* + * Initialize the object body + */ + InitializeListHead(&dir->head); + + return(STATUS_SUCCESS); +} + +PWSTR Rtlstrrchr(PUNICODE_STRING string, WCHAR c) +{ + int i; + DPRINT("string->Length %d\n",string->Length); + for (i=(string->Length-1);i>=0;i--) + { + if (string->Buffer[i]==c) + { + return(&string->Buffer[i]); + } + } + return(NULL); +} + +VOID InitializeObjectAttributes(POBJECT_ATTRIBUTES InitializedAttributes, + PUNICODE_STRING ObjectName, + ULONG Attributes, + HANDLE RootDirectory, + PSECURITY_DESCRIPTOR SecurityDescriptor) +/* + * FUNCTION: Sets up a parameter of type OBJECT_ATTRIBUTES for a + * subsequent call to ZwCreateXXX or ZwOpenXXX + * ARGUMENTS: + * InitializedAttributes (OUT) = Caller supplied storage for the + * object attributes + * ObjectName = Full path name for object + * Attributes = Attributes for the object + * RootDirectory = Where the object should be placed or NULL + * SecurityDescriptor = Ignored + * + * NOTE: + * Either ObjectName is a fully qualified pathname or a path relative + * to RootDirectory + */ +{ + UNICODE_STRING path; + PWSTR name = NULL; + PDIRECTORY_OBJECT parent_dir; + + DPRINT("InitalizeObjectAttributes(ObjectName %w)\n",ObjectName->Buffer); + + if (RootDirectory!=NULL) + { + ObReferenceObjectByHandle(RootDirectory,DIRECTORY_TRAVERSE,NULL, + UserMode,(PVOID*)&parent_dir,NULL); + } + else + { + parent_dir = HEADER_TO_BODY((POBJECT_HEADER)&namespc_root); + } + + ASSERT_IRQL(PASSIVE_LEVEL); + + path.Buffer = ExAllocatePool(NonPagedPool, + ObjectName->Length*sizeof(WCHAR)); + path.MaximumLength = ObjectName->Length; + RtlCopyUnicodeString(&path,ObjectName); + + /* + * Seperate the path into the name of the object and the name of its + * direct parent directory + */ + name = Rtlstrrchr(&path,'\\'); + *name=0; + + /* + * Find the objects parent directory + */ + DPRINT("parent_dir %x\n",&(parent_dir->Type)); + parent_dir=(PDIRECTORY_OBJECT)ObLookupObject(parent_dir,&path); + if (parent_dir==NULL) + { + return; + } + + /* + * Make sure the parent directory doesn't disappear + */ + ObReferenceObjectByPointer(parent_dir,DIRECTORY_CREATE_OBJECT,NULL, + UserMode); + + InitializedAttributes->Attributes = Attributes; + InitializedAttributes->parent = parent_dir; + RtlInitUnicodeString(&InitializedAttributes->name,name+1); + InitializedAttributes->path = path; +} + +int _wcscmp(wchar_t* str1, wchar_t* str2) +{ + while ( (*str1)==(*str2) ) + { + str1++; + str2++; + if ( (*str1)==((wchar_t)0) && (*str1)==((wchar_t)0) ) + { + return(0); + } + } + return( (*str1) - (*str2) ); +} + +static PVOID ObDirLookup(PDIRECTORY_OBJECT dir, PWSTR name) +/* + * FUNCTION: Looks up an entry within a namespace directory + * ARGUMENTS: + * dir = Directory to lookup in + * name = Entry name to find + * RETURNS: A pointer to the object body if found + * NULL otherwise + */ +{ + LIST_ENTRY* current = ((PDIRECTORY_OBJECT)dir)->head.Flink; + POBJECT_HEADER current_obj; + DPRINT("ObDirLookup(dir %x, name %w\n",dir,name); + while (current!=NULL) + { + current_obj = CONTAINING_RECORD(current,OBJECT_HEADER,entry); + DPRINT("current_obj->name %w\n",current_obj->name.Buffer); + if ( _wcscmp(current_obj->name.Buffer, name)==0) + { + return(current_obj); + } + current = current->Flink; + } + return(NULL); +} + + +VOID ObCreateEntry(PDIRECTORY_OBJECT parent,POBJECT_HEADER Object) +/* + * FUNCTION: Add an entry to a namespace directory + * ARGUMENTS: + * parent = directory to add in + * name = Name to give the entry + * Object = Header of the object to add the entry for + */ +{ + DPRINT("ObjCreateEntry(%x,%x,%x,%w)\n",parent,Object,Object->name.Buffer, + Object->name.Buffer); + DPRINT("root type %d\n",namespc_root.hdr.Type); + DPRINT("%x\n",&(namespc_root.hdr.Type)); + DPRINT("type %x\n",&(parent->Type)); + DPRINT("type %x\n",&(BODY_TO_HEADER(parent)->Type)); + DPRINT("type %d\n",parent->Type); + assert(parent->Type == OBJTYP_DIRECTORY); + + /* + * Insert ourselves in our parents list + */ + InsertTailList(&parent->head,&Object->entry); +} + +wchar_t* _wcschr(wchar_t* str, wchar_t ch) +{ + while ((*str)!=((wchar_t)0)) + { + if ((*str)==ch) + { + return(str); + } + str++; + } + return(NULL); +} + +PVOID ObLookupObject(PDIRECTORY_OBJECT root, PUNICODE_STRING _string) +/* + * FUNCTION: Lookup an object within the system namespc + * ARGUMENTS: + * root = Directory to start lookup from + * _string = Pathname to lookup + * RETURNS: On success a pointer to the object body + * On failure NULL + */ +{ + PWSTR current; + PWSTR next; + PDIRECTORY_OBJECT current_dir = root; + POBJECT_HEADER current_hdr; + PWSTR string; + + DPRINT("root %x string %w\n",root,_string->Buffer); + + if (root==NULL) + { + current_dir = HEADER_TO_BODY(&(namespc_root.hdr)); + } + + /* + * Bit of a hack this + */ + if (_string->Buffer[0]==0) + { + DPRINT("current_dir %x\n",current_dir); + DPRINT("type %d\n",current_dir->Type); + return(current_dir); + } + + string=(PWSTR)ExAllocatePool(NonPagedPool,(_string->Length+1)*2); + wcscpy(string,_string->Buffer); + + DPRINT("string = %w\n",string); + + if (string[0]!='\\') + { + printk("(%s:%d) Non absolute pathname passed to %s\n",__FILE__, + __LINE__,__FUNCTION__); + return(NULL); + } + + current = string+1; + DPRINT("current %w\n",current); + next = _wcschr(string+1,'\\'); + if (next!=NULL) + { + *next=0; + } + DPRINT("next %x\n",next); + + while (next!=NULL) + { + DPRINT("Scanning %w next %w current %x\n",current,next+1, + current_dir); + + /* + * Check the current object is a directory + */ + if (current_dir->Type!=OBJTYP_DIRECTORY) + { + printk("(%s:%d) Bad path component\n",__FILE__, + __LINE__); + ExFreePool(string); + return(NULL); + } + + /* + * Lookup the next component of the path in the directory + */ + current_hdr=(PDIRECTORY_OBJECT)ObDirLookup(current_dir,current); + if (current_hdr==NULL) + { + printk("(%s:%d) Path component not found\n",__FILE__, + __LINE__); + ExFreePool(string); + return(NULL); + } + current_dir = HEADER_TO_BODY(current_hdr); + + current = next+1; + next = _wcschr(next+1,'\\'); + if (next!=NULL) + { + *next=0; + } + } + + DPRINT("current_dir %x current %x\n",current_dir,current); + DPRINT("current %w\n",current); + current_hdr = ObDirLookup(current_dir,current); + if (current_hdr==NULL) + { + ExFreePool(string); + return(NULL); + } + DPRINT("Returning %x %x\n",current_hdr,HEADER_TO_BODY(current_hdr)); + ExFreePool(string); + return(HEADER_TO_BODY(current_hdr)); +} + diff --git a/reactos/ntoskrnl/ob/object.c b/reactos/ntoskrnl/ob/object.c new file mode 100644 index 00000000000..83c93bb8aa3 --- /dev/null +++ b/reactos/ntoskrnl/ob/object.c @@ -0,0 +1,230 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ob/object.c + * PURPOSE: Implements generic object managment functions + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 10/06/98: Created + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ****************************************************************/ + +/* + * List of pointers to object types + */ +static POBJECT_TYPE ObjectTypes[OBJTYP_MAX]={NULL,}; + +/* FUNCTIONS ************************************************************/ + +NTSTATUS ZwMakeTemporaryObject(HANDLE Handle) +{ + UNIMPLEMENTED; +} + +PVOID ObGenericCreateObject(PHANDLE Handle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes, + CSHORT Type) +{ + POBJECT_HEADER hdr = NULL; + + DPRINT("ObGenericCreateObject(Handle %x ObjectAttributes %x Type %x)\n", + Handle,ObjectAttributes,Type); + + /* + * Allocate the object body and header + */ + hdr=(POBJECT_HEADER)ExAllocatePool(NonPagedPool,OBJECT_ALLOC_SIZE(Type)); + if (hdr==NULL) + { + return(NULL); + } + + /* + * Initialize the object header + */ + if (ObjectAttributes!=NULL) + { + ObInitializeObjectHeader(Type,&ObjectAttributes->name,hdr); + } + else + { + ObInitializeObjectHeader(Type,NULL,hdr); + } + +// DPRINT("ObjectAttributes->parent->Type %d\n", +// ObjectAttributes->parent->Type); + if (ObjectAttributes!=NULL) + { + /* + * Add the object to its parent directory + */ + DPRINT("hdr->name.Buffer %x\n",hdr->name.Buffer); + ObCreateEntry(ObjectAttributes->parent,hdr); + } + + DPRINT("Handle %x\n",Handle); + *Handle = ObAddHandle(HEADER_TO_BODY(hdr)); + + return(HEADER_TO_BODY(hdr)); +} + +ULONG ObSizeOf(CSHORT Type) +{ + return(ObjectTypes[Type]->PagedPoolCharge); +} + +VOID ObRegisterType(CSHORT id, POBJECT_TYPE type) +/* + * FUNCTION: Registers a new type of object + * ARGUMENTS: + * typ = Pointer to the type definition to register + */ +{ + DPRINT("ObRegisterType(id %d, type %x)\n",id,type); + ObjectTypes[id]=type; +} + +VOID ObInitializeObjectHeader(CSHORT id, PUNICODE_STRING name, + POBJECT_HEADER obj) +/* + * FUNCTION: Creates a new object + * ARGUMENT: + * id = Identifier for the type of object + * obj = Pointer to the header of the object + */ +{ + if (name!=NULL) + { + DPRINT("ObInitializeObjectHeader(id %d name %w obj %x)\n",id, + name->Buffer,obj); + } + else + { + DPRINT("ObInitializeObjectHeader(id %d name %x obj %x)\n",id, + name,obj); + } + + obj->HandleCount = 0; + obj->RefCount = 0; + obj->Type = id; + if (name==NULL) + { + obj->name.Length=0; + obj->name.Buffer=NULL; + } + else + { + obj->name.Length = 0; + obj->name.MaximumLength = name->Length; + obj->name.Buffer = ExAllocatePool(NonPagedPool, + (name->Length+1)*sizeof(WCHAR)); + DPRINT("obj->name.Buffer %x\n",obj->name.Buffer); + RtlCopyUnicodeString(&obj->name,name); + DPRINT("obj->name.Buffer %x\n",obj->name.Buffer); + } +} + + +NTSTATUS ObReferenceObjectByPointer(PVOID ObjectBody, + ACCESS_MASK DesiredAccess, + POBJECT_TYPE ObjectType, + KPROCESSOR_MODE AccessMode) +/* + * FUNCTION: Increments the pointer reference count for a given object + * ARGUMENTS: + * ObjectBody = Object's body + * DesiredAccess = Desired access to the object + * ObjectType = Points to the object type structure + * AccessMode = Type of access check to perform + * RETURNS: Status + */ +{ + POBJECT_HEADER Object = BODY_TO_HEADER(ObjectBody); + + DPRINT("ObReferenceObjectByPointer(%x %x)\n",ObjectBody,Object); + + Object->RefCount++; + return(STATUS_SUCCESS); +} + +VOID ObDereferenceObject(PVOID ObjectBody) +/* + * FUNCTION: Decrements a given object's reference count and performs + * retention checks + * ARGUMENTS: + * ObjectBody = Body of the object + */ +{ + POBJECT_HEADER Object = BODY_TO_HEADER(ObjectBody); + Object->RefCount--; +} + +NTSTATUS ZwClose(HANDLE Handle) +/* + * FUNCTION: Closes a handle reference to an object + * ARGUMENTS: + * Handle = handle to close + * RETURNS: Status + */ +{ + PVOID ObjectBody; + + ASSERT_IRQL(PASSIVE_LEVEL); + + ObjectBody = ObGetObjectByHandle(Handle); + if (ObjectBody == NULL) + { + return(STATUS_INVALID_HANDLE); + } + ObDereferenceObject(ObjectBody); + return(STATUS_SUCCESS); +} + +NTSTATUS ObReferenceObjectByHandle(HANDLE Handle, + ACCESS_MASK DesiredAccess, + POBJECT_TYPE ObjectType, + KPROCESSOR_MODE AccessMode, + PVOID* Object, + POBJECT_HANDLE_INFORMATION + HandleInformationPtr + ) +/* + * FUNCTION: Increments the reference count for an object and returns a + * pointer to its body + * ARGUMENTS: + * Handle = Handle for the object + * DesiredAccess = Desired access to the object + * ObjectType + * AccessMode + * Object (OUT) = Points to the object body on return + * HandleInformation (OUT) = Contains information about the handle + * on return + * RETURNS: Status + */ +{ + PVOID ObjectBody; + + ASSERT_IRQL(PASSIVE_LEVEL); + assert(HandleInformation==NULL); + assert(Object!=NULL); + assert(Handle!=NULL); + + ObjectBody = ObGetObjectByHandle(Handle); + if (ObjectBody == NULL) + { + return(STATUS_INVALID_HANDLE); + } + return(ObReferenceObjectByPointer(ObjectBody,DesiredAccess, + ObjectType,AccessMode)); +} diff --git a/reactos/ntoskrnl/ps/process.c b/reactos/ntoskrnl/ps/process.c new file mode 100644 index 00000000000..0db1a4953a4 --- /dev/null +++ b/reactos/ntoskrnl/ps/process.c @@ -0,0 +1,27 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/psmgr/process.c + * PURPOSE: Process managment + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 21/07/98: Created + */ + +/* INCLUDES ******************************************************************/ + +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PEPROCESS PsGetCurrentProcess(VOID) +/* + * FUNCTION: Returns a pointer to the current process + */ +{ + return(PsGetCurrentThread()->Process); +} + diff --git a/reactos/ntoskrnl/ps/psmgr.c b/reactos/ntoskrnl/ps/psmgr.c new file mode 100644 index 00000000000..e4ecc2200b3 --- /dev/null +++ b/reactos/ntoskrnl/ps/psmgr.c @@ -0,0 +1,21 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/psmgr/psmgr.c + * PURPOSE: Process managment + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES **************************************************************/ + +#include +#include +#include + +/* FUNCTIONS ***************************************************************/ + +VOID PsMgrInit(VOID) +{ + ObjInitializeHandleTable(NULL); + PsInitThreadManagment(); +} diff --git a/reactos/ntoskrnl/ps/thread.c b/reactos/ntoskrnl/ps/thread.c new file mode 100644 index 00000000000..29239efb582 --- /dev/null +++ b/reactos/ntoskrnl/ps/thread.c @@ -0,0 +1,324 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ps/thread.c + * PURPOSE: Thread managment + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 23/06/98: Created + */ + +/* + * NOTE: + * + * All of the routines that manipulate the thread queue synchronize on + * a single spinlock + * + */ + +/* INCLUDES ****************************************************************/ + +#include +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* TYPES *******************************************************************/ + +/* GLOBALS ******************************************************************/ + +OBJECT_TYPE ThreadObjectType = {{NULL,0,0}, + 0, + 0, + ULONG_MAX, + ULONG_MAX, + sizeof(KTHREAD), + 0, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + }; + + +#define NR_THREAD_PRIORITY_LEVELS (32) + +static KSPIN_LOCK ThreadListLock; + +/* + * PURPOSE: List of all threads currently active + */ +static LIST_ENTRY ThreadListHead; + +/* + * PURPOSE: List of threads associated with each priority level + */ +static LIST_ENTRY PriorityListHead[NR_THREAD_PRIORITY_LEVELS]; +static BOOLEAN DoneInitYet = FALSE; + +static PKTHREAD CurrentThread; + +static ULONG NextThreadUniqueId = 0; + +/* FUNCTIONS ***************************************************************/ + +NTSTATUS ZwSetInformationThread(HANDLE ThreadHandle, + THREADINFOCLASS ThreadInformationClass, + PVOID ThreadInformation, + ULONG ThreadInformationLength) +{ + UNIMPLEMENTED; +} + +PKTHREAD KeGetCurrentThread(VOID) +{ + return(CurrentThread); +} + +PETHREAD PsGetCurrentThread(VOID) +{ + return((PETHREAD)KeGetCurrentThread()); +} + +#if CAN_WE_DARE_TO_TRY_THIS +void PsDispatchThread(void) +{ + int i; + + for (i=0; iState==THREAD_STATE_RUNNING) + { + CurrentThread->State=THREAD_STATE_RUNNABLE; + } + + /* + * Simple round robin algorithm, iterate through and dispatch the first + * runnable thread + */ + current = CONTAINING_RECORD(ThreadListHead.Flink,KTHREAD,Entry); + current_entry = ThreadListHead.Flink; + + while (current_entry!=NULL) + { + DPRINT("Scanning %x\n",current); + DPRINT("State %x Runnable %x\n",current->State,THREAD_STATE_RUNNABLE); + if (current->State == THREAD_STATE_RUNNABLE && + current !=CurrentThread) + { + DPRINT("Scheduling this one %x\n",current); + CurrentThread = current; + CurrentThread->State = THREAD_STATE_RUNNING; + KeReleaseSpinLock(&ThreadListLock,irql); + HalTaskSwitch(current); + return; + } + current_entry = current->Entry.Flink; + current = CONTAINING_RECORD(current_entry,KTHREAD,Entry); + } + + /* + * If there are no other threads then continue with the current one if + * possible + */ + if (CurrentThread->State == THREAD_STATE_RUNNABLE) + { + return; + } + + /* + * Disaster + */ + printk("Out of threads at %s:%d\n",__FILE__,__LINE__); + for(;;); +} + +void PsInitThreadManagment(void) +/* + * FUNCTION: Initialize thread managment + */ +{ + PKTHREAD first_thread; + + InitializeListHead(&ThreadListHead); + KeInitializeSpinLock(&ThreadListLock); + + ObRegisterType(OBJTYP_THREAD,&ThreadObjectType); + + first_thread = ExAllocatePool(NonPagedPool,sizeof(KTHREAD)); + first_thread->State = THREAD_STATE_RUNNING; + HalInitFirstTask(first_thread); + ExInterlockedInsertHeadList(&ThreadListHead,&first_thread->Entry, + &ThreadListLock); + CurrentThread = first_thread; + + DoneInitYet = TRUE; +} + +NTSTATUS PsWakeThread(PKTHREAD Thread) +{ + Thread->State = THREAD_STATE_RUNNABLE; +} + +NTSTATUS PsSuspendThread(VOID) +/* + * FUNCTION: Suspend the current thread + */ +{ + KIRQL oldlvl; + + DPRINT("suspending %x\n",CurrentThread); + + /* + * NOTE: When we return from PsDispatchThread the spinlock will be + * released + */ + CurrentThread->State = THREAD_STATE_SUSPENDED; + PsDispatchThread(); +} + +NTSTATUS PsCreateThread(HANDLE Parent, + LPSECURITY_ATTRIBUTES lpThreadAttributes, + PVOID Stack, + LPTHREAD_START_ROUTINE lpStartAddress, + LPVOID Parameter, + DWORD dwCreationFlags, + LPDWORD lpThreadId, + PHANDLE ThreadHandle) +/* + * FUNCTION: Creates a thread + * ARGUMENTS: + * Parent = Parent process (or NULL for current) + * lpThreadAttributes = Security descriptor for the new thread + * Stack = Caller allocated stack + * lpStartAddress = Entry point for the thread + * Parameter = Parameter to be passed to the entrypoint + * dwCreationFlags = Flags for creation + * lpThreadId = Pointer which receives thread identifier + * ThreadHandle = Variable which receives handle + * RETURNS: Status + */ +{ + +} + +NTSTATUS PsTerminateSystemThread(NTSTATUS ExitStatus) +/* + * FUNCTION: Terminates the current thread + * ARGUMENTS: + * ExitStatus = Status to pass to the creater + * RETURNS: Doesn't + */ +{ + KIRQL oldlvl; + + DPRINT("terminating %x\n",CurrentThread); + KeRaiseIrql(DISPATCH_LEVEL,&oldlvl); + CurrentThread->State = THREAD_STATE_TERMINATED; + ExInterlockedRemoveEntryList(&ThreadListHead,&CurrentThread->Entry, + &ThreadListLock); + PsDispatchThread(); + for(;;); +} + +NTSTATUS PsCreateSystemThread(PHANDLE ThreadHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes, + HANDLE ProcessHandle, + PCLIENT_ID ClientId, + PKSTART_ROUTINE StartRoutine, + PVOID StartContext) +/* + * FUNCTION: Creates a thread which executes in kernel mode + * ARGUMENTS: + * ThreadHandle (OUT) = Caller supplied storage for the returned thread + * handle + * DesiredAccess = Requested access to the thread + * ObjectAttributes = Object attributes (optional) + * ProcessHandle = Handle of process thread will run in + * NULL to use system process + * ClientId (OUT) = Caller supplied storage for the returned client id + * of the thread (optional) + * StartRoutine = Entry point for the thread + * StartContext = Argument supplied to the thread when it begins + * execution + * RETURNS: Success or failure status + */ +{ + PKTHREAD thread; + ULONG ThreadId; + ULONG ProcessId; + + thread = ObGenericCreateObject(ThreadHandle,0,NULL,OBJTYP_THREAD); + + + thread->State=THREAD_STATE_RUNNABLE; + thread->Priority=0; +// thread->Process=ObjGetObjectByHandle(ProcessHandle); + thread->ProcessHandle=ProcessHandle; + HalInitTask(thread,StartRoutine,StartContext); + +// ThreadId = InterlockedIncrement(&NextThreadUniqueId); + if (ClientId != NULL) + { + ClientId->UniqueThread = ThreadId; + } + + ExInterlockedInsertHeadList(&ThreadListHead,&thread->Entry, + &ThreadListLock); + return(STATUS_SUCCESS); +} + +LONG KeSetBasePriorityThread(PKTHREAD Thread, LONG Increment) +{ + UNIMPLEMENTED; +} + +KPRIORITY KeSetPriorityThread(PKTHREAD Thread, KPRIORITY Priority) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/rtl/ctype.c b/reactos/ntoskrnl/rtl/ctype.c new file mode 100644 index 00000000000..cbdb1133369 --- /dev/null +++ b/reactos/ntoskrnl/rtl/ctype.c @@ -0,0 +1,37 @@ +/* + * linux/lib/ctype.c + * + * Copyright (C) 1991, 1992 Linus Torvalds + */ + +#include + +#if 0 +char _ctmp; +unsigned char _ctype[] = {0x00, /* EOF */ +_C,_C,_C,_C,_C,_C,_C,_C, /* 0-7 */ +_C,_C|_S,_C|_S,_C|_S,_C|_S,_C|_S,_C,_C, /* 8-15 */ +_C,_C,_C,_C,_C,_C,_C,_C, /* 16-23 */ +_C,_C,_C,_C,_C,_C,_C,_C, /* 24-31 */ +_S|_SP,_P,_P,_P,_P,_P,_P,_P, /* 32-39 */ +_P,_P,_P,_P,_P,_P,_P,_P, /* 40-47 */ +_D,_D,_D,_D,_D,_D,_D,_D, /* 48-55 */ +_D,_D,_P,_P,_P,_P,_P,_P, /* 56-63 */ +_P,_U|_X,_U|_X,_U|_X,_U|_X,_U|_X,_U|_X,_U, /* 64-71 */ +_U,_U,_U,_U,_U,_U,_U,_U, /* 72-79 */ +_U,_U,_U,_U,_U,_U,_U,_U, /* 80-87 */ +_U,_U,_U,_P,_P,_P,_P,_P, /* 88-95 */ +_P,_L|_X,_L|_X,_L|_X,_L|_X,_L|_X,_L|_X,_L, /* 96-103 */ +_L,_L,_L,_L,_L,_L,_L,_L, /* 104-111 */ +_L,_L,_L,_L,_L,_L,_L,_L, /* 112-119 */ +_L,_L,_L,_P,_P,_P,_P,_C, /* 120-127 */ +0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 128-143 */ +0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, /* 144-159 */ +_S|_SP,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P, /* 160-175 */ +_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P,_P, /* 176-191 */ +_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U,_U, /* 192-207 */ +_U,_U,_U,_U,_U,_U,_U,_P,_U,_U,_U,_U,_U,_U,_U,_L, /* 208-223 */ +_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L,_L, /* 224-239 */ +_L,_L,_L,_L,_L,_L,_L,_P,_L,_L,_L,_L,_L,_L,_L,_L}; /* 240-255 */ +#endif + diff --git a/reactos/ntoskrnl/rtl/interlck.asm b/reactos/ntoskrnl/rtl/interlck.asm new file mode 100644 index 00000000000..ba977e77b26 --- /dev/null +++ b/reactos/ntoskrnl/rtl/interlck.asm @@ -0,0 +1,52 @@ +bits 32 +section .text + +global _InterlockedIncrement +_InterlockedIncrement + mov eax,1 + mov ebx,[esp+4] + xadd [ebx],eax + ret + +global _InterlockedDecrement +_InterlockedDecrement: + mov eax,0xffffffff + mov ebx,[esp+4] + xadd [ebx],eax + dec eax + ret + +global _InterlockedExchange +_InterlockedExchange: + push ebp + mov ebp,esp + + push eax + push ebx + + mov eax,[ebp+12] + mov ebx,[ebp+8] + xchg [ebx],eax + + pop ebx + pop eax + + mov esp,ebp + pop ebp + ret + +global _InterlockedExchangeAdd +_InterlockedExchangeAdd: + mov eax,[esp+8] + mov ebx,[esp+4] + xadd [ebx],eax + ret + +global _InterlockedCompareExchange +_InterlockedCompareExchange: + mov eax,[esp+12] + mov edx,[esp+8] + mov ebx,[esp+4] + cmpxchg [ebx],edx + mov eax,edx + ret diff --git a/reactos/ntoskrnl/rtl/largeint.c b/reactos/ntoskrnl/rtl/largeint.c new file mode 100644 index 00000000000..5c46d6e300a --- /dev/null +++ b/reactos/ntoskrnl/rtl/largeint.c @@ -0,0 +1,190 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/rtl/largeint.c + * PURPOSE: Large integer operations + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +LARGE_INTEGER RtlConvertLongToLargeInteger(LONG SignedInteger) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlConvertUlongToLargeInteger(ULONG UnsignedInteger) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlEnlargedIntegerMultiply(LONG Multiplicand, + LONG Multipler) +{ + UNIMPLEMENTED; +} + +ULONG RtlEnlargedUnsignedDivide(ULARGE_INTEGER Dividend, + ULONG Divisor, + PULONG Remainder) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlEnlargedUnsignedMultiply(ULONG Multiplicand, + ULONG Multipler) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlExtendedIntegerMultiply(LARGE_INTEGER Multiplicand, + LONG Multiplier) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlExtendedLargeIntegerDivide(LARGE_INTEGER Dividend, + ULONG Divisor, + PULONG Remainder) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlExtendedMagicDivide(LARGE_INTEGER Dividend, + LARGE_INTEGER MagicDivisor, + CCHAR ShiftCount) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER ExInterlockedAddLargeInteger(PLARGE_INTEGER Addend, + LARGE_INTEGER Increment, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerAdd(LARGE_INTEGER Addend1, + LARGE_INTEGER Addend2) +{ + UNIMPLEMENTED; +} + +VOID RtlLargeIntegerAnd(PLARGE_INTEGER Result, + LARGE_INTEGER Source, + LARGE_INTEGER Mask) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerArithmeticShift(LARGE_INTEGER LargeInteger, + CCHAR ShiftCount) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerDivide(LARGE_INTEGER Dividend, + LARGE_INTEGER Divisor, + PLARGE_INTEGER Remainder) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerEqualTo(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerEqualToZero(LARGE_INTEGER Operand) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerGreaterThan(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerGreaterThanOrEqualTo(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerGreaterThanOrEqualToZero(LARGE_INTEGER Operand1) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerGreaterThanZero(LARGE_INTEGER Operand1) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerLessThan(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerLessThanOrEqualTo(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerLessThanOrEqualToZero(LARGE_INTEGER Operand1) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerLessThanZero(LARGE_INTEGER Operand1) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerNegate(LARGE_INTEGER Subtrahend) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerNotEqualTo(LARGE_INTEGER Operand1, + LARGE_INTEGER Operand2) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlLargeIntegerNotEqualToZero(LARGE_INTEGER Operand) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerShiftLeft(LARGE_INTEGER LargeInteger, + CCHAR ShiftCount) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerShiftRight(LARGE_INTEGER LargeInteger, + CCHAR ShiftCount) +{ + UNIMPLEMENTED; +} + +LARGE_INTEGER RtlLargeIntegerSubtract(LARGE_INTEGER Minuend, + LARGE_INTEGER Subtrahend) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/rtl/list.c b/reactos/ntoskrnl/rtl/list.c new file mode 100644 index 00000000000..a090636e0de --- /dev/null +++ b/reactos/ntoskrnl/rtl/list.c @@ -0,0 +1,285 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/rtl/list.c + * PURPOSE: Manages linked lists + * PROGRAMMER: David Welch (welch@mcmail.com) + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#define NDEBUG +#include + +/* FUNCTIONS *************************************************************/ + +VOID RemoveEntryList(PLIST_ENTRY Entry) +/* + * FUNCTION: Resets the links for an entry from a double linked list + * ARGUMENTS: + * Entry = Entry to reset + * NOTE: This isn't the same as ExInterlockedRemoveEntryList + */ +{ + if (Entry->Blink!=NULL) + { + Entry->Blink->Flink=Entry->Flink; + } + if (Entry->Flink!=NULL) + { + Entry->Flink->Blink=Entry->Blink; + } +} + +PLIST_ENTRY RemoveTailList(PLIST_ENTRY ListHead) +/* + * FUNCTION: Remove the tail entry from a double linked list + * ARGUMENTS: + * ListHead = Head of the list to remove from + * RETURNS: The removed entry + */ +{ + PLIST_ENTRY entry = ListHead->Blink; + if (ListHead->Blink == ListHead->Flink) + { + ListHead->Flink = NULL; + } + if (entry!=NULL) + { + ListHead->Blink = entry->Blink; + } + return(entry); +} + +VOID ExInterlockedRemoveEntryList(PLIST_ENTRY ListHead, PLIST_ENTRY Entry, + PKSPIN_LOCK Lock) +{ + KIRQL oldlvl; + KeAcquireSpinLock(Lock,&oldlvl); + if (ListHead->Flink == Entry && ListHead->Blink == Entry) + { + ListHead->Flink = ListHead->Blink = NULL; + Entry->Flink = Entry->Blink = NULL; + KeReleaseSpinLock(Lock,oldlvl); + return; + } + if (ListHead->Flink == Entry) + { + ListHead->Flink=Entry->Flink; + Entry->Flink = Entry->Blink = NULL; + KeReleaseSpinLock(Lock,oldlvl); + return; + } + if (ListHead->Blink == Entry) + { + ListHead->Blink = Entry->Blink; + Entry->Flink = Entry->Blink = NULL; + KeReleaseSpinLock(Lock,oldlvl); + return; + } + Entry->Flink->Blink = Entry->Blink; + Entry->Blink->Flink = Entry->Flink; + Entry->Flink = Entry->Blink = NULL; + KeReleaseSpinLock(Lock,oldlvl); +} + +PLIST_ENTRY RemoveHeadList(PLIST_ENTRY ListHead) +{ + PLIST_ENTRY Old; + + DPRINT("RemoveHeadList(ListHead %x)\n",ListHead); + DPRINT("Flink %x Blink %x\n",ListHead->Flink,ListHead->Blink); + + Old = ListHead->Flink; + + if (ListHead->Flink==NULL) + { + return(NULL); + } + + DPRINT("ListHead->Flink->Flink %x\n",ListHead->Flink->Flink); + ListHead->Flink=ListHead->Flink->Flink; + if (ListHead->Flink!=NULL) + { + DPRINT("ListHead->Flink->Blink %x\n",ListHead->Flink->Blink); + ListHead->Flink->Blink=NULL; + } + return(Old); +} + +VOID RemoveEntryFromList(PLIST_ENTRY ListHead, PLIST_ENTRY Entry) +{ + if (ListHead->Flink == Entry && ListHead->Blink == Entry) + { + ListHead->Flink = ListHead->Blink = NULL; + Entry->Flink = Entry->Blink = NULL; + return; + } + if (ListHead->Flink == Entry) + { + ListHead->Flink=Entry->Flink; + Entry->Flink = Entry->Blink = NULL; + return; + } + if (ListHead->Blink == Entry) + { + ListHead->Blink = Entry->Blink; + Entry->Flink = Entry->Blink = NULL; + return; + } + Entry->Flink->Blink = Entry->Blink; + Entry->Blink->Flink = Entry->Flink; + Entry->Flink = Entry->Blink = NULL; +} + + + + +VOID InitializeListHead(PLIST_ENTRY ListHead) +/* + * FUNCTION: Initializes a double linked list + * ARGUMENTS: + * ListHead = Caller supplied storage for the head of the list + */ +{ + ListHead->Blink=NULL; + ListHead->Flink=NULL; +} + +VOID InsertTailList(PLIST_ENTRY ListHead, PLIST_ENTRY ListEntry) +/* + * FUNCTION: Inserts an entry in a double linked list + * ARGUMENTS: + * ListHead = Head of the list + * Entry = Entry to insert + */ +{ + assert(ListHead!=NULL); + assert(ListEntry!=NULL); + if (ListHead->Blink==NULL) + { + ListEntry->Blink = ListEntry->Flink = NULL; + ListHead->Blink = ListHead->Flink = ListEntry; + } + else + { + ListEntry->Blink = ListHead->Blink; + ListEntry->Flink = NULL; + ListHead->Blink->Flink = ListEntry; + ListHead->Blink = ListEntry; + } +} + +VOID InsertHeadList(PLIST_ENTRY ListHead, PLIST_ENTRY ListEntry) +{ + /* + * Insert the entry + */ + ListEntry->Blink=NULL; + ListEntry->Flink=ListHead->Flink; + + if (ListHead->Flink==NULL) + { + assert(ListHead->Blink==NULL); + ListHead->Blink = ListHead->Flink = ListEntry; + } + else + { + ListHead->Flink->Blink = ListEntry; + ListHead->Flink = ListEntry; + } +} + +PLIST_ENTRY ExInterlockedInsertTailList(PLIST_ENTRY ListHead, + PLIST_ENTRY ListEntry, + PKSPIN_LOCK Lock) +{ + PLIST_ENTRY Old = NULL; + KIRQL oldlvl; + + /* + * Lock the spinlock + */ + KeAcquireSpinLock(Lock,&oldlvl); + DPRINT("oldlvl %x\n",oldlvl); + /* + * Insert the entry + */ + Old = ListHead->Flink; + InsertTailList(ListHead,ListEntry); + + /* + * Unlock the spinlock + */ + KeReleaseSpinLock(Lock,oldlvl); + + return(Old); +} + +PLIST_ENTRY ExInterlockedInsertHeadList(PLIST_ENTRY ListHead, + PLIST_ENTRY ListEntry, + PKSPIN_LOCK Lock) +/* + * FUNCTION: Inserts an entry at the head of a doubly linked list + * ARGUMENTS: + * ListHead = Points to the head of the list + * ListEntry = Points to the entry to be inserted + * Lock = Caller supplied spinlock used to synchronise access + * RETURNS: The previous head of the list + */ +{ + PLIST_ENTRY old = NULL; + KIRQL oldlvl; + + /* + * Block on the spinlock here + */ + KeAcquireSpinLock(Lock,&oldlvl); + + /* + * Insert the entry + */ + old=ListHead->Flink; + InsertHeadList(ListHead,ListEntry); + + /* + * Release spin lock + */ + KeReleaseSpinLock(Lock,oldlvl); + + return(old); +} + +BOOLEAN IsListEmpty(PLIST_ENTRY ListHead) +/* + * FUNCTION: Determines if a list is emptry + * ARGUMENTS: + * ListHead = Head of the list + * RETURNS: True if there are no entries in the list + */ +{ + return(ListHead->Flink==NULL); +} + +PLIST_ENTRY ExInterlockedRemoveHeadList(PLIST_ENTRY Head, + PKSPIN_LOCK Lock) +/* + * FUNCTION: Removes the head of a double linked list + * ARGUMENTS: + * Head = List head + * Lock = Lock for synchronizing access to the list + * RETURNS: The removed entry + */ +{ + PLIST_ENTRY ret; + KIRQL oldlvl; + + KeAcquireSpinLock(Lock,&oldlvl); + ret = RemoveHeadList(Head); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} diff --git a/reactos/ntoskrnl/rtl/lookas.c b/reactos/ntoskrnl/rtl/lookas.c new file mode 100644 index 00000000000..e6e2799d311 --- /dev/null +++ b/reactos/ntoskrnl/rtl/lookas.c @@ -0,0 +1,73 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.cc + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +PVOID ExAllocateFromNPagedLookasideList(PNPAGED_LOOKASIDE_LIST Lookaside) +{ + UNIMPLEMENTED; +} + +PVOID ExAllocateFromPagedLookasideList(PPAGED_LOOKASIDE_LIST Lookaside) +{ + UNIMPLEMENTED; +} + +VOID ExDeleteNPagedLookasideList(PNPAGED_LOOKASIDE_LIST Lookaside) +{ + UNIMPLEMENTED; +} + +VOID ExDeletePagedLookasideList(PPAGED_LOOKASIDE_LIST Lookaside) +{ + UNIMPLEMENTED; +} + +VOID ExFreeToNPagedLookasideList(PNPAGED_LOOKASIDE_LIST Lookaside, + PVOID Entry) +{ + UNIMPLEMENTED; +} + +VOID ExFreeToPagedLookasideList(PPAGED_LOOKASIDE_LIST Lookaside, + PVOID Entry) +{ + UNIMPLEMENTED; +} + +VOID ExInitializeNPagedLookasideList(PNPAGED_LOOKASIDE_LIST Lookaside, + PALLOCATE_FUNCTION Allocate, + PFREE_FUNCTION Free, + ULONG Flags, + ULONG Size, + ULONG Tag, + USHORT Depth) +{ + UNIMPLEMENTED +} + +VOID ExInitializePagedLookasideList(PPAGED_LOOKASIDE_LIST Lookaside, + PALLOCATE_FUNCTION Allocate, + PFREE_FUNCTION Free, + ULONG Flags, + ULONG Size, + ULONG Tag, + USHORT Depth) +{ + UNIMPLEMENTED +} diff --git a/reactos/ntoskrnl/rtl/mem.c b/reactos/ntoskrnl/rtl/mem.c new file mode 100644 index 00000000000..fd0e90acbc5 --- /dev/null +++ b/reactos/ntoskrnl/rtl/mem.c @@ -0,0 +1,72 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/rtl/mem.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +ULONG RtlCompareMemory(PVOID Source1, PVOID Source2, ULONG Length) +/* + * FUNCTION: Compares blocks of memory and returns the number of equal bytes + * ARGUMENTS: + * Source1 = Block to compare + * Source2 = Block to compare + * Length = Number of bytes to compare + * RETURNS: Number of equal bytes + */ +{ + int i,total; + + for (i=0,total=0;i +#include +#include + +/* TYPES ********************************************************************/ + +typedef union _SLIST_HEADER +{ + ULONGLONG Alignment; + struct + { + SINGLE_LIST_ENTRY Next; + USHORT Depth; + USHORT Sequence; + } s; +} SLIST_HEADER, *PSLIST_HEADER; + +/* FUNCTIONS ****************************************************************/ + +VOID ExInitializeSListHead(PSLIST_HEADER SListHead) +{ + SListHead->s.Next.Next=NULL; + SListHead->s.Depth = 0; + SListHead->s.Sequence = 0; +} + + diff --git a/reactos/ntoskrnl/rtl/slist.c b/reactos/ntoskrnl/rtl/slist.c new file mode 100644 index 00000000000..42cbf1bf6cc --- /dev/null +++ b/reactos/ntoskrnl/rtl/slist.c @@ -0,0 +1,92 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS project + * FILE: kernel/rtl/slist.c + * PURPOSE: Implements single linked lists + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 28/06/98: Created + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS ****************************************************************/ + +PSINGLE_LIST_ENTRY ExInterlockedPopEntrySList(PSLIST_HEADER ListHead, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +PSINGLE_LIST_ENTRY ExInterlockedPushEntrySList(PSLIST_HEADER ListHead, + PSINGLE_LIST_ENTRY ListEntry, + PKSPIN_LOCK Lock) +{ + UNIMPLEMENTED; +} + +USHORT ExQueryDepthSListHead(PSLIST_HEADER SListHead) +{ + UNIMPLEMENTED; +} + +VOID ExInitializeSListHead(PSLIST_HEADER SListHead) +{ + UNIMPLEMENTED; +} + +PSINGLE_LIST_ENTRY PopEntryList(PSINGLE_LIST_ENTRY ListHead) +/* + * FUNCTION: Removes an entry from the head of a single linked list + * ARGUMENTS: + * ListHead = Head of the list + * RETURNS: The removed entry + */ +{ + PSINGLE_LIST_ENTRY entry = ListHead->Next; + if (entry==NULL) + { + return(NULL); + } + ListHead->Next = ListHead->Next->Next; + return(entry); +} + +PSINGLE_LIST_ENTRY ExInterlockedPopEntryList(PSINGLE_LIST_ENTRY ListHead, + PKSPIN_LOCK Lock) +{ + PSINGLE_LIST_ENTRY ret; + KIRQL oldlvl; + + KeAcquireSpinLock(Lock,&oldlvl); + ret = PopEntryList(ListHead); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} + +VOID PushEntryList(PSINGLE_LIST_ENTRY ListHead, PSINGLE_LIST_ENTRY Entry) +{ + Entry->Next = ListHead->Next; + ListHead->Next = Entry; +} + +PSINGLE_LIST_ENTRY ExInterlockedPushEntryList(PSINGLE_LIST_ENTRY ListHead, + PSINGLE_LIST_ENTRY ListEntry, + PKSPIN_LOCK Lock) +{ + KIRQL oldlvl; + PSINGLE_LIST_ENTRY ret; + + KeAcquireSpinLock(Lock,&oldlvl); + ret=ListHead->Next; + PushEntryList(ListHead,ListEntry); + KeReleaseSpinLock(Lock,oldlvl); + return(ret); +} + diff --git a/reactos/ntoskrnl/rtl/strtok.c b/reactos/ntoskrnl/rtl/strtok.c new file mode 100644 index 00000000000..af8d44a1756 --- /dev/null +++ b/reactos/ntoskrnl/rtl/strtok.c @@ -0,0 +1,66 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/rtl/strtok.c + * PURPOSE: Unicode and thread safe implementation of strtok + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + + +/* FUNCTIONS *****************************************************************/ + +PWSTR RtlStrtok(PUNICODE_STRING _string, PWSTR _sep, + PWSTR* temp) +/* + * FUNCTION: Splits a string into tokens + * ARGUMENTS: + * string = string to operate on + * if NULL then continue with previous string + * sep = Token deliminators + * temp = Tempory storage provided by the caller + * ARGUMENTS: Returns the beginning of the next token + */ +{ + PWSTR string; + PWSTR sep; + PWSTR start; + + if (_string!=NULL) + { + string = _string->Buffer; + } + else + { + string = *temp; + } + + start = string; + + while ((*string)!=0) + { + sep = _sep; + while ((*sep)!=0) + { + if ((*string)==(*sep)) + { + *string=0; + *temp=string+1; + return(start); + } + sep++; + } + string++; + } + *temp=NULL; + return(start); +} diff --git a/reactos/ntoskrnl/rtl/time.c b/reactos/ntoskrnl/rtl/time.c new file mode 100644 index 00000000000..3fc2dc87858 --- /dev/null +++ b/reactos/ntoskrnl/rtl/time.c @@ -0,0 +1,31 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/rtl/time.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID RtlTimeToTimeFields(PLARGE_INTEGER Time, + PTIME_FIELDS TimeFields) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlTimeFieldsToTime(PTIME_FIELDS TimeFields, + PLARGE_INTEGER Time) +{ + UNIMPLEMENTED; +} diff --git a/reactos/ntoskrnl/rtl/unalign.c b/reactos/ntoskrnl/rtl/unalign.c new file mode 100644 index 00000000000..143e6db2cb1 --- /dev/null +++ b/reactos/ntoskrnl/rtl/unalign.c @@ -0,0 +1,43 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: kernel/base/bug.c + * PURPOSE: Graceful system shutdown if a bug is detected + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * Created 22/05/98 + */ + +/* INCLUDES *****************************************************************/ + +#include +#include +#include + +#include + +/* FUNCTIONS *****************************************************************/ + +VOID RtlStoreUlong(PULONG Address, + ULONG Value) +{ + *Address=Value; +} + +VOID RtlStoreUshort(PUSHORT Address, + USHORT Value) +{ + *Address=Value; +} + +VOID RtlRetrieveUlong(PULONG DestinationAddress, + PULONG SourceAddress) +{ + *DestinationAddress = *SourceAddress; +} + +VOID RtlRetrieveUshort(PUSHORT DestinationAddress, + PUSHORT SourceAddress) +{ + *DestinationAddress = *SourceAddress; +} diff --git a/reactos/ntoskrnl/rtl/unicode.c b/reactos/ntoskrnl/rtl/unicode.c new file mode 100644 index 00000000000..c1514b4642e --- /dev/null +++ b/reactos/ntoskrnl/rtl/unicode.c @@ -0,0 +1,561 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/rtl/unicode.c + * PURPOSE: String functions + * PROGRAMMER: Jason Filby (jasonfilby@yahoo.com) + * UPDATE HISTORY: + * Created 10/08/98 + */ + +#include + +#include + +#include +#include +#include + +#define NDEBUG +#include + +#define Aa_Difference 'A'-'a'; + +VOID RtlUpperString(PSTRING DestinationString, PSTRING SourceString) +{ + UNIMPLEMENTED; +} + +WCHAR wtoupper(WCHAR c) +{ + if((c>='a') && (c<='z')) return c+Aa_Difference; + return c; +} + +unsigned long wstrlen(PWSTR s) +{ + WCHAR c=' '; + unsigned int len=0; + + while(c!=0) { + c=*s; + s++; + len++; + }; + s-=len; + + return len-1; +} + +ULONG RtlAnsiStringToUnicodeSize(IN PANSI_STRING AnsiString) +{ + return AnsiString->Length*2; +} + +NTSTATUS RtlAnsiStringToUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PANSI_STRING SourceString, + IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + + if (AllocateDestinationString==TRUE) + { + DestinationString->Buffer=ExAllocatePool(NonPagedPool, + (SourceString->Length+1)*2); + DestinationString->MaximumLength=SourceString->Length; + } + + DestinationString->Length=SourceString->Length; + + memset(DestinationString->Buffer,0,SourceString->Length*2); + + for (i=0; iLength; i++) + { + *DestinationString->Buffer=*SourceString->Buffer; + + SourceString->Buffer++; + DestinationString->Buffer++; + }; + *DestinationString->Buffer=0; + + SourceString->Buffer-=SourceString->Length; + DestinationString->Buffer-=SourceString->Length; + + return STATUS_SUCCESS; +} + +NTSTATUS RtlAppendUnicodeStringToString(IN OUT PUNICODE_STRING Destination, + IN PUNICODE_STRING Source) +{ + unsigned long i; + + if(Destination->MaximumLength-Destination->Length-Source->Length<0) + return STATUS_BUFFER_TOO_SMALL; + + Destination->Buffer+=Destination->Length; + for(i=0; iLength; i++) { + *Destination->Buffer=*Source->Buffer; + Destination->Buffer++; + Source->Buffer++; + }; + *Destination->Buffer=0; + Destination->Buffer-=(Destination->Length+Source->Length); + Source->Buffer-=Source->Length; + + Destination->Length+=Source->Length; + return STATUS_SUCCESS; +} + +NTSTATUS RtlAppendUnicodeToString(IN OUT PUNICODE_STRING Destination, + IN PWSTR Source) +{ + unsigned long i, slen=wstrlen(Source); + + if(Destination->MaximumLength-Destination->Length-slen<0) + return STATUS_BUFFER_TOO_SMALL; + + Destination->Buffer+=Destination->Length; + for(i=0; iBuffer=*Source; + Destination->Buffer++; + Source++; + }; + *Destination->Buffer=0; + Destination->Buffer-=(Destination->Length+slen); + Source-=slen; + + Destination->Length+=slen; + return STATUS_SUCCESS; +} + +NTSTATUS RtlCharToInteger(IN PCSZ String, IN ULONG Base, IN OUT PULONG Value) +{ + *Value=simple_strtoul((const char *)String, NULL, Base); +} + +LONG RtlCompareString(PSTRING String1, PSTRING String2, BOOLEAN CaseInsensitive) +{ + unsigned long i; + char c1, c2; + + if(String1->Length!=String2->Length) return String1->Length-String2->Length; + + for(i=0; iLength; i++) { + if(CaseInsensitive==TRUE) { + c1=toupper(*String1->Buffer); + c2=toupper(*String2->Buffer); + } else { + c1=*String1->Buffer; + c2=*String2->Buffer; + }; + if(c1!=c2) { + String1->Buffer-=i; + String2->Buffer-=i; + return c1-c2; + }; + String1->Buffer++; + String2->Buffer++; + }; + String1->Buffer-=i; + String2->Buffer-=i; + + return 0; +} + +LONG RtlCompareUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, + BOOLEAN CaseInsensitive) +{ + unsigned long i; + WCHAR wc1, wc2; + + if(String1->Length!=String2->Length) return + String1->Length-String2->Length; + + for(i=0; iLength; i++) { + if(CaseInsensitive==TRUE) { + wc1=wtoupper(*String1->Buffer); + wc2=wtoupper(*String2->Buffer); + } else { + wc1=*String1->Buffer; + wc2=*String2->Buffer; + }; + + if(wc1!=wc2) { + String1->Buffer-=i; + String2->Buffer-=i; + return wc1-wc2; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return 0; +} + +VOID RtlCopyString(IN OUT PSTRING DestinationString, IN PSTRING SourceString) +{ + unsigned long copylen, i; + + if(SourceString==NULL) { + DestinationString->Length=0; + DestinationString->Buffer=NULL; + } else { + if(SourceString->LengthMaximumLength) { + copylen=SourceString->Length; + } else { + copylen=DestinationString->MaximumLength; + }; + for(i=0; iBuffer)=*(SourceString->Buffer); + DestinationString++; + SourceString++; + }; + *DestinationString->Buffer=0; + DestinationString->Buffer-=copylen; + SourceString->Buffer-=copylen; + }; +} + +VOID RtlCopyUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PUNICODE_STRING SourceString) +{ + unsigned long copylen, i; + WCHAR* src; + WCHAR* dest; + + DPRINT("RtlCopyUnicodeString(Dest %x Source %x)\n",DestinationString, + SourceString); + DPRINT("Dest->Length %d Dest->Buffer %x\n",DestinationString->Length, + DestinationString->Buffer); + if (SourceString!=NULL) + { + DPRINT("Source->Length %d Source->Buffer %x\n",SourceString->Length, + SourceString->Buffer); + } + + if(SourceString==NULL) + { + DestinationString->Length=0; + } + else + { + DestinationString->Length=SourceString->Length; + if(SourceString->LengthMaximumLength) + { + copylen=SourceString->Length; + } + else + { + copylen=DestinationString->MaximumLength; + } + DPRINT("Beginning copy of length %d\n",copylen); + src = SourceString->Buffer; + dest = DestinationString->Buffer; + for(i=0; iBuffer); + *dest=0; + DPRINT("Finished copy %x\n",DestinationString->Buffer); + } +} + +BOOLEAN RtlEqualString(PSTRING String1, PSTRING String2, BOOLEAN CaseInsensitive) +{ + unsigned long s1l=String1->Length; + unsigned long s2l=String2->Length; + unsigned long i; + char c1, c2; + + if(s1l!=s2l) return FALSE; + + for(i=0; iBuffer; + c2=*String2->Buffer; + + if(CaseInsensitive==TRUE) { + c1=toupper(c1); + c2=toupper(c2); + }; + + if(c1!=c2) { + String1->Buffer-=i; + String2->Buffer-=i; + return FALSE; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return TRUE; +} + +BOOLEAN RtlEqualUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, + BOOLEAN CaseInsensitive) +{ + unsigned long s1l=String1->Length; + unsigned long s2l=String2->Length; + unsigned long i; + char wc1, wc2; + + if(s1l!=s2l) return FALSE; + + for(i=0; iBuffer); + wc2=wtoupper(*String2->Buffer); + } else { + wc1=*String1->Buffer; + wc2=*String2->Buffer; + }; + + if(wc1!=wc2) { + String1->Buffer-=i; + String2->Buffer-=i; + return FALSE; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return TRUE; +} + +VOID RtlFreeAnsiString(IN PANSI_STRING AnsiString) +{ + ExFreePool(AnsiString->Buffer); +} + +VOID RtlFreeUnicodeString(IN PUNICODE_STRING UnicodeString) +{ + ExFreePool(UnicodeString->Buffer); +} + +VOID RtlInitAnsiString(IN OUT PANSI_STRING DestinationString, + IN PCSZ SourceString) +{ + unsigned long DestSize; + + if(SourceString==NULL) { + DestinationString->Length=0; + DestinationString->MaximumLength=0; + } else { + DestSize=strlen((const char *)SourceString); + DestinationString->Length=DestSize; + DestinationString->MaximumLength=DestSize+1; + }; + DestinationString->Buffer=(PCHAR)SourceString; +} + +VOID RtlInitString(IN OUT PSTRING DestinationString, + IN PCSZ SourceString) +{ + DestinationString->Length=strlen((char *)SourceString); + DestinationString->MaximumLength=strlen((char *)SourceString)+1; + DestinationString->Buffer=SourceString; +} + +VOID RtlInitUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PCWSTR SourceString) +{ + unsigned long i, DestSize; + UNICODE_STRING Dest=*DestinationString; + + if(SourceString==NULL) { + DestinationString->Length=0; + DestinationString->MaximumLength=0; + DestinationString->Buffer=NULL; + } else { + DestSize=wstrlen((PWSTR)SourceString); + DestinationString->Length=DestSize; + DestinationString->MaximumLength=DestSize+1; + + DestinationString->Buffer=(PWSTR)SourceString; + }; +} + +NTSTATUS RtlIntegerToUnicodeString(IN ULONG Value, IN ULONG Base, /* optional */ + IN OUT PUNICODE_STRING String) +{ + char *str; + unsigned long len, i; + + str=ExAllocatePool(NonPagedPool, 100); + if(Base==16) { + sprintf(str, "%x", Value); + } else + if(Base==8) { + sprintf(str, "%o", Value); + } else + if(Base==2) { + sprintf(str, "%b", Value); + } else { + sprintf(str, "%u", Value); + }; + + len=strlen(str); + if(String->MaximumLengthBuffer=*str; + String->Buffer++; + str++; + }; + *String->Buffer=0; + String->Buffer-=len; + String->Length=len; + str-=len; + ExFreePool(str); + + return STATUS_SUCCESS; +} + +NTSTATUS RtlUnicodeStringToAnsiString(IN OUT PANSI_STRING DestinationString, + IN PUNICODE_STRING SourceString, + IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + WCHAR* dest; + char* src; + + if(AllocateDestinationString==TRUE) + { + DestinationString->Buffer=ExAllocatePool(NonPagedPool, + (SourceString->Length+1)*2); + DestinationString->MaximumLength=SourceString->Length; + } + + DestinationString->Length=SourceString->Length; + + dest = DestinationString->Buffer; + src = SourceString->Buffer; + for(i=0; iLength; i++) + { + *dest=*src; + src++; + dest++; + } + *DestinationString->Buffer=0; + + return STATUS_SUCCESS; +} + +NTSTATUS RtlUnicodeStringToInteger(IN PUNICODE_STRING String, IN ULONG Base, + OUT PULONG Value) +{ + char *str; + unsigned long i, lenmin=0; + BOOLEAN addneg=FALSE; + + str=ExAllocatePool(NonPagedPool, String->Length+1); + + for(i=0; iLength; i++) { + *str=*String->Buffer; + + if(*str=='b') { Base=2; lenmin++; } else + if(*str=='o') { Base=8; lenmin++; } else + if(*str=='d') { Base=10; lenmin++; } else + if(*str=='x') { Base=16; lenmin++; } else + if(*str=='+') { lenmin++; } else + if(*str=='-') { addneg=TRUE; lenmin++; } else + if((*str>'1') && (Base==2)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if(((*str>'7') || (*str<'0')) && (Base==8)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if(((*str>'9') || (*str<'0')) && (Base==10)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if((((*str>'9') || (*str<'0')) || + ((toupper(*str)>'F') || (toupper(*str)<'A'))) && (Base==16)) + { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + str++; + + String->Buffer++; + }; + + *str=0; + String->Buffer-=String->Length; + str-=(String->Length-lenmin); + + if(addneg==TRUE) { + *Value=simple_strtoul(str, NULL, Base)*-1; + } else + *Value=simple_strtoul(str, NULL, Base); + + ExFreePool(str); +} + +NTSTATUS RtlUpcaseUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PUNICODE_STRING SourceString, + IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + + if(AllocateDestinationString==TRUE) { + DestinationString->Buffer=ExAllocatePool(NonPagedPool, SourceString->Length+1); + DestinationString->Length=SourceString->Length; + DestinationString->MaximumLength-SourceString->Length+1; + }; + + for(i=0; iLength; i++) { + *DestinationString->Buffer=wtoupper(*SourceString->Buffer); + DestinationString++; + SourceString++; + }; + *DestinationString->Buffer=0; + + DestinationString->Buffer-=SourceString->Length; + SourceString->Buffer-=SourceString->Length; + + return STATUS_SUCCESS; +} + +VOID RtlUpcaseString(IN OUT PSTRING DestinationString, + IN PSTRING SourceString) +{ + unsigned long i, len; + + if(SourceString->Length>DestinationString->MaximumLength) { + len=DestinationString->MaximumLength; + } else { + len=SourceString->Length; + }; + + for(i=0; iBuffer=toupper(*SourceString->Buffer); + DestinationString++; + SourceString++; + }; + *DestinationString->Buffer=0; + + DestinationString->Buffer-=len; + SourceString->Buffer-=len; +} diff --git a/reactos/ntoskrnl/rtl/unicode.c.new b/reactos/ntoskrnl/rtl/unicode.c.new new file mode 100644 index 00000000000..6135ceeb03d --- /dev/null +++ b/reactos/ntoskrnl/rtl/unicode.c.new @@ -0,0 +1,529 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/rtl/unicode.c + * PURPOSE: String functions + * PROGRAMMER: Jason Filby (jasonfilby@yahoo.com) + * UPDATE HISTORY: + * Created 10/08/98 + * Fixed bugs 21/08/98 + */ + +#include +#include +#include +#include +#include +#include + +#define Aa_Difference 'A'-'a'; + +VOID RtlUpperString(PSTRING DestinationString, PSTRING SourceString) +{ + UNIMPLEMENTED; +} + +WCHAR wtoupper(WCHAR c) +{ + if((c>='a') && (c<='z')) return c+Aa_Difference; + return c; +}; + +unsigned long wstrlen(PWSTR s) +{ + WCHAR c=' '; + unsigned int len=0; + + while(c!=0) { + c=*s; + s++; + len++; + }; + s-=len; + + return len-1; +}; + +ULONG RtlAnsiStringToUnicodeSize(IN PANSI_STRING AnsiString) +{ + return AnsiString->Length*2; +}; + +NTSTATUS RtlAnsiStringToUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PANSI_STRING SourceString, IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + + if(AllocateDestinationString==TRUE) { + DestinationString->Buffer=ExAllocatePool(NonPagedPool, SourceString->Length*2+1); + DestinationString->MaximumLength=SourceString->Length; + }; + + DestinationString->Length=SourceString->Length; + memset(DestinationString->Buffer, 0, SourceString->Length*2); + + for (i=0; iLength; i++) + { + *DestinationString->Buffer=*SourceString->Buffer; + + SourceString->Buffer++; + DestinationString->Buffer++; + }; + *DestinationString->Buffer=0; + + SourceString->Buffer-=SourceString->Length; + DestinationString->Buffer-=SourceString->Length; + + return STATUS_SUCCESS; +}; + +NTSTATUS RtlAppendUnicodeStringToString(IN OUT PUNICODE_STRING Destination, + IN PUNICODE_STRING Source) +{ + unsigned long i; + + if(Destination->MaximumLength-Destination->Length-Source->Length<0) + return STATUS_BUFFER_TOO_SMALL; + + Destination->Buffer+=Destination->Length; + for(i=0; iLength; i++) { + *Destination->Buffer=*Source->Buffer; + Destination->Buffer++; + Source->Buffer++; + }; + *Destination->Buffer=0; + Destination->Buffer-=(Destination->Length+Source->Length); + Source->Buffer-=Source->Length; + + Destination->Length+=Source->Length; + return STATUS_SUCCESS; +}; + +NTSTATUS RtlAppendUnicodeToString(IN OUT PUNICODE_STRING Destination, + IN PWSTR Source) +{ + unsigned long i, slen=wstrlen(Source); + + if(Destination->MaximumLength-Destination->Length-slen<0) + return STATUS_BUFFER_TOO_SMALL; + + Destination->Buffer+=Destination->Length; + for(i=0; iBuffer=*Source; + Destination->Buffer++; + Source++; + }; + *Destination->Buffer=0; + Destination->Buffer-=(Destination->Length+slen); + Source-=slen; + + Destination->Length+=slen; + return STATUS_SUCCESS; +}; + +NTSTATUS RtlCharToInteger(IN PCSZ String, IN ULONG Base, IN OUT PULONG Value) +{ + *Value=simple_strtoul((const char *)String, NULL, Base); +}; + +LONG RtlCompareString(PSTRING String1, PSTRING String2, BOOLEAN CaseInsensitive) +{ + unsigned long i; + char c1, c2; + + if(String1->Length!=String2->Length) return String1->Length-String2->Length; + + for(i=0; iLength; i++) { + if(CaseInsensitive==TRUE) { + c1=toupper(*String1->Buffer); + c2=toupper(*String2->Buffer); + } else { + c1=*String1->Buffer; + c2=*String2->Buffer; + }; + if(c1!=c2) { + String1->Buffer-=i; + String2->Buffer-=i; + return c1-c2; + }; + String1->Buffer++; + String2->Buffer++; + }; + String1->Buffer-=i; + String2->Buffer-=i; + + return 0; +}; + +LONG RtlCompareUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, + BOOLEAN CaseInsensitive) +{ + unsigned long i; + WCHAR wc1, wc2; + + if(String1->Length!=String2->Length) return + String1->Length-String2->Length; + + for(i=0; iLength; i++) { + if(CaseInsensitive==TRUE) { + wc1=wtoupper(*String1->Buffer); + wc2=wtoupper(*String2->Buffer); + } else { + wc1=*String1->Buffer; + wc2=*String2->Buffer; + }; + + if(wc1!=wc2) { + String1->Buffer-=i; + String2->Buffer-=i; + return wc1-wc2; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return 0; +}; + +VOID RtlCopyString(IN OUT PSTRING DestinationString, IN PSTRING SourceString) +{ + unsigned long copylen, i; + + if(SourceString==NULL) { + DestinationString->Length=0; + } else { + if(SourceString->LengthMaximumLength) { + copylen=SourceString->Length; + } else { + copylen=DestinationString->MaximumLength; + }; + for(i=0; iBuffer=*SourceString->Buffer; + DestinationString->Buffer++; + SourceString->Buffer++; + }; + *DestinationString->Buffer=0; + DestinationString->Buffer-=copylen; + SourceString->Buffer-=copylen; + }; +}; + +VOID RtlCopyUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PUNICODE_STRING SourceString) +{ + unsigned long copylen, i; + + if(SourceString==NULL) { + DestinationString->Length=0; + } else { + if(SourceString->LengthMaximumLength) { + copylen=SourceString->Length; + } else { + copylen=DestinationString->MaximumLength; + }; + for(i=0; iBuffer=*SourceString->Buffer; + DestinationString->Buffer++; + SourceString->Buffer++; + }; + *DestinationString->Buffer=0; + DestinationString->Buffer-=copylen; + SourceString->Buffer-=copylen; + }; +}; + +BOOLEAN RtlEqualString(PSTRING String1, PSTRING String2, BOOLEAN CaseInsensitive) +{ + unsigned long s1l=String1->Length; + unsigned long s2l=String2->Length; + unsigned long i; + char c1, c2; + + if(s1l!=s2l) return FALSE; + + for(i=0; iBuffer; + c2=*String2->Buffer; + + if(CaseInsensitive==TRUE) { + c1=toupper(c1); + c2=toupper(c2); + }; + + if(c1!=c2) { + String1->Buffer-=i; + String2->Buffer-=i; + return FALSE; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return TRUE; +}; + +BOOLEAN RtlEqualUnicodeString(PUNICODE_STRING String1, PUNICODE_STRING String2, + BOOLEAN CaseInsensitive) +{ + unsigned long s1l=String1->Length; + unsigned long s2l=String2->Length; + unsigned long i; + char wc1, wc2; + + if(s1l!=s2l) return FALSE; + + for(i=0; iBuffer); + wc2=wtoupper(*String2->Buffer); + } else { + wc1=*String1->Buffer; + wc2=*String2->Buffer; + }; + + if(wc1!=wc2) { + String1->Buffer-=i; + String2->Buffer-=i; + return FALSE; + }; + + String1->Buffer++; + String2->Buffer++; + }; + + String1->Buffer-=i; + String2->Buffer-=i; + + return TRUE; +}; + +VOID RtlFreeAnsiString(IN PANSI_STRING AnsiString) +{ + ExFreePool(AnsiString->Buffer); +}; + +VOID RtlFreeUnicodeString(IN PUNICODE_STRING UnicodeString) +{ + ExFreePool(UnicodeString->Buffer); +}; + +VOID RtlInitAnsiString(IN OUT PANSI_STRING DestinationString, + IN PCSZ SourceString) +{ + unsigned long DestSize; + + if(SourceString==NULL) { + DestinationString->Length=0; + DestinationString->MaximumLength=0; + } else { + DestSize=strlen((const char *)SourceString); + DestinationString->Length=DestSize; + DestinationString->MaximumLength=DestSize+1; + }; + DestinationString->Buffer=(PCHAR)SourceString; +}; + +VOID RtlInitString(IN OUT PSTRING DestinationString, + IN PCSZ SourceString) +{ + DestinationString->Length=strlen((char *)SourceString); + DestinationString->MaximumLength=strlen((char *)SourceString)+1; + DestinationString->Buffer=SourceString; +}; + +VOID RtlInitUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PCWSTR SourceString) +{ + unsigned long i, DestSize; + UNICODE_STRING Dest=*DestinationString; + + if(SourceString==NULL) { + DestinationString->Length=0; + DestinationString->MaximumLength=0; + DestinationString->Buffer=NULL; + } else { + DestSize=wstrlen((PWSTR)SourceString); + DestinationString->Length=DestSize; + DestinationString->MaximumLength=DestSize+1; + + DestinationString->Buffer=(PWSTR)SourceString; + }; +}; + +NTSTATUS RtlIntegerToUnicodeString(IN ULONG Value, IN ULONG Base, /* optional */ + IN OUT PUNICODE_STRING String) +{ + char *str; + unsigned long len, i; + + str=ExAllocatePool(NonPagedPool, 1024); + if(Base==16) { + sprintf(str, "%x", Value); + } else + if(Base==8) { + sprintf(str, "%o", Value); + } else + if(Base==2) { + sprintf(str, "%b", Value); + } else { + sprintf(str, "%u", Value); + }; + + len=strlen(str); + if(String->MaximumLengthBuffer=*str; + String->Buffer++; + str++; + }; + *String->Buffer=0; + String->Buffer-=len; + String->Length=len; + str-=len; + ExFreePool(str); + + return STATUS_SUCCESS; +}; + +NTSTATUS RtlUnicodeStringToAnsiString(IN OUT PANSI_STRING DestinationString, + IN PUNICODE_STRING SourceString, + IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + + if(AllocateDestinationString==TRUE) { + + // Causes excetion 14(0) in _Validate_Free_List + DestinationString->Buffer=ExAllocatePool(NonPagedPool, SourceString->Length+1); + DestinationString->MaximumLength=SourceString->Length+1; + }; + + DestinationString->Length=SourceString->Length; + + for(i=0; iLength; i++) { + *DestinationString->Buffer=*SourceString->Buffer; + DestinationString->Buffer++; + SourceString->Buffer++; + }; + *DestinationString->Buffer=0; + + DestinationString->Buffer-=SourceString->Length; + SourceString->Buffer-=SourceString->Length; + + return STATUS_SUCCESS; +}; + +NTSTATUS RtlUnicodeStringToInteger(IN PUNICODE_STRING String, IN ULONG Base, + OUT PULONG Value) +{ + char *str; + unsigned long i, lenmin=0; + BOOLEAN addneg=FALSE; + + str=ExAllocatePool(NonPagedPool, String->Length+1); + + for(i=0; iLength; i++) { + *str=*String->Buffer; + + if(*str=='b') { Base=2; lenmin++; } else + if(*str=='o') { Base=8; lenmin++; } else + if(*str=='d') { Base=10; lenmin++; } else + if(*str=='x') { Base=16; lenmin++; } else + if(*str=='+') { lenmin++; } else + if(*str=='-') { addneg=TRUE; lenmin++; } else + if((*str>'1') && (Base==2)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if(((*str>'7') || (*str<'0')) && (Base==8)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if(((*str>'9') || (*str<'0')) && (Base==10)) { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + if((((*str>'9') || (*str<'0')) || + ((toupper(*str)>'F') || (toupper(*str)<'A'))) && (Base==16)) + { + String->Buffer-=i; + *Value=0; + return STATUS_INVALID_PARAMETER; + } else + str++; + + String->Buffer++; + }; + + *str=0; + String->Buffer-=String->Length; + str-=(String->Length-lenmin); + + if(addneg==TRUE) { + *Value=simple_strtoul(str, NULL, Base)*-1; + } else + *Value=simple_strtoul(str, NULL, Base); + + ExFreePool(str); +}; + +NTSTATUS RtlUpcaseUnicodeString(IN OUT PUNICODE_STRING DestinationString, + IN PUNICODE_STRING SourceString, + IN BOOLEAN AllocateDestinationString) +{ + unsigned long i; + + if(AllocateDestinationString==TRUE) { + DestinationString->Buffer=ExAllocatePool(NonPagedPool, SourceString->Length*2+1); + DestinationString->Length=SourceString->Length; + DestinationString->MaximumLength=SourceString->Length+1; + }; + + for(i=0; iLength; i++) { + *DestinationString->Buffer=wtoupper(*SourceString->Buffer); + DestinationString->Buffer++; + SourceString->Buffer++; + }; + *DestinationString->Buffer=0; + + DestinationString->Buffer-=SourceString->Length; + SourceString->Buffer-=SourceString->Length; + + return STATUS_SUCCESS; +}; + +VOID RtlUpcaseString(IN OUT PSTRING DestinationString, + IN PSTRING SourceString) +{ + unsigned long i, len; + + if(SourceString->Length>DestinationString->MaximumLength) { + len=DestinationString->MaximumLength; + } else { + len=SourceString->Length; + }; + + for(i=0; iBuffer=toupper(*SourceString->Buffer); + DestinationString->Buffer++; + SourceString->Buffer++; + }; + *DestinationString->Buffer=0; + + DestinationString->Buffer-=len; + SourceString->Buffer-=len; +}; diff --git a/reactos/ntoskrnl/rtl/vsprintf.c b/reactos/ntoskrnl/rtl/vsprintf.c new file mode 100644 index 00000000000..e35f71e3817 --- /dev/null +++ b/reactos/ntoskrnl/rtl/vsprintf.c @@ -0,0 +1,326 @@ +/* + * linux/lib/vsprintf.c + * + * Copyright (C) 1991, 1992 Linus Torvalds + */ + +/* vsprintf.c -- Lars Wirzenius & Linus Torvalds. */ +/* + * Wirzenius wrote this portably, Torvalds fucked it up :-) + */ + +/* + * Appropiated for the reactos kernel, March 1998 -- David Welch + */ + +#include + +#include +#include +#include +#include + +unsigned long simple_strtoul(const char *cp,char **endp,unsigned int base) +{ + unsigned long result = 0,value; + + if (!base) { + base = 10; + if (*cp == '0') { + base = 8; + cp++; + if ((*cp == 'x') && isxdigit(cp[1])) { + cp++; + base = 16; + } + } + } + while (isxdigit(*cp) && (value = isdigit(*cp) ? *cp-'0' : (islower(*cp) + ? toupper(*cp) : *cp)-'A'+10) < base) { + result = result*base + value; + cp++; + } + if (endp) + *endp = (char *)cp; + return result; +} + +/* we use this so that we can do without the ctype library */ +#define is_digit(c) ((c) >= '0' && (c) <= '9') + +static int skip_atoi(const char **s) +{ + int i=0; + + while (is_digit(**s)) + i = i*10 + *((*s)++) - '0'; + return i; +} + +#define ZEROPAD 1 /* pad with zero */ +#define SIGN 2 /* unsigned/signed long */ +#define PLUS 4 /* show plus */ +#define SPACE 8 /* space if plus */ +#define LEFT 16 /* left justified */ +#define SPECIAL 32 /* 0x */ +#define LARGE 64 /* use 'ABCDEF' instead of 'abcdef' */ + +#define do_div(n,base) ({ \ +int __res; \ +__res = ((unsigned long) n) % (unsigned) base; \ +n = ((unsigned long) n) / (unsigned) base; \ +__res; }) + +static char * number(char * str, long num, int base, int size, int precision + ,int type) +{ + char c,sign,tmp[66]; + const char *digits="0123456789abcdefghijklmnopqrstuvwxyz"; + int i; + + if (type & LARGE) + digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"; + if (type & LEFT) + type &= ~ZEROPAD; + if (base < 2 || base > 36) + return 0; + c = (type & ZEROPAD) ? '0' : ' '; + sign = 0; + if (type & SIGN) { + if (num < 0) { + sign = '-'; + num = -num; + size--; + } else if (type & PLUS) { + sign = '+'; + size--; + } else if (type & SPACE) { + sign = ' '; + size--; + } + } + if (type & SPECIAL) { + if (base == 16) + size -= 2; + else if (base == 8) + size--; + } + i = 0; + if (num == 0) + tmp[i++]='0'; + else while (num != 0) + tmp[i++] = digits[do_div(num,base)]; + if (i > precision) + precision = i; + size -= precision; + if (!(type&(ZEROPAD+LEFT))) + while(size-->0) + *str++ = ' '; + if (sign) + *str++ = sign; + if (type & SPECIAL) + if (base==8) + *str++ = '0'; + else if (base==16) { + *str++ = '0'; + *str++ = digits[33]; + } + if (!(type & LEFT)) + while (size-- > 0) + *str++ = c; + while (i < precision--) + *str++ = '0'; + while (i-- > 0) + *str++ = tmp[i]; + while (size-- > 0) + *str++ = ' '; + return str; +} + +int vsprintf(char *buf, const char *fmt, va_list args) +{ + int len; + unsigned long num; + int i, base; + char * str; + const char *s; + const short int* sw; + + int flags; /* flags to number() */ + + int field_width; /* width of output field */ + int precision; /* min. # of digits for integers; max + number of chars for from string */ + int qualifier; /* 'h', 'l', or 'L' for integer fields */ + + for (str=buf ; *fmt ; ++fmt) { + if (*fmt != '%') { + *str++ = *fmt; + continue; + } + + /* process flags */ + flags = 0; + repeat: + ++fmt; /* this also skips first '%' */ + switch (*fmt) { + case '-': flags |= LEFT; goto repeat; + case '+': flags |= PLUS; goto repeat; + case ' ': flags |= SPACE; goto repeat; + case '#': flags |= SPECIAL; goto repeat; + case '0': flags |= ZEROPAD; goto repeat; + } + + /* get field width */ + field_width = -1; + if (is_digit(*fmt)) + field_width = skip_atoi(&fmt); + else if (*fmt == '*') { + ++fmt; + /* it's the next argument */ + field_width = va_arg(args, int); + if (field_width < 0) { + field_width = -field_width; + flags |= LEFT; + } + } + + /* get the precision */ + precision = -1; + if (*fmt == '.') { + ++fmt; + if (is_digit(*fmt)) + precision = skip_atoi(&fmt); + else if (*fmt == '*') { + ++fmt; + /* it's the next argument */ + precision = va_arg(args, int); + } + if (precision < 0) + precision = 0; + } + + /* get the conversion qualifier */ + qualifier = -1; + if (*fmt == 'h' || *fmt == 'l' || *fmt == 'L') { + qualifier = *fmt; + ++fmt; + } + + /* default base */ + base = 10; + + switch (*fmt) { + case 'c': + if (!(flags & LEFT)) + while (--field_width > 0) + *str++ = ' '; + *str++ = (unsigned char) va_arg(args, int); + while (--field_width > 0) + *str++ = ' '; + continue; + + case 'w': + sw = va_arg(args,short int *); +// DPRINT("L %x\n",sw); + while ((*sw)!=0) + { + *str++ = (char)(*sw++); + } + continue; + + case 's': + s = va_arg(args, char *); + if (!s) + s = ""; + + len = strnlen(s, precision); + + if (!(flags & LEFT)) + while (len < field_width--) + *str++ = ' '; + for (i = 0; i < len; ++i) + *str++ = *s++; + while (len < field_width--) + *str++ = ' '; + continue; + + case 'p': + if (field_width == -1) { + field_width = 2*sizeof(void *); + flags |= ZEROPAD; + } + str = number(str, + (unsigned long) va_arg(args, void *), 16, + field_width, precision, flags); + continue; + + + case 'n': + if (qualifier == 'l') { + long * ip = va_arg(args, long *); + *ip = (str - buf); + } else { + int * ip = va_arg(args, int *); + *ip = (str - buf); + } + continue; + + /* integer number formats - set up the flags and "break" */ + case 'o': + base = 8; + break; + + case 'b': + base = 2; + break; + + case 'X': + flags |= LARGE; + case 'x': + base = 16; + break; + + case 'd': + case 'i': + flags |= SIGN; + case 'u': + break; + + default: + if (*fmt != '%') + *str++ = '%'; + if (*fmt) + *str++ = *fmt; + else + --fmt; + continue; + } + if (qualifier == 'l') + num = va_arg(args, unsigned long); + else if (qualifier == 'h') + if (flags & SIGN) + num = va_arg(args, short); + else + num = va_arg(args, unsigned short); + else if (flags & SIGN) + num = va_arg(args, int); + else + num = va_arg(args, unsigned int); + str = number(str, num, base, field_width, precision, flags); + } + *str = '\0'; + return str-buf; +} + +int sprintf(char * buf, const char *fmt, ...) +{ + va_list args; + int i; + + va_start(args, fmt); + i=vsprintf(buf,fmt,args); + va_end(args); + return i; +} + diff --git a/reactos/ntoskrnl/se/semgr.c b/reactos/ntoskrnl/se/semgr.c new file mode 100644 index 00000000000..ae75b4bd926 --- /dev/null +++ b/reactos/ntoskrnl/se/semgr.c @@ -0,0 +1,96 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * PURPOSE: Security manager + * FILE: kernel/se/semgr.c + * PROGRAMER: ? + * REVISION HISTORY: + * 26/07/98: Added stubs for security functions + */ + +/* INCLUDES *****************************************************************/ + +#include + +#include + +#include + +/* FUNCTIONS ***************************************************************/ + +NTSTATUS RtlCreateSecurityDescriptor(PSECURITY_DESCRIPTOR SecurityDescriptor, + ULONG Revision) +{ + UNIMPLEMENTED; +} + +ULONG RtlLengthSecurityDescriptor(PSECURITY_DESCRIPTOR SecurityDescriptor) +{ + UNIMPLEMENTED; +} + +NTSTATUS RtlSetDaclSecurityDescriptor(PSECURITY_DESCRIPTOR SecurityDescriptor, + BOOLEAN DaclPresent, + PACL Dacl, + BOOLEAN DaclDefaulted) +{ + UNIMPLEMENTED; +} + +BOOLEAN RtlValidSecurityDescriptor(PSECURITY_DESCRIPTOR SecurityDescriptor) +{ + UNIMPLEMENTED; +} + +BOOLEAN SeSinglePrivilegeCheck(LUID PrivilegeValue, + KPROCESSOR_MODE PreviousMode) +{ + UNIMPLEMENTED; +} + +NTSTATUS SeDeassignSecurity(PSECURITY_DESCRIPTOR* SecurityDescriptor) +{ + UNIMPLEMENTED; +} + +NTSTATUS SeAssignSecurity(PSECURITY_DESCRIPTOR ParentDescriptor, + PSECURITY_DESCRIPTOR ExplicitDescriptor, + BOOLEAN IsDirectoryObject, + PSECURITY_SUBJECT_CONTEXT SubjectContext, + PGENERIC_MAPPING GenericMapping, + POOL_TYPE PoolType) +{ + UNIMPLEMENTED; +} + +BOOLEAN SeAccessCheck(IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN PSECURITY_DESCRIPTOR_CONTEXT SubjectSecurityContext, + IN BOOLEAN SubjectContextLocked, + IN ACCESS_MASK DesiredAccess, + IN ACCESS_MASK PreviouslyGrantedAccess, + OUT PPRIVILEGE_SET* Privileges, + IN PGENERIC_MAPPING GenericMapping, + IN KPROCESSOR_MODE AccessMode, + OUT PACCESS_MODE GrantedAccess, + OUT PNTSTATUS AccessStatus) +/* + * FUNCTION: Determines whether the requested access rights can be granted + * to an object protected by a security descriptor and an object owner + * ARGUMENTS: + * SecurityDescriptor = Security descriptor protected the object + * SubjectSecurityContext = Subject's captured security context + * SubjectContextLocked = Indicates the user's subject context is locked + * DesiredAccess = Access rights the caller is trying to acquire + * PreviouslyGrantedAccess = Specified the access rights already granted + * Priveleges = ? + * GenericMapping = Generic mapping associated with the object + * AccessMode = Access mode used for the check + * GrantedAccess (OUT) = On return specifies the access granted + * AccessStatus (OUT) = Status indicating why access was denied + * RETURNS: If access was granted, returns TRUE + */ +{ + UNIMPLEMENTED; +} + + diff --git a/reactos/ntoskrnl/tst/test.c b/reactos/ntoskrnl/tst/test.c new file mode 100644 index 00000000000..2f7d8a992fd --- /dev/null +++ b/reactos/ntoskrnl/tst/test.c @@ -0,0 +1,97 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/test/test.c + * PURPOSE: Kernel regression tests + * PROGRAMMER: David Welch (welch@mcmail.com) + * UPDATE HISTORY: + * 28/05/98: Created + */ + +/* INCLUDES *****************************************************************/ + +#include + +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ******************************************************************/ + +static KEVENT event; + +/* FUNCTIONS ****************************************************************/ + +NTSTATUS TstFirstThread(PVOID start) +{ + printk("Beginning Thread A\n"); + for(;;) + { + KeWaitForSingleObject(&event,Executive,KernelMode,FALSE,NULL); + KeClearEvent(&event); + printk("AAA "); + KeSetEvent(&event,IO_NO_INCREMENT,TRUE); + } +} + +NTSTATUS TstSecondThread(PVOID start) +{ + printk("Beginning Thread B\n"); + for(;;) + { + KeSetEvent(&event,IO_NO_INCREMENT,TRUE); + KeWaitForSingleObject(&event,Executive,KernelMode,FALSE,NULL); + KeClearEvent(&event); + printk("BBB "); + } +} + +NTSTATUS TstThreadSupport() +{ + HANDLE th1, th2; + + KeInitializeEvent(&event,SynchronizationEvent,FALSE); + PsCreateSystemThread(&th1,0,NULL,NULL,NULL,TstFirstThread,NULL); + PsCreateSystemThread(&th2,0,NULL,NULL,NULL,TstSecondThread,NULL); + for(;;); +} + +void TstParallelPortWrite() +{ + HANDLE hfile; + + DbgPrint("Opening parallel port\n"); + hfile = CreateFile("\\Device\\Parallel",0,0,0,0,0,0); + if (hfile==NULL) + { + DbgPrint("Failed to open parallel port\n"); + } + WriteFile(hfile,"hello world",strlen("hello world"),NULL,NULL); + } + +void TstKeyboardRead() +{ + KEY_EVENT_RECORD key; + HANDLE hfile; + + hfile = CreateFile("\\Device\\Keyboard",0,0,0,0,0,0); + if (hfile == NULL) + { + printk("Failed to open keyboard\n"); + return; + } + for (;;) + { + ReadFile(hfile,&key,sizeof(KEY_EVENT_RECORD),NULL,NULL); + printk("%c",key.AsciiChar); + for(;;); + } +} + +void TstBegin() +{ + TstKeyboardRead(); +} + diff --git a/reactos/ntoskrnl/utils/export/export b/reactos/ntoskrnl/utils/export/export new file mode 100644 index 0000000000000000000000000000000000000000..d1f0f2e09c82a3e56482922e61790ec6245fac2c GIT binary patch literal 33 ecmb<-^>JflWMqH=CI)5(5Ko|$g~J3$-v9tI7y}Ie literal 0 HcmV?d00001 diff --git a/reactos/ntoskrnl/utils/export/export.c b/reactos/ntoskrnl/utils/export/export.c new file mode 100644 index 00000000000..cc3f5bebb69 --- /dev/null +++ b/reactos/ntoskrnl/utils/export/export.c @@ -0,0 +1,78 @@ +/* + * This program takes a list of export symbols and builds a c source + * file which when linked will contain a symbol table + */ + +#include +#include +#include + +int read_line(char* buf) +{ + char ch; + while ((ch=fgetc(stdin))!='\n'&& !feof(stdin)) + { + *buf=ch; + buf++; + } + *buf=0; + return(1); +} + +int main(int argc, char* argv[]) +{ + char buffer[12000]; + char* sym[4096]; + int i=0,j=0; + char ch; + + if (argc!=1) + { + fprintf(stderr,"Usage: export < export_list > symbol table\n"); + exit(0); + } + + /* + * Output preamble + */ + fprintf(stdout,"/*\n"); + fprintf(stdout," * This file was machine generated by export\n"); + fprintf(stdout," * Don't edit\n"); + fprintf(stdout," *\n"); + fprintf(stdout," *\n"); + fprintf(stdout,"*/\n"); + + fprintf(stdout,"#include \n"); + + while (!feof(stdin)) + { + read_line(buffer); +// printf("reading line %s\n",buffer); + if (buffer[0]!='#' && strlen(buffer) >= 1) + { + sym[i]=strdup(buffer); + i++; + } + + } + fprintf(stdout,"#ifdef __cplusplus\n"); + fprintf(stdout,"extern \"C\" {\n"); + fprintf(stdout,"#endif\n"); + for (j=0;j