From d01f8c3180946240fabd337bd362a1f35a1fc033 Mon Sep 17 00:00:00 2001 From: Rex Jolliff Date: Sat, 16 Jan 1999 02:11:45 +0000 Subject: [PATCH] Boudewjin's massive work on kernel32 and crtdll and a console driver. svn path=/trunk/; revision=168 --- reactos/apps/utils/shell/makefile | 8 +- reactos/apps/utils/shell/shell.c | 454 ++++---- reactos/bootflop.bat | 38 + reactos/drivers/dd/blue/blues.c | 154 +++ reactos/drivers/dd/ide/ide.c | 4 +- reactos/include/conio.h | 111 ++ reactos/include/direct.h | 27 + reactos/include/fcntl.h | 164 +++ reactos/include/internal/ntoskrnl.h | 11 + reactos/include/io.h | 94 ++ reactos/include/kernel32/heap.h | 4 +- reactos/include/process.h | 52 + reactos/include/share.h | 17 + reactos/include/stdio.h | 157 +++ reactos/include/stdlib.h | 131 +++ reactos/include/string.h | 8 + reactos/include/time.h | 104 ++ reactos/include/wchar.h | 81 ++ reactos/include/wstring.h | 55 +- reactos/lib/crtdll/conio/cputs.c | 21 + reactos/lib/crtdll/conio/getch.c | 42 + reactos/lib/crtdll/conio/getche.c | 33 + reactos/lib/crtdll/conio/putch.c | 21 + reactos/lib/crtdll/conio/ungetch.c | 28 + reactos/lib/crtdll/ctype/MAKEFILE | 23 + reactos/lib/crtdll/ctype/atof.c | 18 + reactos/lib/crtdll/ctype/atoi.c | 19 + reactos/lib/crtdll/ctype/atol.c | 20 + reactos/lib/crtdll/ctype/atold.c | 19 + reactos/lib/crtdll/ctype/ct_flags.c | 264 +++++ reactos/lib/crtdll/ctype/ct_lower.c | 39 + reactos/lib/crtdll/ctype/ct_upper.c | 39 + reactos/lib/crtdll/ctype/isalnum.c | 16 + reactos/lib/crtdll/ctype/isalpha.c | 17 + reactos/lib/crtdll/ctype/isascii.c | 30 + reactos/lib/crtdll/ctype/iscntrl.c | 8 + reactos/lib/crtdll/ctype/iscsym.c | 40 + reactos/lib/crtdll/ctype/isctype.c | 290 +++++ reactos/lib/crtdll/ctype/isdigit.c | 8 + reactos/lib/crtdll/ctype/isgraph.c | 8 + reactos/lib/crtdll/ctype/islower.c | 8 + reactos/lib/crtdll/ctype/isprint.c | 8 + reactos/lib/crtdll/ctype/ispunct.c | 8 + reactos/lib/crtdll/ctype/isspace.c | 8 + reactos/lib/crtdll/ctype/isupper.c | 8 + reactos/lib/crtdll/ctype/isxdigit.c | 8 + reactos/lib/crtdll/ctype/toascii.c | 14 + reactos/lib/crtdll/ctype/tolower.c | 7 + reactos/lib/crtdll/ctype/toupper.c | 8 + reactos/lib/crtdll/direct/chdir.c | 25 + reactos/lib/crtdll/direct/chdrive.c | 25 + reactos/lib/crtdll/direct/getcwd.c | 33 + reactos/lib/crtdll/direct/getdfree.c | 19 + reactos/lib/crtdll/direct/getdrive.c | 18 + reactos/lib/crtdll/direct/mkdir.c | 14 + reactos/lib/crtdll/direct/rmdir.c | 15 + reactos/lib/crtdll/dirent/dirent.c | 316 ++++++ reactos/lib/crtdll/float/fpreset.c | 7 + reactos/lib/crtdll/io/access.c | 33 + reactos/lib/crtdll/io/close.c | 16 + reactos/lib/crtdll/io/create.c | 8 + reactos/lib/crtdll/io/dup.c | 13 + reactos/lib/crtdll/io/dup2.c | 14 + reactos/lib/crtdll/io/find.c | 253 +++++ reactos/lib/crtdll/io/fmode.c | 8 + reactos/lib/crtdll/io/isatty.c | 8 + reactos/lib/crtdll/io/lseek.c | 17 + reactos/lib/crtdll/io/mktemp.c | 74 ++ reactos/lib/crtdll/io/open.c | 254 +++++ reactos/lib/crtdll/io/read.c | 26 + reactos/lib/crtdll/io/setmode.c | 24 + reactos/lib/crtdll/io/unlink.c | 23 + reactos/lib/crtdll/io/write.c | 27 + reactos/lib/crtdll/libc/atexit.h | 33 + reactos/lib/crtdll/libc/file.h | 64 ++ reactos/lib/crtdll/makefile | 67 +- reactos/lib/crtdll/math/ftol.c | 3 + reactos/lib/crtdll/misc/CRT_noglob.c | 18 + reactos/lib/crtdll/misc/CRTfmode.c | 21 + reactos/lib/crtdll/misc/CRTglob.c | 19 + reactos/lib/crtdll/misc/CRTinit.c | 33 + reactos/lib/crtdll/misc/GetArgs.c | 86 ++ reactos/lib/crtdll/misc/crt1.c | 166 +++ reactos/lib/crtdll/misc/dllcrt1.c | 105 ++ reactos/lib/crtdll/misc/dllmain.c | 32 + reactos/lib/crtdll/misc/gccmain.c | 85 ++ reactos/lib/crtdll/misc/init.c | 75 ++ reactos/lib/crtdll/misc/main.c | 95 ++ reactos/lib/crtdll/misc/sleep.c | 7 + reactos/lib/crtdll/misc/unwind.c | 10 + reactos/lib/crtdll/process/Cwait.c | 20 + reactos/lib/crtdll/process/System.c | 16 + reactos/lib/crtdll/process/execl.c | 10 + reactos/lib/crtdll/process/execle.c | 17 + reactos/lib/crtdll/process/execlp.c | 11 + reactos/lib/crtdll/process/execlpe.c | 17 + reactos/lib/crtdll/process/execv.c | 11 + reactos/lib/crtdll/process/execve.c | 9 + reactos/lib/crtdll/process/execvp.c | 11 + reactos/lib/crtdll/process/execvpe.c | 15 + reactos/lib/crtdll/process/spawnl.c | 10 + reactos/lib/crtdll/process/spawnle.c | 16 + reactos/lib/crtdll/process/spawnlp.c | 10 + reactos/lib/crtdll/process/spawnlpe.c | 15 + reactos/lib/crtdll/process/spawnv.c | 10 + reactos/lib/crtdll/process/spawnve.c | 42 + reactos/lib/crtdll/process/spawnvp.c | 10 + reactos/lib/crtdll/process/spawnvpe.c | 23 + reactos/lib/crtdll/stdio/allocfil.c | 94 ++ reactos/lib/crtdll/stdio/clearerr.c | 10 + reactos/lib/crtdll/stdio/doprnt.c | 319 ++++++ reactos/lib/crtdll/stdio/doscan.c | 404 +++++++ reactos/lib/crtdll/stdio/fclose.c | 45 + reactos/lib/crtdll/stdio/fdopen.c | 55 + reactos/lib/crtdll/stdio/feof.c | 10 + reactos/lib/crtdll/stdio/ferror.c | 10 + reactos/lib/crtdll/stdio/fflush.c | 56 + reactos/lib/crtdll/stdio/fgetc.c | 9 + reactos/lib/crtdll/stdio/fgetpos.c | 15 + reactos/lib/crtdll/stdio/fgets.c | 22 + reactos/lib/crtdll/stdio/filbuf.c | 110 ++ reactos/lib/crtdll/stdio/flsbuf.c | 100 ++ reactos/lib/crtdll/stdio/fopen.c | 78 ++ reactos/lib/crtdll/stdio/fprintf.c | 26 + reactos/lib/crtdll/stdio/fputc.c | 9 + reactos/lib/crtdll/stdio/fputs.c | 42 + reactos/lib/crtdll/stdio/fread.c | 89 ++ reactos/lib/crtdll/stdio/freopen.c | 68 ++ reactos/lib/crtdll/stdio/frlist.c | 11 + reactos/lib/crtdll/stdio/fscanf.c | 15 + reactos/lib/crtdll/stdio/fseek.c | 57 + reactos/lib/crtdll/stdio/fsetpos.c | 15 + reactos/lib/crtdll/stdio/ftell.c | 35 + reactos/lib/crtdll/stdio/fwalk.c | 25 + reactos/lib/crtdll/stdio/fwrite.c | 88 ++ reactos/lib/crtdll/stdio/getc.c | 16 + reactos/lib/crtdll/stdio/getchar.c | 10 + reactos/lib/crtdll/stdio/getenv.c | 16 + reactos/lib/crtdll/stdio/gets.c | 17 + reactos/lib/crtdll/stdio/getw.c | 18 + reactos/lib/crtdll/stdio/perror.c | 13 + reactos/lib/crtdll/stdio/printf.c | 19 + reactos/lib/crtdll/stdio/putc.c | 28 + reactos/lib/crtdll/stdio/putchar.c | 22 + reactos/lib/crtdll/stdio/puts.c | 21 + reactos/lib/crtdll/stdio/putw.c | 15 + reactos/lib/crtdll/stdio/remove.c | 9 + reactos/lib/crtdll/stdio/rename.c | 18 + reactos/lib/crtdll/stdio/rewind.c | 17 + reactos/lib/crtdll/stdio/scanf.c | 15 + reactos/lib/crtdll/stdio/setbuf.c | 13 + reactos/lib/crtdll/stdio/setbuffe.c | 12 + reactos/lib/crtdll/stdio/setlineb.c | 7 + reactos/lib/crtdll/stdio/setvbuf.c | 55 + reactos/lib/crtdll/stdio/sprintf.c | 19 + reactos/lib/crtdll/stdio/sscanf.c | 26 + reactos/lib/crtdll/stdio/stdhnd.c | 39 + reactos/lib/crtdll/stdio/stdiohk.c | 19 + reactos/lib/crtdll/stdio/tempnam.c | 17 + reactos/lib/crtdll/stdio/tmpfile.c | 68 ++ reactos/lib/crtdll/stdio/tmpnam.c | 24 + reactos/lib/crtdll/stdio/ungetc.c | 32 + reactos/lib/crtdll/stdio/vfprintf.c | 27 + reactos/lib/crtdll/stdio/vprintf.c | 13 + reactos/lib/crtdll/stdio/vsprintf.c | 349 +----- reactos/lib/crtdll/stdlib/Exit.c | 48 + reactos/lib/crtdll/stdlib/abort.c | 12 + reactos/lib/crtdll/stdlib/abs.c | 8 + reactos/lib/crtdll/stdlib/atexit.c | 18 + reactos/lib/crtdll/stdlib/atof.c | 8 + reactos/lib/crtdll/stdlib/atoi.c | 8 + reactos/lib/crtdll/stdlib/atol.c | 8 + reactos/lib/crtdll/stdlib/atold.c | 8 + reactos/lib/crtdll/stdlib/bsearch.c | 26 + reactos/lib/crtdll/stdlib/calloc.c | 12 + reactos/lib/crtdll/stdlib/div.c | 24 + reactos/lib/crtdll/stdlib/errno.c | 13 + reactos/lib/crtdll/stdlib/fullpath.c | 32 + reactos/lib/crtdll/stdlib/labs.c | 8 + reactos/lib/crtdll/stdlib/ldiv.c | 25 + reactos/lib/crtdll/stdlib/llabs.c | 9 + reactos/lib/crtdll/stdlib/lldiv.c | 26 + reactos/lib/crtdll/stdlib/makepath.c | 30 + reactos/lib/crtdll/stdlib/malloc.c | 45 +- reactos/lib/crtdll/stdlib/putenv.c | 30 + reactos/lib/crtdll/stdlib/qsort.c | 238 ++++ reactos/lib/crtdll/stdlib/rand.c | 17 + reactos/lib/crtdll/stdlib/senv.c | 28 + reactos/lib/crtdll/stdlib/splitp.c | 42 + reactos/lib/crtdll/stdlib/strtod.c | 97 ++ reactos/lib/crtdll/stdlib/strtol.c | 91 ++ reactos/lib/crtdll/stdlib/strtold.c | 124 ++ reactos/lib/crtdll/stdlib/strtoll.c | 84 ++ reactos/lib/crtdll/stdlib/strtoul.c | 75 ++ reactos/lib/crtdll/stdlib/strtoull.c | 76 ++ reactos/lib/crtdll/string/memchr.c | 5 +- reactos/lib/crtdll/string/memcpy.c | 19 + reactos/lib/crtdll/string/memmove.c | 20 + reactos/lib/crtdll/string/memset.c | 11 + reactos/lib/crtdll/string/str_old.c | 48 + reactos/lib/crtdll/string/strchr.c | 13 +- reactos/lib/crtdll/string/strcpy.c | 3 +- reactos/lib/crtdll/string/strdup.c | 2 +- reactos/lib/crtdll/string/strerror.c | 102 ++ reactos/lib/crtdll/string/stricmp.c | 16 + reactos/lib/crtdll/string/strlwr.c | 23 + reactos/lib/crtdll/string/strncmp.c | 1 + reactos/lib/crtdll/string/strnicmp.c | 18 + reactos/lib/crtdll/string/strnlen.c | 14 + reactos/lib/crtdll/string/strpbrk.c | 4 +- reactos/lib/crtdll/string/strrchr.c | 4 +- reactos/lib/crtdll/string/strstr.c | 4 +- reactos/lib/crtdll/string/strtoul.c | 27 + reactos/lib/crtdll/string/strupr.c | 24 + reactos/lib/crtdll/string/strxfrm.c | 5 +- reactos/lib/crtdll/sys_stat/fstat.c | 32 + reactos/lib/crtdll/sys_stat/stat.c | 22 + reactos/lib/crtdll/time/ctime.c | 1433 ++++++++++++++++++++++++ reactos/lib/crtdll/time/difftime.c | 8 + reactos/lib/crtdll/time/posixrul.h | 49 + reactos/lib/crtdll/time/strftime.c | 243 ++++ reactos/lib/crtdll/time/time.c | 30 + reactos/lib/crtdll/time/tzfile.h | 160 +++ reactos/lib/crtdll/wchar/wcscat.c | 19 + reactos/lib/crtdll/wchar/wcschr.c | 16 + reactos/lib/crtdll/wchar/wcscmp.c | 16 + reactos/lib/crtdll/wchar/wcscoll.c | 17 + reactos/lib/crtdll/wchar/wcscpy.c | 11 + reactos/lib/crtdll/wchar/wcscspn.c | 20 + reactos/lib/crtdll/wchar/wcsdup.c | 15 + reactos/lib/crtdll/wchar/wcsicmp.c | 16 + reactos/lib/crtdll/wchar/wcslen.c | 19 + reactos/lib/crtdll/wchar/wcslwr.c | 22 + reactos/lib/crtdll/wchar/wcsncat.c | 20 + reactos/lib/crtdll/wchar/wcsncmp.c | 16 + reactos/lib/crtdll/wchar/wcsncpy.c | 21 + reactos/lib/crtdll/wchar/wcsnicmp.c | 15 + reactos/lib/crtdll/wchar/wcsnlen.c | 10 + reactos/lib/crtdll/wchar/wcsrchr.c | 14 + reactos/lib/crtdll/wchar/wcsrev.c | 16 + reactos/lib/crtdll/wchar/wcsspn.c | 18 + reactos/lib/crtdll/wchar/wcsstr.c | 21 + reactos/lib/crtdll/wchar/wcstok.c | 52 + reactos/lib/crtdll/wchar/wcstol.c | 25 + reactos/lib/crtdll/wchar/wcstombs.c | 6 + reactos/lib/crtdll/wchar/wcsupr.c | 10 + reactos/lib/kernel32/file/create.c | 130 ++- reactos/lib/kernel32/file/curdir.c | 24 +- reactos/lib/kernel32/file/dir.c | 216 +++- reactos/lib/kernel32/file/file.c | 155 ++- reactos/lib/kernel32/file/find.c | 721 +++++++----- reactos/lib/kernel32/file/volume.c | 40 + reactos/lib/kernel32/makefile | 11 +- reactos/lib/kernel32/mem/heap.c | 104 +- reactos/lib/kernel32/mem/utils.c | 4 +- reactos/lib/kernel32/misc/atom.c | 13 +- reactos/lib/kernel32/misc/console.c | 168 +++ reactos/lib/kernel32/misc/dllmain.c | 19 +- reactos/lib/kernel32/misc/env.c | 278 ++++- reactos/lib/kernel32/misc/error.c | 1 + reactos/lib/kernel32/process/proc.c | 696 ++++++------ reactos/lib/kernel32/thread/thread.c | 734 ++++++------ reactos/lib/ntdll/string/wstring.c | 2 +- reactos/makedisk.bat | 11 + reactos/makefile.dos | 6 +- reactos/makefile_rex | 11 +- reactos/ntoskrnl/exports.lst | 5 + reactos/ntoskrnl/hal/x86/printk.c | 33 +- reactos/ntoskrnl/io/create.c | 2 + reactos/ntoskrnl/io/fs.c | 93 +- reactos/ntoskrnl/io/symlink.c | 11 +- reactos/ntoskrnl/ke/main.c | 185 +-- reactos/ntoskrnl/ldr/loader.c | 35 +- reactos/ntoskrnl/mm/virtual.c | 1493 +++++++++++++------------ reactos/ntoskrnl/ob/namespc.c | 1109 +++++++++--------- reactos/ntoskrnl/ob/object.c | 776 ++++++------- reactos/ntoskrnl/ps/process.c | 625 +++++------ reactos/ntoskrnl/rtl/wstring.c | 6 +- reactos/ntoskrnl/tst/test.c | 27 - 279 files changed, 15679 insertions(+), 4097 deletions(-) create mode 100644 reactos/bootflop.bat create mode 100644 reactos/drivers/dd/blue/blues.c create mode 100644 reactos/include/conio.h create mode 100644 reactos/include/direct.h create mode 100644 reactos/include/fcntl.h create mode 100644 reactos/include/io.h create mode 100644 reactos/include/process.h create mode 100644 reactos/include/share.h create mode 100644 reactos/include/stdio.h create mode 100644 reactos/include/stdlib.h create mode 100644 reactos/include/time.h create mode 100644 reactos/include/wchar.h create mode 100644 reactos/lib/crtdll/conio/cputs.c create mode 100644 reactos/lib/crtdll/conio/getch.c create mode 100644 reactos/lib/crtdll/conio/getche.c create mode 100644 reactos/lib/crtdll/conio/putch.c create mode 100644 reactos/lib/crtdll/conio/ungetch.c create mode 100644 reactos/lib/crtdll/ctype/MAKEFILE create mode 100644 reactos/lib/crtdll/ctype/atof.c create mode 100644 reactos/lib/crtdll/ctype/atoi.c create mode 100644 reactos/lib/crtdll/ctype/atol.c create mode 100644 reactos/lib/crtdll/ctype/atold.c create mode 100644 reactos/lib/crtdll/ctype/ct_flags.c create mode 100644 reactos/lib/crtdll/ctype/ct_lower.c create mode 100644 reactos/lib/crtdll/ctype/ct_upper.c create mode 100644 reactos/lib/crtdll/ctype/isalnum.c create mode 100644 reactos/lib/crtdll/ctype/isalpha.c create mode 100644 reactos/lib/crtdll/ctype/isascii.c create mode 100644 reactos/lib/crtdll/ctype/iscntrl.c create mode 100644 reactos/lib/crtdll/ctype/iscsym.c create mode 100644 reactos/lib/crtdll/ctype/isctype.c create mode 100644 reactos/lib/crtdll/ctype/isdigit.c create mode 100644 reactos/lib/crtdll/ctype/isgraph.c create mode 100644 reactos/lib/crtdll/ctype/islower.c create mode 100644 reactos/lib/crtdll/ctype/isprint.c create mode 100644 reactos/lib/crtdll/ctype/ispunct.c create mode 100644 reactos/lib/crtdll/ctype/isspace.c create mode 100644 reactos/lib/crtdll/ctype/isupper.c create mode 100644 reactos/lib/crtdll/ctype/isxdigit.c create mode 100644 reactos/lib/crtdll/ctype/toascii.c create mode 100644 reactos/lib/crtdll/ctype/tolower.c create mode 100644 reactos/lib/crtdll/ctype/toupper.c create mode 100644 reactos/lib/crtdll/direct/chdir.c create mode 100644 reactos/lib/crtdll/direct/chdrive.c create mode 100644 reactos/lib/crtdll/direct/getcwd.c create mode 100644 reactos/lib/crtdll/direct/getdfree.c create mode 100644 reactos/lib/crtdll/direct/getdrive.c create mode 100644 reactos/lib/crtdll/direct/mkdir.c create mode 100644 reactos/lib/crtdll/direct/rmdir.c create mode 100644 reactos/lib/crtdll/dirent/dirent.c create mode 100644 reactos/lib/crtdll/float/fpreset.c create mode 100644 reactos/lib/crtdll/io/access.c create mode 100644 reactos/lib/crtdll/io/close.c create mode 100644 reactos/lib/crtdll/io/create.c create mode 100644 reactos/lib/crtdll/io/dup.c create mode 100644 reactos/lib/crtdll/io/dup2.c create mode 100644 reactos/lib/crtdll/io/find.c create mode 100644 reactos/lib/crtdll/io/fmode.c create mode 100644 reactos/lib/crtdll/io/isatty.c create mode 100644 reactos/lib/crtdll/io/lseek.c create mode 100644 reactos/lib/crtdll/io/mktemp.c create mode 100644 reactos/lib/crtdll/io/open.c create mode 100644 reactos/lib/crtdll/io/read.c create mode 100644 reactos/lib/crtdll/io/setmode.c create mode 100644 reactos/lib/crtdll/io/unlink.c create mode 100644 reactos/lib/crtdll/io/write.c create mode 100644 reactos/lib/crtdll/libc/atexit.h create mode 100644 reactos/lib/crtdll/libc/file.h create mode 100644 reactos/lib/crtdll/math/ftol.c create mode 100644 reactos/lib/crtdll/misc/CRT_noglob.c create mode 100644 reactos/lib/crtdll/misc/CRTfmode.c create mode 100644 reactos/lib/crtdll/misc/CRTglob.c create mode 100644 reactos/lib/crtdll/misc/CRTinit.c create mode 100644 reactos/lib/crtdll/misc/GetArgs.c create mode 100644 reactos/lib/crtdll/misc/crt1.c create mode 100644 reactos/lib/crtdll/misc/dllcrt1.c create mode 100644 reactos/lib/crtdll/misc/dllmain.c create mode 100644 reactos/lib/crtdll/misc/gccmain.c create mode 100644 reactos/lib/crtdll/misc/init.c create mode 100644 reactos/lib/crtdll/misc/main.c create mode 100644 reactos/lib/crtdll/misc/sleep.c create mode 100644 reactos/lib/crtdll/misc/unwind.c create mode 100644 reactos/lib/crtdll/process/Cwait.c create mode 100644 reactos/lib/crtdll/process/System.c create mode 100644 reactos/lib/crtdll/process/execl.c create mode 100644 reactos/lib/crtdll/process/execle.c create mode 100644 reactos/lib/crtdll/process/execlp.c create mode 100644 reactos/lib/crtdll/process/execlpe.c create mode 100644 reactos/lib/crtdll/process/execv.c create mode 100644 reactos/lib/crtdll/process/execve.c create mode 100644 reactos/lib/crtdll/process/execvp.c create mode 100644 reactos/lib/crtdll/process/execvpe.c create mode 100644 reactos/lib/crtdll/process/spawnl.c create mode 100644 reactos/lib/crtdll/process/spawnle.c create mode 100644 reactos/lib/crtdll/process/spawnlp.c create mode 100644 reactos/lib/crtdll/process/spawnlpe.c create mode 100644 reactos/lib/crtdll/process/spawnv.c create mode 100644 reactos/lib/crtdll/process/spawnve.c create mode 100644 reactos/lib/crtdll/process/spawnvp.c create mode 100644 reactos/lib/crtdll/process/spawnvpe.c create mode 100644 reactos/lib/crtdll/stdio/allocfil.c create mode 100644 reactos/lib/crtdll/stdio/clearerr.c create mode 100644 reactos/lib/crtdll/stdio/doprnt.c create mode 100644 reactos/lib/crtdll/stdio/doscan.c create mode 100644 reactos/lib/crtdll/stdio/fclose.c create mode 100644 reactos/lib/crtdll/stdio/fdopen.c create mode 100644 reactos/lib/crtdll/stdio/feof.c create mode 100644 reactos/lib/crtdll/stdio/ferror.c create mode 100644 reactos/lib/crtdll/stdio/fflush.c create mode 100644 reactos/lib/crtdll/stdio/fgetc.c create mode 100644 reactos/lib/crtdll/stdio/fgetpos.c create mode 100644 reactos/lib/crtdll/stdio/fgets.c create mode 100644 reactos/lib/crtdll/stdio/filbuf.c create mode 100644 reactos/lib/crtdll/stdio/flsbuf.c create mode 100644 reactos/lib/crtdll/stdio/fopen.c create mode 100644 reactos/lib/crtdll/stdio/fprintf.c create mode 100644 reactos/lib/crtdll/stdio/fputc.c create mode 100644 reactos/lib/crtdll/stdio/fputs.c create mode 100644 reactos/lib/crtdll/stdio/fread.c create mode 100644 reactos/lib/crtdll/stdio/freopen.c create mode 100644 reactos/lib/crtdll/stdio/frlist.c create mode 100644 reactos/lib/crtdll/stdio/fscanf.c create mode 100644 reactos/lib/crtdll/stdio/fseek.c create mode 100644 reactos/lib/crtdll/stdio/fsetpos.c create mode 100644 reactos/lib/crtdll/stdio/ftell.c create mode 100644 reactos/lib/crtdll/stdio/fwalk.c create mode 100644 reactos/lib/crtdll/stdio/fwrite.c create mode 100644 reactos/lib/crtdll/stdio/getc.c create mode 100644 reactos/lib/crtdll/stdio/getchar.c create mode 100644 reactos/lib/crtdll/stdio/getenv.c create mode 100644 reactos/lib/crtdll/stdio/gets.c create mode 100644 reactos/lib/crtdll/stdio/getw.c create mode 100644 reactos/lib/crtdll/stdio/perror.c create mode 100644 reactos/lib/crtdll/stdio/printf.c create mode 100644 reactos/lib/crtdll/stdio/putc.c create mode 100644 reactos/lib/crtdll/stdio/putchar.c create mode 100644 reactos/lib/crtdll/stdio/puts.c create mode 100644 reactos/lib/crtdll/stdio/putw.c create mode 100644 reactos/lib/crtdll/stdio/remove.c create mode 100644 reactos/lib/crtdll/stdio/rename.c create mode 100644 reactos/lib/crtdll/stdio/rewind.c create mode 100644 reactos/lib/crtdll/stdio/scanf.c create mode 100644 reactos/lib/crtdll/stdio/setbuf.c create mode 100644 reactos/lib/crtdll/stdio/setbuffe.c create mode 100644 reactos/lib/crtdll/stdio/setlineb.c create mode 100644 reactos/lib/crtdll/stdio/setvbuf.c create mode 100644 reactos/lib/crtdll/stdio/sprintf.c create mode 100644 reactos/lib/crtdll/stdio/sscanf.c create mode 100644 reactos/lib/crtdll/stdio/stdhnd.c create mode 100644 reactos/lib/crtdll/stdio/stdiohk.c create mode 100644 reactos/lib/crtdll/stdio/tempnam.c create mode 100644 reactos/lib/crtdll/stdio/tmpfile.c create mode 100644 reactos/lib/crtdll/stdio/tmpnam.c create mode 100644 reactos/lib/crtdll/stdio/ungetc.c create mode 100644 reactos/lib/crtdll/stdio/vfprintf.c create mode 100644 reactos/lib/crtdll/stdio/vprintf.c create mode 100644 reactos/lib/crtdll/stdlib/Exit.c create mode 100644 reactos/lib/crtdll/stdlib/abort.c create mode 100644 reactos/lib/crtdll/stdlib/abs.c create mode 100644 reactos/lib/crtdll/stdlib/atexit.c create mode 100644 reactos/lib/crtdll/stdlib/atof.c create mode 100644 reactos/lib/crtdll/stdlib/atoi.c create mode 100644 reactos/lib/crtdll/stdlib/atol.c create mode 100644 reactos/lib/crtdll/stdlib/atold.c create mode 100644 reactos/lib/crtdll/stdlib/bsearch.c create mode 100644 reactos/lib/crtdll/stdlib/calloc.c create mode 100644 reactos/lib/crtdll/stdlib/div.c create mode 100644 reactos/lib/crtdll/stdlib/errno.c create mode 100644 reactos/lib/crtdll/stdlib/fullpath.c create mode 100644 reactos/lib/crtdll/stdlib/labs.c create mode 100644 reactos/lib/crtdll/stdlib/ldiv.c create mode 100644 reactos/lib/crtdll/stdlib/llabs.c create mode 100644 reactos/lib/crtdll/stdlib/lldiv.c create mode 100644 reactos/lib/crtdll/stdlib/makepath.c create mode 100644 reactos/lib/crtdll/stdlib/putenv.c create mode 100644 reactos/lib/crtdll/stdlib/qsort.c create mode 100644 reactos/lib/crtdll/stdlib/rand.c create mode 100644 reactos/lib/crtdll/stdlib/senv.c create mode 100644 reactos/lib/crtdll/stdlib/splitp.c create mode 100644 reactos/lib/crtdll/stdlib/strtod.c create mode 100644 reactos/lib/crtdll/stdlib/strtol.c create mode 100644 reactos/lib/crtdll/stdlib/strtold.c create mode 100644 reactos/lib/crtdll/stdlib/strtoll.c create mode 100644 reactos/lib/crtdll/stdlib/strtoul.c create mode 100644 reactos/lib/crtdll/stdlib/strtoull.c create mode 100644 reactos/lib/crtdll/string/memcpy.c create mode 100644 reactos/lib/crtdll/string/memmove.c create mode 100644 reactos/lib/crtdll/string/memset.c create mode 100644 reactos/lib/crtdll/string/str_old.c create mode 100644 reactos/lib/crtdll/string/strerror.c create mode 100644 reactos/lib/crtdll/string/stricmp.c create mode 100644 reactos/lib/crtdll/string/strlwr.c create mode 100644 reactos/lib/crtdll/string/strnicmp.c create mode 100644 reactos/lib/crtdll/string/strnlen.c create mode 100644 reactos/lib/crtdll/string/strtoul.c create mode 100644 reactos/lib/crtdll/string/strupr.c create mode 100644 reactos/lib/crtdll/sys_stat/fstat.c create mode 100644 reactos/lib/crtdll/sys_stat/stat.c create mode 100644 reactos/lib/crtdll/time/ctime.c create mode 100644 reactos/lib/crtdll/time/difftime.c create mode 100644 reactos/lib/crtdll/time/posixrul.h create mode 100644 reactos/lib/crtdll/time/strftime.c create mode 100644 reactos/lib/crtdll/time/time.c create mode 100644 reactos/lib/crtdll/time/tzfile.h create mode 100644 reactos/lib/crtdll/wchar/wcscat.c create mode 100644 reactos/lib/crtdll/wchar/wcschr.c create mode 100644 reactos/lib/crtdll/wchar/wcscmp.c create mode 100644 reactos/lib/crtdll/wchar/wcscoll.c create mode 100644 reactos/lib/crtdll/wchar/wcscpy.c create mode 100644 reactos/lib/crtdll/wchar/wcscspn.c create mode 100644 reactos/lib/crtdll/wchar/wcsdup.c create mode 100644 reactos/lib/crtdll/wchar/wcsicmp.c create mode 100644 reactos/lib/crtdll/wchar/wcslen.c create mode 100644 reactos/lib/crtdll/wchar/wcslwr.c create mode 100644 reactos/lib/crtdll/wchar/wcsncat.c create mode 100644 reactos/lib/crtdll/wchar/wcsncmp.c create mode 100644 reactos/lib/crtdll/wchar/wcsncpy.c create mode 100644 reactos/lib/crtdll/wchar/wcsnicmp.c create mode 100644 reactos/lib/crtdll/wchar/wcsnlen.c create mode 100644 reactos/lib/crtdll/wchar/wcsrchr.c create mode 100644 reactos/lib/crtdll/wchar/wcsrev.c create mode 100644 reactos/lib/crtdll/wchar/wcsspn.c create mode 100644 reactos/lib/crtdll/wchar/wcsstr.c create mode 100644 reactos/lib/crtdll/wchar/wcstok.c create mode 100644 reactos/lib/crtdll/wchar/wcstol.c create mode 100644 reactos/lib/crtdll/wchar/wcstombs.c create mode 100644 reactos/lib/crtdll/wchar/wcsupr.c create mode 100644 reactos/lib/kernel32/misc/console.c create mode 100644 reactos/makedisk.bat diff --git a/reactos/apps/utils/shell/makefile b/reactos/apps/utils/shell/makefile index eed5a5394a6..7f71c38c932 100644 --- a/reactos/apps/utils/shell/makefile +++ b/reactos/apps/utils/shell/makefile @@ -1,9 +1,11 @@ all: shell.bin -OBJECTS = ../common/crt0.o shell.o +OBJECTS= ../common/crt0.o shell.o +LIBS= ../../lib/kernel32/kernel32.a ../../lib/ntdll/ntdll.a -shell.bin: $(OBJECTS) - $(LD) -Ttext 0x10000 $(OBJECTS) ../../lib/kernel32/kernel32.a ../../lib/ntdll/ntdll.a -o shell.exe +shell.bin: $(OBJECTS) $(LIBS) + $(LD) -Ttext 0x10000 $(OBJECTS) $(LIBS) -o shell.exe + $(NM) --numeric-sort shell.exe > shell.sym $(OBJCOPY) -O binary shell.exe shell.bin include ../../rules.mak diff --git a/reactos/apps/utils/shell/shell.c b/reactos/apps/utils/shell/shell.c index 6b7fee632c8..915e215b206 100644 --- a/reactos/apps/utils/shell/shell.c +++ b/reactos/apps/utils/shell/shell.c @@ -1,229 +1,225 @@ - -#include - -#include -#include -#include - -void debug_printf(char* fmt, ...) -{ - va_list args; - char buffer[255]; - - va_start(args,fmt); - vsprintf(buffer,fmt,args); - OutputDebugStringA(buffer); - va_end(args); -} - -HANDLE KeyboardHandle; - -void ExecuteCd(char* cmdline) -{ - UCHAR Buffer[255]; - - debug_printf("ExecuteCd(cmdline %s)\n",cmdline); - - if (cmdline[0] != '\\' && - cmdline[1] != ':') - { - GetCurrentDirectoryA(255,Buffer); - } - else - { - Buffer[0] = 0; - } - debug_printf("Buffer %s\n",Buffer); - - lstrcatA(Buffer,cmdline); - - debug_printf("Buffer %s\n",Buffer); - - if (Buffer[lstrlenA(Buffer)-1] != '\\') - { - lstrcatA(Buffer,"\\"); - } - debug_printf("Buffer %s\n",Buffer); - - SetCurrentDirectoryA(Buffer); -} - -void ExecuteDir(char* cmdline) -{ - HANDLE shandle; - WIN32_FIND_DATA FindData; - - shandle = FindFirstFile("*",&FindData); - - if (shandle==INVALID_HANDLE_VALUE) - { - return; - } - do - { - debug_printf("Scanning %s\n",FindData.cFileName); - } while(FindNextFile(shandle,&FindData)); -} - -void ExecuteType(char* cmdline) -{ - HANDLE FileHandle; - char c; - DWORD Result; - - FileHandle = CreateFile(cmdline, - FILE_GENERIC_READ, - 0, - NULL, - OPEN_EXISTING, - 0, - NULL); - while (ReadFile(FileHandle, - &c, - 1, - &Result, - NULL)) - { - debug_printf("%c",c); - c = 0; - } -} - -int ExecuteProcess(char* name, char* cmdline) -{ - PROCESS_INFORMATION ProcessInformation; - STARTUPINFO StartupInfo; - char arguments; - BOOL ret; - - memset(&StartupInfo,0,sizeof(StartupInfo)); - StartupInfo.cb = sizeof(STARTUPINFO); - StartupInfo.lpTitle = name; - - ret = CreateProcessA(name, - cmdline, - NULL, - NULL, - TRUE, - CREATE_NEW_CONSOLE, - NULL, - NULL, - &StartupInfo, - &ProcessInformation); - if (ret) - { - WaitForSingleObject(ProcessInformation.hProcess,INFINITE); - } - return(ret); -} - -void ExecuteCommand(char* line) -{ - char* cmd; - char* tail; - - if (line[1] == ':' && line[2] == 0) - { - line[2] = '\\'; - line[3] = 0; - SetCurrentDirectoryA(line); - return; - } - - tail = line; - while ((*tail)!=' ' && (*tail)!=0) - { - tail++; - } - if ((*tail)==' ') - { - *tail = 0; - tail++; - } - cmd = line; - -// debug_printf("cmd '%s' tail '%s'\n",cmd,tail); - - if (cmd==NULL) - { - return; - } - if (strcmp(cmd,"cd")==0) - { - ExecuteCd(tail); - return; - } - if (strcmp(cmd,"dir")==0) - { - ExecuteDir(tail); - return; - } - if (strcmp(cmd,"type")==0) - { - ExecuteType(tail); - return; - } - if (ExecuteProcess(cmd,tail)) - { - debug_printf("Done ExecuteProcess\n"); - return; - } - debug_printf("Unknown command\n"); -} - -void ReadLine(char* line) -{ - KEY_EVENT_RECORD KeyEvent; - DWORD Result; - UCHAR CurrentDir[255]; - - GetCurrentDirectoryA(255,CurrentDir); - debug_printf(CurrentDir); - - do - { - ReadFile(KeyboardHandle, - &KeyEvent, - sizeof(KEY_EVENT_RECORD), - &Result, - NULL); - if (KeyEvent.bKeyDown && KeyEvent.AsciiChar != 0) - { - debug_printf("%c",KeyEvent.AsciiChar); - *line = KeyEvent.AsciiChar; - line++; - } - } while (!(KeyEvent.bKeyDown && KeyEvent.AsciiChar == '\n')); - ReadFile(KeyboardHandle, - &KeyEvent, - sizeof(KEY_EVENT_RECORD), - &Result, - NULL); - line--; - *line = 0; -} - -void main() -{ - static char line[255]; - - KERNEL32_Init(); - - NtDisplayString("Shell Starting...\n"); - - KeyboardHandle = CreateFile("Keyboard", - FILE_GENERIC_READ, - 0, - NULL, - OPEN_EXISTING, - 0, - NULL); - - SetCurrentDirectoryA("C:\\"); - - for(;;) - { - ReadLine(line); - ExecuteCommand(line); - } -} +#include + +#include +#include +#include + +HANDLE InputHandle, OutputHandle; + +void debug_printf(char* fmt, ...) +{ + va_list args; + char buffer[255]; + + va_start(args,fmt); + vsprintf(buffer,fmt,args); + WriteConsoleA(OutputHandle, buffer, strlen(buffer), NULL, NULL); + va_end(args); +} + +void ExecuteCd(char* cmdline) +{ + UCHAR Buffer[255]; + + debug_printf("ExecuteCd(cmdline %s)\n",cmdline); + + if (cmdline[0] != '\\' && + cmdline[1] != ':') + { + GetCurrentDirectoryA(255,Buffer); + } + else + { + Buffer[0] = 0; + } + debug_printf("Buffer %s\n",Buffer); + + lstrcatA(Buffer,cmdline); + + debug_printf("Buffer %s\n",Buffer); + + if (Buffer[lstrlenA(Buffer)-1] != '\\') + { + lstrcatA(Buffer,"\\"); + } + debug_printf("Buffer %s\n",Buffer); + + SetCurrentDirectoryA(Buffer); +} + +void ExecuteDir(char* cmdline) +{ + HANDLE shandle; + WIN32_FIND_DATA FindData; + + shandle = FindFirstFile("*",&FindData); + + if (shandle==INVALID_HANDLE_VALUE) + { + return; + } + do + { + debug_printf("Scanning %s\n",FindData.cFileName); + } while(FindNextFile(shandle,&FindData)); +} + +void ExecuteType(char* cmdline) +{ + HANDLE FileHandle; + char c; + DWORD Result; + + FileHandle = CreateFile(cmdline, + FILE_GENERIC_READ, + 0, + NULL, + OPEN_EXISTING, + 0, + NULL); + while (ReadFile(FileHandle, + &c, + 1, + &Result, + NULL)) + { + debug_printf("%c",c); + c = 0; + } +} + +int ExecuteProcess(char* name, char* cmdline) +{ + PROCESS_INFORMATION ProcessInformation; + STARTUPINFO StartupInfo; + char arguments; + BOOL ret; + + memset(&StartupInfo,0,sizeof(StartupInfo)); + StartupInfo.cb = sizeof(STARTUPINFO); + StartupInfo.lpTitle = name; + + ret = CreateProcessA(name, + cmdline, + NULL, + NULL, + TRUE, + CREATE_NEW_CONSOLE, + NULL, + NULL, + &StartupInfo, + &ProcessInformation); + if (ret) + { + WaitForSingleObject(ProcessInformation.hProcess,INFINITE); + } + return(ret); +} + +void ExecuteCommand(char* line) +{ + char* cmd; + char* tail; + + if (line[1] == ':' && line[2] == 0) + { + line[2] = '\\'; + line[3] = 0; + SetCurrentDirectoryA(line); + return; + } + + tail = line; + while ((*tail)!=' ' && (*tail)!=0) + { + tail++; + } + if ((*tail)==' ') + { + *tail = 0; + tail++; + } + cmd = line; + +// debug_printf("cmd '%s' tail '%s'\n",cmd,tail); + + if (cmd==NULL) + { + return; + } + if (strcmp(cmd,"cd")==0) + { + ExecuteCd(tail); + return; + } + if (strcmp(cmd,"dir")==0) + { + ExecuteDir(tail); + return; + } + if (strcmp(cmd,"type")==0) + { + ExecuteType(tail); + return; + } + if (ExecuteProcess(cmd,tail)) + { + debug_printf("Done ExecuteProcess\n"); + return; + } + debug_printf("Unknown command\n"); +} + +void ReadLine(char* line) +{ + KEY_EVENT_RECORD KeyEvent; + DWORD Result; + UCHAR CurrentDir[255]; + + GetCurrentDirectoryA(255,CurrentDir); + debug_printf(CurrentDir); + + do + { + ReadConsoleA(InputHandle, + &KeyEvent, + sizeof(KEY_EVENT_RECORD), + &Result, + NULL); + if (KeyEvent.bKeyDown && KeyEvent.AsciiChar != 0) + { + debug_printf("%c", KeyEvent.AsciiChar); + *line = KeyEvent.AsciiChar; + line++; + } + } while (!(KeyEvent.bKeyDown && KeyEvent.AsciiChar == '\n')); + ReadFile(InputHandle, + &KeyEvent, + sizeof(KEY_EVENT_RECORD), + &Result, + NULL); + line--; + *line = 0; +} + +void main() +{ + static char line[255]; + + KERNEL32_Init(); + + AllocConsole(); + InputHandle = GetStdHandle(STD_INPUT_HANDLE); + OutputHandle = GetStdHandle(STD_OUTPUT_HANDLE); + + debug_printf("Shell Starting...\n"); + + SetCurrentDirectoryA("C:\\"); + + for(;;) + { + ReadLine(line); + ExecuteCommand(line); + } +} + diff --git a/reactos/bootflop.bat b/reactos/bootflop.bat new file mode 100644 index 00000000000..240b29ba039 --- /dev/null +++ b/reactos/bootflop.bat @@ -0,0 +1,38 @@ +@ECHO OFF + +: +: copy files to HD... +: +COPY /Y SHELL.BIN C:\reactos\system\SHELL.bin +COPY /Y BLUES.o C:\reactos\system\drivers\BLUES.o +COPY /Y KEYBOARD.o C:\reactos\system\drivers\KEYBOARD.o + +: +: present a menu to the booter... +: +ECHO 1) Keyboard,IDE,VFatFSD +ECHO 2) IDE,VFatFSD +ECHO 3) No Drivers +CHOICE /C:123 /T:2,10 "Select kernel boot config" +IF ERRORLEVEL 3 GOTO :L3 +IF ERRORLEVEL 2 GOTO :L2 + +:L1 +CLS +LOADROS KIMAGE.BIN KEYBOARD.O IDE.O VFATFSD.O +GOTO :END + +:L2 +CLS +LOADROS KIMAGE.BIN IDE.O VFATFSD.O +GOTO :END + +:L3 +CLS +LOADROS KIMAGE.BIN +GOTO :END + +:END +EXIT + + diff --git a/reactos/drivers/dd/blue/blues.c b/reactos/drivers/dd/blue/blues.c new file mode 100644 index 00000000000..4eef10d50f8 --- /dev/null +++ b/reactos/drivers/dd/blue/blues.c @@ -0,0 +1,154 @@ + +#undef WIN32_LEAN_AND_MEAN +#include +#include +#include +#include +#include + +//#define NDEBUG +#include + + + +#define FSCTL_GET_CONSOLE_SCREEN_BUFFER_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 254, DO_DIRECT_IO, FILE_READ_ACCESS|FILE_WRITE_ACCESS) +#define FSCTL_SET_CONSOLE_SCREEN_BUFFER_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 255, DO_DIRECT_IO, FILE_READ_ACCESS|FILE_WRITE_ACCESS) + + + +CONSOLE_SCREEN_BUFFER_INFO ConsoleScreenBufferInfo; + + +VOID ScrStartIo(PDEVICE_OBJECT DeviceObject, PIRP Irp) +{ + PIO_STACK_LOCATION stk = IoGetCurrentIrpStackLocation(Irp); + +} + +NTSTATUS ScrDispatch(PDEVICE_OBJECT DeviceObject, PIRP Irp) +{ + PIO_STACK_LOCATION stk = IoGetCurrentIrpStackLocation(Irp); + ULONG ControlCode; + NTSTATUS Status; + char *UserBuf = Irp->UserBuffer; + int i; + + switch (stk->MajorFunction) + { + case IRP_MJ_CREATE: + case IRP_MJ_CLOSE: + Status = STATUS_SUCCESS; + break; + + case IRP_MJ_WRITE: + for(i=0;iParameters.Write.Length;i++) + __putchar(UserBuf[i]); + Status = STATUS_SUCCESS; + break; + case IRP_MJ_DEVICE_CONTROL: + ControlCode = stk->Parameters.DeviceIoControl.IoControlCode; + if ( ControlCode == FSCTL_GET_CONSOLE_SCREEN_BUFFER_INFO ) { + // printk("get console screen buffer info\n"); + ConsoleScreenBufferInfo.dwCursorPosition.X=__wherex(); + ConsoleScreenBufferInfo.dwCursorPosition.Y=__wherey(); + + __getscreensize(&ConsoleScreenBufferInfo.dwSize.X, &ConsoleScreenBufferInfo.dwSize.Y ); + + memcpy(UserBuf,&ConsoleScreenBufferInfo,sizeof(CONSOLE_SCREEN_BUFFER_INFO)); + Status = STATUS_SUCCESS; + } + else if ( ControlCode == FSCTL_SET_CONSOLE_SCREEN_BUFFER_INFO ) { + // printk("set console screen buffer info\n"); + memcpy(&ConsoleScreenBufferInfo,UserBuf,sizeof(CONSOLE_SCREEN_BUFFER_INFO)); + __goxy(ConsoleScreenBufferInfo.dwCursorPosition.X,ConsoleScreenBufferInfo.dwCursorPosition.Y); + Status = STATUS_SUCCESS; + + } + break; + + default: + Status = STATUS_NOT_IMPLEMENTED; + break; + } + + +// DPRINT("Status %d\n",Status); + return(Status); +} + +/* + * Module entry point + */ +NTSTATUS DriverEntry(PDRIVER_OBJECT DriverObject, PUNICODE_STRING RegistryPath) +{ + PDEVICE_OBJECT DeviceObject; + ANSI_STRING adevice_name; + UNICODE_STRING device_name; + ANSI_STRING asymlink_name; + UNICODE_STRING symlink_name; + + DbgPrint("Screen Driver 0.0.4\n"); + + + DriverObject->MajorFunction[IRP_MJ_CREATE] = ScrDispatch; + DriverObject->MajorFunction[IRP_MJ_CLOSE] = ScrDispatch; + DriverObject->MajorFunction[IRP_MJ_READ] = ScrDispatch; + DriverObject->MajorFunction[IRP_MJ_WRITE] = ScrDispatch; + DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL ] = ScrDispatch; + DriverObject->DriverStartIo = ScrStartIo; + + //ScrSwitchToBlueScreen(); + + + RtlInitAnsiString(&adevice_name,"\\Device\\BlueScreen"); + RtlAnsiStringToUnicodeString(&device_name,&adevice_name,TRUE); + IoCreateDevice(DriverObject,0,&device_name,FILE_DEVICE_SCREEN,0, + TRUE,&DeviceObject); + + + RtlInitAnsiString(&asymlink_name,"\\??\\BlueScreen"); + RtlAnsiStringToUnicodeString(&symlink_name,&asymlink_name,TRUE); + IoCreateSymbolicLink(&symlink_name,&device_name); + + return(STATUS_SUCCESS); +} + + + + +/* FUNCTIONS ***************************************************************/ + + +void ScrSwitchToBlueScreen(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. + */ +{ + + /* + * Reset the cursor position + */ + ConsoleScreenBufferInfo.dwCursorPosition.X=__wherex(); + ConsoleScreenBufferInfo.dwCursorPosition.Y=__wherey(); + + __getscreensize(&ConsoleScreenBufferInfo.dwSize.X, &ConsoleScreenBufferInfo.dwSize.Y ); + + + /* + * This code section is taken from the sample routines by + * Jeff Morgan (kinfira@hotmail.com) + */ + +} + + + + + + + + + + diff --git a/reactos/drivers/dd/ide/ide.c b/reactos/drivers/dd/ide/ide.c index 529399af20d..7dfe9c3eefe 100644 --- a/reactos/drivers/dd/ide/ide.c +++ b/reactos/drivers/dd/ide/ide.c @@ -907,7 +907,7 @@ IDECreateDevice(IN PDRIVER_OBJECT DriverObject, IN DWORD Offset, IN DWORD Size) { - WORD UnicodeBuffer[IDE_MAX_NAME_LENGTH]; + WCHAR UnicodeBuffer[IDE_MAX_NAME_LENGTH]; NTSTATUS RC; ANSI_STRING AnsiName, AnsiSymLink; UNICODE_STRING UnicodeName, SymLink; @@ -915,7 +915,7 @@ IDECreateDevice(IN PDRIVER_OBJECT DriverObject, // Create a unicode device name RtlInitAnsiString(&AnsiName, DeviceName); - UnicodeName.MaximumLength = IDE_MAX_NAME_LENGTH; + UnicodeName.MaximumLength = IDE_MAX_NAME_LENGTH * sizeof(WCHAR); UnicodeName.Buffer = UnicodeBuffer; RtlAnsiStringToUnicodeString(&UnicodeName, &AnsiName, FALSE); diff --git a/reactos/include/conio.h b/reactos/include/conio.h new file mode 100644 index 00000000000..3c0b26be697 --- /dev/null +++ b/reactos/include/conio.h @@ -0,0 +1,111 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_conio_h_ +#define __dj_include_conio_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + + +extern int directvideo; /* ignored by gppconio */ +extern int _wscroll; + +#define _NOCURSOR 0 +#define _SOLIDCURSOR 1 +#define _NORMALCURSOR 2 + +struct text_info { + unsigned char winleft; + unsigned char wintop; + unsigned char winright; + unsigned char winbottom; + unsigned char attribute; + unsigned char normattr; + unsigned char currmode; + unsigned char screenheight; + unsigned char screenwidth; + unsigned char curx; + unsigned char cury; +}; + +enum text_modes { LASTMODE=-1, BW40=0, C40, BW80, C80, MONO=7, C4350=64 }; + +enum COLORS { + /* dark colors */ + BLACK, + BLUE, + GREEN, + CYAN, + RED, + MAGENTA, + BROWN, + LIGHTGRAY, + /* light colors */ + DARKGRAY, + LIGHTBLUE, + LIGHTGREEN, + LIGHTCYAN, + LIGHTRED, + LIGHTMAGENTA, + YELLOW, + WHITE +}; + +#define BLINK 0x80 /* blink bit */ + +void blinkvideo(void); +char * cgets(char *_str); +void clreol(void); +void clrscr(void); +int _conio_kbhit(void); /* checks for ungetch char */ +//int cprintf(const char *_format, ...) __attribute__((format(printf,1,2))); +int cputs(const char *_str); +//int cscanf(const char *_format, ...) __attribute__((format(scanf,1,2))); +void delline(void); +int getch(void); +int getche(void); +int gettext(int _left, int _top, int _right, int _bottom, void *_destin); +void gettextinfo(struct text_info *_r); +void gotoxy(int _x, int _y); +void gppconio_init(void); +void highvideo(void); +void insline(void); +void intensevideo(void); +void lowvideo(void); +int movetext(int _left, int _top, int _right, int _bottom, int _destleft, int _desttop); +void normvideo(void); +int putch(int _c); +int puttext(int _left, int _top, int _right, int _bottom, void *_source); +void _setcursortype(int _type); +void _set_screen_lines(int _nlines); +void textattr(int _attr); +void textbackground(int _color); +void textcolor(int _color); +void textmode(int _mode); +int ungetch(int); +unsigned int wherex(void); +unsigned int wherey(void); +void window(int _left, int _top, int _right, int _bottom); + +#define kbhit _conio_kbhit /* Who ever includes gppconio.h probably + also wants _conio_kbhit and not kbhit + from libc */ + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_conio_h_ */ diff --git a/reactos/include/direct.h b/reactos/include/direct.h new file mode 100644 index 00000000000..35002545832 --- /dev/null +++ b/reactos/include/direct.h @@ -0,0 +1,27 @@ +#ifndef __include_direct_h_ +#define __include_direct_h_ + +struct _diskfree_t { + unsigned short total_clusters; + unsigned short avail_clusters; + unsigned short sectors_per_cluster; + unsigned short bytes_per_sector; +}; + + +int _chdrive( int drive ); +int _getdrive( void ); +char *_getcwd( char *buffer, int maxlen ); + +int _chdir(const char *_path); +char *_getcwd(char *, int); +int _mkdir(const char *_path); +int _rmdir(const char *_path); +unsigned int _getdiskfree(unsigned int _drive, struct _diskfree_t *_diskspace); +#define chdir _chdir +#define getcwd _getcwd +#define mkdir _mkdir +#define rmdir _rmdir + + +#endif \ No newline at end of file diff --git a/reactos/include/fcntl.h b/reactos/include/fcntl.h new file mode 100644 index 00000000000..d6f772ab32e --- /dev/null +++ b/reactos/include/fcntl.h @@ -0,0 +1,164 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_fcntl_h_ +#define __dj_include_fcntl_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#define _IOREAD 000010 +#define _IOWRT 000020 +#define _IOMYBUF 000040 +#define _IOEOF 000100 +#define _IOERR 000200 +#define _IOSTRG 000400 +#define _IORW 001000 +#define _IOAPPEND 002000 +#define _IORMONCL 004000 /* remove on close, for temp files */ +/* if _flag & _IORMONCL, ._name_to_remove needs freeing */ +#define _IOUNGETC 010000 /* there is an ungetc'ed character in the buffer */ + + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#define FD_CLOEXEC 0x0001 + +#define F_DUPFD 1 +#define F_GETFD 2 +#define F_GETFL 3 +#define F_GETLK 4 +#define F_SETFD 5 +#define F_SETFL 6 +#define F_SETLK 7 +#define F_SETLKW 8 + +#define F_UNLCK 0 +#define F_RDLCK 1 +#define F_WRLCK 2 + +#define O_RDONLY 0x0000 +#define O_WRONLY 0x0001 +#define O_RDWR 0x0002 +#define O_ACCMODE 0x0003 + +#define O_BINARY 0x0004 /* must fit in char, reserved by dos */ +#define O_TEXT 0x0008 /* must fit in char, reserved by dos */ + +#define O_RANDOM 0x0010 +#define O_SEQUENTIAL 0x0020 + + +#define O_TEMPORARY 0x0040 + +/* temporary access hint */ + + + +/* sequential/random access hints */ + + + + +#define O_NOINHERIT 0x0080 /* DOS-specific */ + +#define O_CREAT 0x0100 /* second byte, away from DOS bits */ +#define O_EXCL 0x0200 +#define O_NOCTTY 0x0400 +#define O_TRUNC 0x0800 +#define O_APPEND 0x1000 +#define O_NONBLOCK 0x2000 + +#define O_SHORT_LIVED 0x1000 + +//#include +#include + +//typedef int dev_t; +//typedef int ino_t; +//typedef int mode_t; +//typedef int nlink_t; + +#include + + +struct flock { + off_t l_len; + pid_t l_pid; + off_t l_start; + short l_type; + short l_whence; +}; + +extern int _fmode; /* O_TEXT or O_BINARY */ + +//int open(const char *_path, int _oflag, ...); +//int creat(const char *_path, int _mode); +int fcntl(int _fildes, int _cmd, ...); + +#ifndef _POSIX_SOURCE + + +#define S_IREAD S_IRUSR +#define S_IWRITE S_IWUSR +#define S_IEXEC S_IXUSR + +/* + * For compatibility with other DOS C compilers. + */ + +#define _O_RDONLY O_RDONLY +#define _O_WRONLY O_WRONLY +#define _O_RDWR O_RDWR +#define _O_APPEND O_APPEND +#define _O_CREAT O_CREAT +#define _O_TRUNC O_TRUNC +#define _O_EXCL O_EXCL +#define _O_TEXT O_TEXT +#define _O_BINARY O_BINARY +#define _O_NOINHERIT O_NOINHERIT +#define _O_RANDOM O_RANDOM +#define _O_SEQUENTIAL O_RANDOM +#define _O_SHORT_LIVED O_SHORT_LIVED +#define _O_TEMPORARY O_TEMPORARY + +#define _S_IREAD S_IRUSR +#define _S_IWRITE S_IWUSR +#define _S_IEXEC S_IXUSR + +/* + * Support for advanced filesystems (Windows 9x VFAT, NTFS, LFN etc.) + */ + +#define _FILESYS_UNKNOWN 0x80000000U +#define _FILESYS_CASE_SENSITIVE 0x0001 +#define _FILESYS_CASE_PRESERVED 0x0002 +#define _FILESYS_UNICODE 0x0004 +#define _FILESYS_LFN_SUPPORTED 0x4000 +#define _FILESYS_VOL_COMPRESSED 0x8000 + +unsigned _get_volume_info (const char *_path, int *_max_file_len, int *_max_path_len, char *_filesystype); +char _use_lfn (const char *_path); +char *_lfn_gen_short_fname (const char *_long_fname, char *_short_fname); + +#define _LFN_CTIME 1 +#define _LFN_ATIME 2 + +unsigned _lfn_get_ftime (int _handle, int _which); + +char _preserve_fncase (void); +#define _USE_LFN _use_lfn(0) /* assume it's the same on ALL drives */ + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_fcntl_h_ */ diff --git a/reactos/include/internal/ntoskrnl.h b/reactos/include/internal/ntoskrnl.h index a38a2eb8968..850fda90779 100644 --- a/reactos/include/internal/ntoskrnl.h +++ b/reactos/include/internal/ntoskrnl.h @@ -39,6 +39,11 @@ extern descriptor gdt[256]; /* * printf style functions */ +void __putchar(char c); +void __goxy(unsigned x, unsigned y); +unsigned __wherex (void); +unsigned __wherey (void); +void __getscreensize (unsigned *maxx, unsigned *maxy); asmlinkage void printk(const char* fmt, ...); int vsprintf(char *buf, const char *fmt, va_list args); int sprintf(char* buf, const char* fmt, ...); @@ -86,4 +91,10 @@ void TstBegin(void); VOID KeInit(VOID); VOID HalInitConsole(boot_param* bp); +/* + * Loader functions (called in main()) + */ +VOID LdrInitModuleManagement(VOID); +VOID LdrLoadAutoConfigDrivers(VOID); + #endif diff --git a/reactos/include/io.h b/reactos/include/io.h new file mode 100644 index 00000000000..bb42272e368 --- /dev/null +++ b/reactos/include/io.h @@ -0,0 +1,94 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_io_h_ +#define __dj_include_io_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +#include +#include + + +/* + * For compatibility with other DOS C compilers. + */ + +#define _A_NORMAL 0x00 /* Normal file - No read/write restrictions */ +#define _A_RDONLY 0x01 /* Read only file */ +#define _A_HIDDEN 0x02 /* Hidden file */ +#define _A_SYSTEM 0x04 /* System file */ +#define _A_VOLID 0x08 /* Volume ID file */ +#define _A_SUBDIR 0x10 /* Subdirectory */ +#define _A_ARCH 0x20 /* Archive file */ + + +struct _finddata_t { + char reserved[21] __attribute__((packed)); + unsigned char attrib __attribute__((packed)); + unsigned short time_create __attribute__((packed)); + unsigned short time_access __attribute__((packed)); + unsigned short time_write __attribute__((packed)); + unsigned long size __attribute__((packed)); + char name[256] __attribute__((packed)); +}; + +int chsize(int handle, long size); +int close(int _fd); +int _close(int _fd); +int _creat(const char *_path, int _attrib); +unsigned int _commit(int _handle); +ssize_t crlf2nl(char *_buffer, ssize_t _length); +int _dos_lock(int _fd, long _offset, long _length); +long filelength(int _handle); +long _findfirst(char *_name, struct _finddata_t *_result); +int _findnext(long handle, struct _finddata_t *_result); +int _findclose(long handle); +short _get_dev_info(int _arg); +int lock(int _fd, long _offset, long _length); +int _open(const char *_path, int _oflag, ...); +size_t _read(int _fd, void *_buf,size_t _nbyte); +int setmode(int _fd, int _newmode); +int _setmode(int _fd, int _newmode); +off_t tell(int _fd); +int _dos_unlock(int _fd, long _offset, long _length); +int unlock(int _fd, long _offset, long _length); +size_t _write(int _fd, const void *_buf, size_t _nbyte); +int _chmod(const char *_path, int _func, ...); +void _flush_disk_cache(void); + +int _dup( int handle); +int _dup2( int handle1, int handle2 ); +long _lseek(int _filedes, long _offset, int _whence); +int _open_osfhandle ( void *osfhandle, int flags ); + +#define open _open +#define dup _dup +#define dup2 _dup2 +#define lseek _lseek +#define open_osfhandle _open_osfhandle + + + + +#define sopen(path, access, shflag, mode) \ + open((path), (access)|(shflag), (mode)) + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_io_h_ */ diff --git a/reactos/include/kernel32/heap.h b/reactos/include/kernel32/heap.h index 7cc17d31ea3..6a1de987aa5 100644 --- a/reactos/include/kernel32/heap.h +++ b/reactos/include/kernel32/heap.h @@ -16,8 +16,8 @@ #include /* definitions */ -#define HEAP_ADMIN_SIZE 8 -#define HEAP_FRAG_ADMIN_SIZE 8 +#define HEAP_ADMIN_SIZE (sizeof(HEAP_BLOCK)) +#define HEAP_FRAG_ADMIN_SIZE (sizeof(HEAP_FRAGMENT)) #define HEAP_ROUNDVAL (2*(HEAP_ADMIN_SIZE)-1) #define HEAP_FRAGMENT_THRESHOLD 256 diff --git a/reactos/include/process.h b/reactos/include/process.h new file mode 100644 index 00000000000..ffcb90dea29 --- /dev/null +++ b/reactos/include/process.h @@ -0,0 +1,52 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_process_h_ +#define __dj_include_process_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +int _dos_exec(const char *program, const char *args, char *const _envp[]); + +int execl(const char *_path, const char *_argv0, ...); +int execle(const char *_path, const char *_argv0, ... /*, char *const _envp[] */); +int execlp(const char *_path, const char *_argv0, ...); +int execlpe(const char *_path, const char *_argv0, ... /*, char *const _envp[] */); + +int execv(const char *_path,const char *const _argv[]); +int execve(const char *_path,const char *const _argv[],const char *const _envp[]); +int execvp(const char *_path,const char *const _argv[]); +int execvpe(const char *_path,const char *const _argv[],const char *const _envp[]); + +int spawnl(int _mode, const char *_path, const char *_argv0, ...); +int spawnle(int _mode, const char *_path, const char *_argv0, ... /*, char *const _envp[] */); +int spawnlp(int _mode, const char *_path, const char *_argv0, ...); +int spawnlpe(int _mode, const char *_path, const char *_argv0, ... /*, char *const _envp[] */); + +int spawnv(int _mode, const char *_path,const char *const _argv[]); +int spawnve(int _mode, const char *_path,const char *const _argv[],const char *const _envp[]); +int spawnvp(int _mode, const char *_path,const char *const _argv[]); +int spawnvpe(int _mode, const char *_path,const char *const _argv[],const char *const _envp[]); + +#define P_WAIT 1 +#define P_NOWAIT 2 /* always generates error */ +#define P_OVERLAY 3 + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_process_h_ */ diff --git a/reactos/include/share.h b/reactos/include/share.h new file mode 100644 index 00000000000..c6087e177af --- /dev/null +++ b/reactos/include/share.h @@ -0,0 +1,17 @@ +#ifndef _include_share_h_ +#define _include_share_h_ + + +#define SH_COMPAT 0x0000 +#define SH_DENYRW 0x0010 +#define SH_DENYWR 0x0020 +#define SH_DENYRD 0x0030 +#define SH_DENYNO 0x0040 + +#define _SH_COMPAT SH_COMPAT +#define _SH_DENYRW SH_DENYRW +#define _SH_DENYWR SH_DENYWR +#define _SH_DENYRD SH_DENYRD +#define _SH_DENYNO SH_DENYNO + +#endif \ No newline at end of file diff --git a/reactos/include/stdio.h b/reactos/include/stdio.h new file mode 100644 index 00000000000..85f4ef8d75b --- /dev/null +++ b/reactos/include/stdio.h @@ -0,0 +1,157 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#ifndef __dj_include_stdio_h_ +#define __dj_include_stdio_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#include + +#define _IOFBF 00001 +#define _IONBF 00002 +#define _IOLBF 00004 + +#define BUFSIZ 16384 +#define EOF (-1) +#define FILENAME_MAX 260 +#define FOPEN_MAX 20 +#define L_tmpnam 260 +#ifndef NULL +#define NULL 0 +#endif +#define TMP_MAX 999999 + +#define SEEK_SET 0 +#define SEEK_CUR 1 +#define SEEK_END 2 + +#define _IOREAD 000010 +#define _IOWRT 000020 +#define _IOMYBUF 000040 +#define _IOEOF 000100 +#define _IOERR 000200 +#define _IOSTRG 000400 +#define _IORW 001000 +#define _IOAPPEND 002000 +#define _IORMONCL 004000 /* remove on close, for temp files */ +/* if _flag & _IORMONCL, ._name_to_remove needs freeing */ +#define _IOUNGETC 010000 /* there is an ungetc'ed character in the buffer */ + + +#include + +__DJ_va_list +#undef __DJ_va_list +#define __DJ_va_list + +#ifndef _FILE_DEFINED +typedef struct { + char *_ptr; + int _cnt; + char *_base; + int _flag; + int _file; + int _ungotchar; + int _bufsiz; + char *_name_to_remove; +} FILE; +#define _FILE_DEFINED +#endif + +typedef unsigned long fpos_t; + +extern FILE _iob[]; + +#define stdin (&_iob[0]) +#define stdout (&_iob[1]) +#define stderr (&_iob[2]) +#define stdaux (&_iob[3]) +#define stdprn (&_iob[4]) + +void clearerr(FILE *_stream); +int fclose(FILE *_stream); +int feof(FILE *_stream); +int ferror(FILE *_stream); +int fflush(FILE *_stream); +int fgetc(FILE *_stream); +int fgetpos(FILE *_stream, fpos_t *_pos); +char * fgets(char *_s, int _n, FILE *_stream); +FILE * fopen(const char *_filename, const char *_mode); +int fprintf(FILE *_stream, const char *_format, ...); +int fputc(int _c, FILE *_stream); +int fputs(const char *_s, FILE *_stream); +size_t fread(void *_ptr, size_t _size, size_t _nelem, FILE *_stream); +FILE * freopen(const char *_filename, const char *_mode, FILE *_stream); +int fscanf(FILE *_stream, const char *_format, ...); +int fseek(FILE *_stream, long _offset, int _mode); +int fsetpos(FILE *_stream, const fpos_t *_pos); +long ftell(FILE *_stream); +size_t fwrite(const void *_ptr, size_t _size, size_t _nelem, FILE *_stream); +int getc(FILE *_stream); +int getchar(void); +char * gets(char *_s); +void perror(const char *_s); +int printf(const char *_format, ...); +int putc(int _c, FILE *_stream); +int putchar(int _c); +int puts(const char *_s); +int remove(const char *_filename); +int rename(const char *_old, const char *_new); +void rewind(FILE *_stream); +int scanf(const char *_format, ...); +void setbuf(FILE *_stream, char *_buf); +int setvbuf(FILE *_stream, char *_buf, int _mode, size_t _size); +int sprintf(char *_s, const char *_format, ...); +int sscanf(const char *_s, const char *_format, ...); +FILE * tmpfile(void); +char * tmpnam(char *_s); +char * _tmpnam(char *_s); +int ungetc(int _c, FILE *_stream); +int vfprintf(FILE *_stream, const char *_format, va_list _ap); +int vprintf(const char *_format, va_list _ap); +int vsprintf(char *_s, const char *_format, va_list _ap); + +#ifndef __STRICT_ANSI__ + +#define L_ctermid +#define L_cusrid +/* #define STREAM_MAX 20 - DOS can change this */ + +int fileno(FILE *_stream); +int _fileno(FILE *_stream); +FILE * fdopen(int _fildes, const char *_type); +int pclose(FILE *_pf); +FILE * popen(const char *_command, const char *_mode); + +#ifndef _POSIX_SOURCE + +void _djstat_describe_lossage(FILE *_to_where); +int _doprnt(const char *_fmt, va_list _args, FILE *_f); +int _doscan(FILE *_f, const char *_fmt, void **_argp); +int _doscan_low(FILE *, int (*)(FILE *_get), int (*_unget)(int, FILE *), const char *_fmt, void **_argp); +int fpurge(FILE *_f); +int getw(FILE *_f); +int mkstemp(char *_template); +char * mktemp(char *_template); +int putw(int _v, FILE *_f); +void setbuffer(FILE *_f, void *_buf, int _size); +void setlinebuf(FILE *_f); +char * tempnam(const char *_dir, const char *_prefix); +int _rename(const char *_old, const char *_new); /* Simple (no directory) */ + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_stdio_h_ */ diff --git a/reactos/include/stdlib.h b/reactos/include/stdlib.h new file mode 100644 index 00000000000..fae1e5a7524 --- /dev/null +++ b/reactos/include/stdlib.h @@ -0,0 +1,131 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_stdlib_h_ +#define __dj_include_stdlib_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +//#include + +#define EXIT_FAILURE 1 +#define EXIT_SUCCESS 0 +#define MB_CUR_MAX __dj_mb_cur_max +#ifndef NULL +#define NULL 0 +#endif +#define RAND_MAX 2147483647 + +#define _MAX_DRIVE 26 +#define _MAX_FNAME 100 +#define _MAX_EXT 100 +#define _MAX_DIR 26 +#define _MAX_PATH 250 + + +extern int errno; +extern int __dj_mb_cur_max; + +extern char ** environ; + + +typedef struct { + int quot; + int rem; +} div_t; + +typedef struct { + long quot; + long rem; +} ldiv_t; + +#include +#ifndef _WCHAR_T_ +#define _WCHAR_T_ +#define _WCHAR_T + typedef int wchar_t; +#endif + + +void abort(void) __attribute__((noreturn)); +int abs(int _i); +int atexit(void (*_func)(void)); +double atof(const char *_s); +int atoi(const char *_s); +long atol(const char *_s); +void * bsearch(const void *_key, const void *_base, size_t _nelem, + size_t _size, int (*_cmp)(const void *_ck, const void *_ce)); +void * calloc(size_t _nelem, size_t _size); +div_t div(int _numer, int _denom); +void exit(int _status) __attribute__((noreturn)); +void free(void *_ptr); +char * getenv(const char *_name); +long labs(long _i); +ldiv_t ldiv(long _numer, long _denom); +void * malloc(size_t _size); +int mblen(const char *_s, size_t _n); +size_t mbstowcs(wchar_t *_wcs, const char *_s, size_t _n); +int mbtowc(wchar_t *_pwc, const char *_s, size_t _n); +void qsort(void *_base, size_t _nelem, size_t _size, + int (*_cmp)(const void *_e1, const void *_e2)); +int rand(void); +void * realloc(void *_ptr, size_t _size); +void srand(unsigned _seed); +double strtod(const char *_s, char **_endptr); +long strtol(const char *_s, char **_endptr, int _base); +unsigned long strtoul(const char *_s, char **_endptr, int _base); +int system(const char *_s); +size_t wcstombs(char *_s, const wchar_t *_wcs, size_t _n); +int wctomb(char *_s, wchar_t _wchar); + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +typedef struct { + long long quot; + long long rem; +} lldiv_t; + +void * alloca(size_t _size); +long double _atold(const char *_s); +long long atoll(const char *_s); +void cfree(void *_ptr); +char * getpass(const char *_prompt); +int getlongpass(const char *_prompt, char *_buffer, int _max_len); +char * itoa(int value, char *buffer, int radix); +long long llabs(long long _i); +lldiv_t lldiv(long long _numer, long long _denom); +int putenv(const char *_val); +int setenv(const char *_var, const char *_val, int _replace); +double _strtold(const char *_s, char **_endptr); +long strtoll(const char *_s, char **_endptr, int _base); +unsigned long strtoull(const char *_s, char **_endptr, int _base); +void swab(const void *from, void *to, int nbytes); + +#ifndef alloca +#define alloca __builtin_alloca +#endif + +/* BSD Random Number Generator */ +char * initstate (unsigned _seed, char *_arg_state, int _n); +char * setstate(char *_arg_state); +long random(void); +int srandom(int _seed); + + + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_stdlib_h_ */ diff --git a/reactos/include/string.h b/reactos/include/string.h index 0d9c811dbc5..575cf1e1141 100644 --- a/reactos/include/string.h +++ b/reactos/include/string.h @@ -21,6 +21,7 @@ extern "C" { #endif +#define __kernel_size_t size_t char * ___strtok; // removed extern specifier 02-06-98, BD @@ -47,6 +48,13 @@ extern void * memmove(void *,const void *,__kernel_size_t); extern void * memscan(void *,int,__kernel_size_t); extern int memcmp(const void *,const void *,__kernel_size_t); +char *strerror( int errnum ); +char *_strerror( const char *string ); + +// obsolete +int strcasecmp (const char* sz1, const char* sz2); +int strncasecmp (const char* sz1, const char* sz2, size_t sizeMaxCompare); + /* * Include machine specific inline routines diff --git a/reactos/include/time.h b/reactos/include/time.h new file mode 100644 index 00000000000..c170157f78c --- /dev/null +++ b/reactos/include/time.h @@ -0,0 +1,104 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_time_h_ +#define __dj_include_time_h_ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +/* 65536(tics/hour) / 3600(sec/hour) * 5(scale) = 91.02 + The 5 is to make it a whole number (18.2*5=91) so that + floating point ops aren't required to use it. */ +#define CLOCKS_PER_SEC 91 + +#include +#include +#ifndef NULL +#define NULL 0 +#endif +__DJ_clock_t +#undef __DJ_clock_t +#define __DJ_clock_t +//__DJ_size_t +#undef __DJ_size_t +#define __DJ_size_t +__DJ_time_t +#undef __DJ_time_t +#define __DJ_time_t + + +#ifndef _TM_DEFINED +struct tm { + int tm_sec; + int tm_min; + int tm_hour; + int tm_mday; + int tm_mon; + int tm_year; + int tm_wday; + int tm_yday; + int tm_isdst; + char *tm_zone; + int tm_gmtoff; +}; +#define _TM_DEFINED +#endif + +char * asctime(const struct tm *_tptr); +clock_t clock(void); +char * ctime(const time_t *_cal); +double difftime(time_t _t1, time_t _t0); +struct tm * gmtime(const time_t *_tod); +struct tm * localtime(const time_t *_tod); +time_t mktime(struct tm *_tptr); +size_t strftime(char *_s, size_t _n, const char *_format, const struct tm *_tptr); +time_t time(time_t *_tod); + +#ifndef __STRICT_ANSI__ + +#define CLK_TCK CLOCKS_PER_SEC + +extern char *tzname[2]; + +void tzset(void); + +#ifndef _POSIX_SOURCE + +//#define tm_zone __tm_zone +//#define tm_gmtoff __tm_gmtoff + +struct timeval { + time_t tv_sec; + long tv_usec; +}; + +struct timezone { + int tz_minuteswest; + int tz_dsttime; +}; + +#include + +typedef long long uclock_t; +#define UCLOCKS_PER_SEC 1193180 + +int gettimeofday(struct timeval *_tp, struct timezone *_tzp); +unsigned long rawclock(void); +int select(int _nfds, fd_set *_readfds, fd_set *_writefds, fd_set *_exceptfds, struct timeval *_timeout); +int settimeofday(struct timeval *_tp, ...); +uclock_t uclock(void); + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* !__dj_include_time_h_ */ diff --git a/reactos/include/wchar.h b/reactos/include/wchar.h new file mode 100644 index 00000000000..021016120a7 --- /dev/null +++ b/reactos/include/wchar.h @@ -0,0 +1,81 @@ +/* + * Adapted from linux for the reactos kernel, march 1998 -- David Welch + * Added wide character string functions, june 1998 -- Boudewijn Dekker + * Removed extern specifier from ___wcstok, june 1998 -- Boudewijn Dekker + * Added wcsicmp and wcsnicmp -- Boudewijn Dekker + */ + +#include + +#ifndef _LINUX_WSTRING_H_ +#define _LINUX_WSTRING_H_ + + + +#ifndef _WCHAR_T_ +#define _WCHAR_T_ +#define _WCHAR_T + typedef unsigned short wchar_t; +#endif +#define Aa_Difference (L'A'-L'a') + +#define towupper(c) (((c>=L'a') && (c<=L'z')) ? c+Aa_Difference : c) +#define towlower(c) (((c>=L'A') && (c<=L'Z')) ? c-Aa_Difference : c) + +//obsolete +wchar_t wtolower(wchar_t c ); +wchar_t wtoupper(wchar_t c ); + + +#define iswlower(c) ((c) >= L'a' && (c) <= L'z') +#define iswupper(c) ((c) >= L'A' && (c) <= L'Z') + +#define iswdigit(c) ((c) >= L'0' && (c) <= L'9') +#define iswxdigit(c) (((c) >= L'0' && (c) <= L'9') || ((c) >= L'A' && (c) <= L'F') || ((c) >= L'a' && (c) <= L'f') ) + +#ifndef NULL +#define NULL ((void *) 0) +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +//wchar_t * ___wcstok = NULL; +wchar_t * wcscpy(wchar_t *,const wchar_t *); +wchar_t * wcsncpy(wchar_t *,const wchar_t *, size_t); +wchar_t * wcscat(wchar_t *, const wchar_t *); +wchar_t * wcsncat(wchar_t *, const wchar_t *, size_t); +int wcscmp(const wchar_t *,const wchar_t *); +int wcsncmp(const wchar_t *,const wchar_t *,size_t); +wchar_t* wcschr(const wchar_t* str, wchar_t ch); +wchar_t * wcsrchr(const wchar_t *,wchar_t); +wchar_t * wcspbrk(const wchar_t *,const wchar_t *); +wchar_t * wcstok(wchar_t *,const wchar_t *); +wchar_t * wcsstr(const wchar_t *,const wchar_t *); +size_t wcslen(const wchar_t * s); +size_t wcsnlen(const wchar_t * s, size_t count); +int wcsicmp(const wchar_t* cs,const wchar_t * ct); +int wcsnicmp(const wchar_t* cs,const wchar_t * ct, size_t count); +size_t wcsspn(const wchar_t *str,const wchar_t *accept); +size_t wcscspn(const wchar_t *str,const wchar_t *reject); +wchar_t *wcsrev(wchar_t *s); +wchar_t *wcsstr(const wchar_t *s,const wchar_t *b); +wchar_t *wcsdup(const wchar_t *ptr); +wchar_t *wcsupr(wchar_t *x); +wchar_t * wcslwr(wchar_t *x); + +//obsolete +size_t wstrlen(const wchar_t * s); +int wcscmpi (const wchar_t* ws1, const wchar_t* ws2); + + + + + +#ifdef __cplusplus +} +#endif + +#endif + diff --git a/reactos/include/wstring.h b/reactos/include/wstring.h index 91182a84963..59c1888349a 100644 --- a/reactos/include/wstring.h +++ b/reactos/include/wstring.h @@ -1,52 +1,3 @@ -/* - * Adapted from linux for the reactos kernel, march 1998 -- David Welch - * Added wide character string functions, june 1998 -- Boudewijn Dekker - * Removed extern specifier from ___wcstok, june 1998 -- Boudewijn Dekker - * Added wcsicmp and wcsnicmp -- Boudewijn Dekker - */ - -#ifndef _LINUX_WSTRING_H_ -#define _LINUX_WSTRING_H_ - -#include /* for size_t */ - -typedef unsigned short wchar_t; - -#ifndef NULL -#define NULL ((void *) 0) -#endif - -#ifdef __cplusplus -extern "C" { -#endif - -wchar_t* wstrdup(const wchar_t* src); -extern wchar_t * ___wcstok; -extern wchar_t * wcscpy(wchar_t *,const wchar_t *); -extern wchar_t * wcsncpy(wchar_t *,const wchar_t *, __kernel_size_t); -extern wchar_t * wcscat(wchar_t *, const wchar_t *); -extern wchar_t * wcsncat(wchar_t *, const wchar_t *, __kernel_size_t); -extern int wcscmp(const wchar_t *,const wchar_t *); -extern int wcsncmp(const wchar_t *,const wchar_t *,__kernel_size_t); -wchar_t* wcschr(const wchar_t* str, wchar_t ch); -extern wchar_t * wcsrchr(const wchar_t *,wchar_t); -extern wchar_t * wcspbrk(const wchar_t *,const wchar_t *); -extern wchar_t * wcstok(wchar_t *,const wchar_t *); -extern wchar_t * wcsstr(const wchar_t *,const wchar_t *); -extern size_t wcsnlen(const wchar_t * s, size_t count); -extern int wcsicmp(const wchar_t* cs,const wchar_t * ct); -extern int wcsnicmp(const wchar_t* cs,const wchar_t * ct, size_t count); -extern size_t wcscspn(const wchar_t *, const wchar_t *); -extern size_t wcslen(const wchar_t *); -extern size_t wcsspn(const wchar_t *, const wchar_t *); - -extern unsigned long wstrlen(PWSTR); -WCHAR wtoupper(WCHAR c); -WCHAR wtolower(WCHAR c); - -#ifdef __cplusplus -} -#endif - -#endif - +// this file is obsolete +#include + diff --git a/reactos/lib/crtdll/conio/cputs.c b/reactos/lib/crtdll/conio/cputs.c new file mode 100644 index 00000000000..05dfab50dfc --- /dev/null +++ b/reactos/lib/crtdll/conio/cputs.c @@ -0,0 +1,21 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/cputs.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include +#include + +int cputs(const char *_str) +{ + int len = strlen(_str); + int written = 0; + if ( !WriteFile(GetStdHandle(STD_OUTPUT_HANDLE),_str,len,&written,NULL)) + return -1; + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/conio/getch.c b/reactos/lib/crtdll/conio/getch.c new file mode 100644 index 00000000000..4ca74b0b787 --- /dev/null +++ b/reactos/lib/crtdll/conio/getch.c @@ -0,0 +1,42 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/getch.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include +#include + +extern int char_avail; +extern int ungot_char; + +int getch( void ) +{ + return _getch(); +} + +int +_getch(void) +{ + + DWORD NumberOfCharsRead; + char c; + if (char_avail) + { + c = ungot_char; + char_avail = 0; + } + else + { + + if( !ReadFile(filehnd(stdin->_file), &c,1,&NumberOfCharsRead ,NULL)) + return -1; + + } + printk("%c",c); + return c; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/conio/getche.c b/reactos/lib/crtdll/conio/getche.c new file mode 100644 index 00000000000..e35002334f5 --- /dev/null +++ b/reactos/lib/crtdll/conio/getche.c @@ -0,0 +1,33 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/getche.c + * PURPOSE: Reads a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include +#include + + +extern int char_avail; +int +getche(void) +{ + if (char_avail) + /* + * We don't know, wether the ungot char was already echoed + * we assume yes (for example in cscanf, probably the only + * place where ungetch is ever called. + * There is no way to check for this really, because + * ungetch could have been called with a character that + * hasn't been got by a conio function. + * We don't echo again. + */ + return(getch()); + return (_putch(getch())); +} diff --git a/reactos/lib/crtdll/conio/putch.c b/reactos/lib/crtdll/conio/putch.c new file mode 100644 index 00000000000..cbeaa078c9c --- /dev/null +++ b/reactos/lib/crtdll/conio/putch.c @@ -0,0 +1,21 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/putch.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include + +int _putch( int c ) +{ + DWORD NumberOfCharsWritten; + if ( WriteFile(GetStdHandle(STD_OUTPUT_HANDLE),&c,1,&NumberOfCharsWritten,NULL) ) { + return -1; + } + + return NumberOfCharsWritten; +} diff --git a/reactos/lib/crtdll/conio/ungetch.c b/reactos/lib/crtdll/conio/ungetch.c new file mode 100644 index 00000000000..5e08fdadc21 --- /dev/null +++ b/reactos/lib/crtdll/conio/ungetch.c @@ -0,0 +1,28 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/ungetch.c + * PURPOSE: Ungets a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker [ Adapted from djgpp libc ] + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include +#define EOF -1 + +int char_avail = 0; +char ungot_char = 0; + + +int +ungetch(int c) +{ + if (char_avail) + return(EOF); + ungot_char = c; + char_avail = 1; + return(c); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/ctype/MAKEFILE b/reactos/lib/crtdll/ctype/MAKEFILE new file mode 100644 index 00000000000..2fa6f26e0bb --- /dev/null +++ b/reactos/lib/crtdll/ctype/MAKEFILE @@ -0,0 +1,23 @@ +# Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details +TOP=../.. + +SRC += ct_flags.c +SRC += ct_lower.c +SRC += ct_upper.c +SRC += isalnum.c +SRC += isalpha.c +SRC += isascii.c +SRC += iscntrl.c +SRC += isdigit.c +SRC += isgraph.c +SRC += islower.c +SRC += isprint.c +SRC += ispunct.c +SRC += isspace.c +SRC += isupper.c +SRC += isxdigit.c +SRC += toascii.c +SRC += tolower.c +SRC += toupper.c + +include $(TOP)/../makefile.inc diff --git a/reactos/lib/crtdll/ctype/atof.c b/reactos/lib/crtdll/ctype/atof.c new file mode 100644 index 00000000000..c6469856c4a --- /dev/null +++ b/reactos/lib/crtdll/ctype/atof.c @@ -0,0 +1,18 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/ungetch.c + * PURPOSE: Ungets a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker [ Adapted from djgpp libc ] + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include + +double +atof(const char *ascii) +{ + return strtod(ascii, 0); +} diff --git a/reactos/lib/crtdll/ctype/atoi.c b/reactos/lib/crtdll/ctype/atoi.c new file mode 100644 index 00000000000..1ebbe88a809 --- /dev/null +++ b/reactos/lib/crtdll/ctype/atoi.c @@ -0,0 +1,19 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/ungetch.c + * PURPOSE: Ungets a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker [ Adapted from djgpp libc ] + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include + +int +atoi(const char *str) +{ + return (int)strtol(str, 0, 10); +} diff --git a/reactos/lib/crtdll/ctype/atol.c b/reactos/lib/crtdll/ctype/atol.c new file mode 100644 index 00000000000..e1461462ef1 --- /dev/null +++ b/reactos/lib/crtdll/ctype/atol.c @@ -0,0 +1,20 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/atol.c + * PURPOSE: Ungets a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker [ Adapted from djgpp libc ] + * UPDATE HISTORY: + * 28/12/98: Created + */ + +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long +atol(const char *str) +{ + return strtol(str, 0, 10); +} diff --git a/reactos/lib/crtdll/ctype/atold.c b/reactos/lib/crtdll/ctype/atold.c new file mode 100644 index 00000000000..b327fc0c6f4 --- /dev/null +++ b/reactos/lib/crtdll/ctype/atold.c @@ -0,0 +1,19 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/ungetch.c + * PURPOSE: Ungets a character from stdin + * PROGRAMER: DJ Delorie + Boudewijn Dekker [ Adapted from djgpp libc ] + * UPDATE HISTORY: + * 28/12/98: Created + */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long double +_atold(const char *ascii) +{ + return _strtold(ascii, 0); +} diff --git a/reactos/lib/crtdll/ctype/ct_flags.c b/reactos/lib/crtdll/ctype/ct_flags.c new file mode 100644 index 00000000000..c897e5ecb94 --- /dev/null +++ b/reactos/lib/crtdll/ctype/ct_flags.c @@ -0,0 +1,264 @@ + +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +unsigned short __dj_ctype_flags[] = { + 0, /* CTRL+?, 0xffff */ + __dj_ISCNTRL, /* CTRL+@, 0x00 */ + __dj_ISCNTRL, /* CTRL+A, 0x01 */ + __dj_ISCNTRL, /* CTRL+B, 0x02 */ + __dj_ISCNTRL, /* CTRL+C, 0x03 */ + __dj_ISCNTRL, /* CTRL+D, 0x04 */ + __dj_ISCNTRL, /* CTRL+E, 0x05 */ + __dj_ISCNTRL, /* CTRL+F, 0x06 */ + __dj_ISCNTRL, /* CTRL+G, 0x07 */ + __dj_ISCNTRL, /* CTRL+H, 0x08 */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+I, 0x09 */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+J, 0x0a */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+K, 0x0b */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+L, 0x0c */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+M, 0x0d */ + __dj_ISCNTRL, /* CTRL+N, 0x0e */ + __dj_ISCNTRL, /* CTRL+O, 0x0f */ + __dj_ISCNTRL, /* CTRL+P, 0x10 */ + __dj_ISCNTRL, /* CTRL+Q, 0x11 */ + __dj_ISCNTRL, /* CTRL+R, 0x12 */ + __dj_ISCNTRL, /* CTRL+S, 0x13 */ + __dj_ISCNTRL, /* CTRL+T, 0x14 */ + __dj_ISCNTRL, /* CTRL+U, 0x15 */ + __dj_ISCNTRL, /* CTRL+V, 0x16 */ + __dj_ISCNTRL, /* CTRL+W, 0x17 */ + __dj_ISCNTRL, /* CTRL+X, 0x18 */ + __dj_ISCNTRL, /* CTRL+Y, 0x19 */ + __dj_ISCNTRL, /* CTRL+Z, 0x1a */ + __dj_ISCNTRL, /* CTRL+[, 0x1b */ + __dj_ISCNTRL, /* CTRL+\, 0x1c */ + __dj_ISCNTRL, /* CTRL+], 0x1d */ + __dj_ISCNTRL, /* CTRL+^, 0x1e */ + __dj_ISCNTRL, /* CTRL+_, 0x1f */ + __dj_ISPRINT | __dj_ISSPACE, /* ` ', 0x20 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `!', 0x21 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x22 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `#', 0x23 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `$', 0x24 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `%', 0x25 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `&', 0x26 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x27 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `(', 0x28 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `)', 0x29 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `*', 0x2a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `+', 0x2b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `,', 0x2c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `-', 0x2d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `.', 0x2e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `/', 0x2f */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `0', 0x30 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `1', 0x31 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `2', 0x32 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `3', 0x33 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `4', 0x34 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `5', 0x35 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `6', 0x36 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `7', 0x37 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `8', 0x38 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `9', 0x39 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `:', 0x3a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `;', 0x3b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `<', 0x3c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `=', 0x3d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `>', 0x3e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `?', 0x3f */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `@', 0x40 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `A', 0x41 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `B', 0x42 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `C', 0x43 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `D', 0x44 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `E', 0x45 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `F', 0x46 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `G', 0x47 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `H', 0x48 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `I', 0x49 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `J', 0x4a */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `K', 0x4b */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `L', 0x4c */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `M', 0x4d */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `N', 0x4e */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `O', 0x4f */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `P', 0x50 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Q', 0x51 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `R', 0x52 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `S', 0x53 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `T', 0x54 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `U', 0x55 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `V', 0x56 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `W', 0x57 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `X', 0x58 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Y', 0x59 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Z', 0x5a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `[', 0x5b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x5c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `]', 0x5d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `^', 0x5e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `_', 0x5f */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x60 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `a', 0x61 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `b', 0x62 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `c', 0x63 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `d', 0x64 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `e', 0x65 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `f', 0x66 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `g', 0x67 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `h', 0x68 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `i', 0x69 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `j', 0x6a */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `k', 0x6b */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `l', 0x6c */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `m', 0x6d */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `n', 0x6e */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `o', 0x6f */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `p', 0x70 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `q', 0x71 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `r', 0x72 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `s', 0x73 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `t', 0x74 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `u', 0x75 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `v', 0x76 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `w', 0x77 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `x', 0x78 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `y', 0x79 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `z', 0x7a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `{', 0x7b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `|', 0x7c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `}', 0x7d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `~', 0x7e */ + __dj_ISCNTRL, /* 0x7f */ + 0, /* 0x80 */ + 0, /* 0x81 */ + 0, /* 0x82 */ + 0, /* 0x83 */ + 0, /* 0x84 */ + 0, /* 0x85 */ + 0, /* 0x86 */ + 0, /* 0x87 */ + 0, /* 0x88 */ + 0, /* 0x89 */ + 0, /* 0x8a */ + 0, /* 0x8b */ + 0, /* 0x8c */ + 0, /* 0x8d */ + 0, /* 0x8e */ + 0, /* 0x8f */ + 0, /* 0x90 */ + 0, /* 0x91 */ + 0, /* 0x92 */ + 0, /* 0x93 */ + 0, /* 0x94 */ + 0, /* 0x95 */ + 0, /* 0x96 */ + 0, /* 0x97 */ + 0, /* 0x98 */ + 0, /* 0x99 */ + 0, /* 0x9a */ + 0, /* 0x9b */ + 0, /* 0x9c */ + 0, /* 0x9d */ + 0, /* 0x9e */ + 0, /* 0x9f */ + 0, /* 0xa0 */ + 0, /* 0xa1 */ + 0, /* 0xa2 */ + 0, /* 0xa3 */ + 0, /* 0xa4 */ + 0, /* 0xa5 */ + 0, /* 0xa6 */ + 0, /* 0xa7 */ + 0, /* 0xa8 */ + 0, /* 0xa9 */ + 0, /* 0xaa */ + 0, /* 0xab */ + 0, /* 0xac */ + 0, /* 0xad */ + 0, /* 0xae */ + 0, /* 0xaf */ + 0, /* 0xb0 */ + 0, /* 0xb1 */ + 0, /* 0xb2 */ + 0, /* 0xb3 */ + 0, /* 0xb4 */ + 0, /* 0xb5 */ + 0, /* 0xb6 */ + 0, /* 0xb7 */ + 0, /* 0xb8 */ + 0, /* 0xb9 */ + 0, /* 0xba */ + 0, /* 0xbb */ + 0, /* 0xbc */ + 0, /* 0xbd */ + 0, /* 0xbe */ + 0, /* 0xbf */ + 0, /* 0xc0 */ + 0, /* 0xc1 */ + 0, /* 0xc2 */ + 0, /* 0xc3 */ + 0, /* 0xc4 */ + 0, /* 0xc5 */ + 0, /* 0xc6 */ + 0, /* 0xc7 */ + 0, /* 0xc8 */ + 0, /* 0xc9 */ + 0, /* 0xca */ + 0, /* 0xcb */ + 0, /* 0xcc */ + 0, /* 0xcd */ + 0, /* 0xce */ + 0, /* 0xcf */ + 0, /* 0xd0 */ + 0, /* 0xd1 */ + 0, /* 0xd2 */ + 0, /* 0xd3 */ + 0, /* 0xd4 */ + 0, /* 0xd5 */ + 0, /* 0xd6 */ + 0, /* 0xd7 */ + 0, /* 0xd8 */ + 0, /* 0xd9 */ + 0, /* 0xda */ + 0, /* 0xdb */ + 0, /* 0xdc */ + 0, /* 0xdd */ + 0, /* 0xde */ + 0, /* 0xdf */ + 0, /* 0xe0 */ + 0, /* 0xe1 */ + 0, /* 0xe2 */ + 0, /* 0xe3 */ + 0, /* 0xe4 */ + 0, /* 0xe5 */ + 0, /* 0xe6 */ + 0, /* 0xe7 */ + 0, /* 0xe8 */ + 0, /* 0xe9 */ + 0, /* 0xea */ + 0, /* 0xeb */ + 0, /* 0xec */ + 0, /* 0xed */ + 0, /* 0xee */ + 0, /* 0xef */ + 0, /* 0xf0 */ + 0, /* 0xf1 */ + 0, /* 0xf2 */ + 0, /* 0xf3 */ + 0, /* 0xf4 */ + 0, /* 0xf5 */ + 0, /* 0xf6 */ + 0, /* 0xf7 */ + 0, /* 0xf8 */ + 0, /* 0xf9 */ + 0, /* 0xfa */ + 0, /* 0xfb */ + 0, /* 0xfc */ + 0, /* 0xfd */ + 0, /* 0xfe */ + 0, /* 0xff */ +}; diff --git a/reactos/lib/crtdll/ctype/ct_lower.c b/reactos/lib/crtdll/ctype/ct_lower.c new file mode 100644 index 00000000000..2f992ce76e2 --- /dev/null +++ b/reactos/lib/crtdll/ctype/ct_lower.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +unsigned char __dj_ctype_tolower[] = { + 0x00, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, + 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, + 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, + 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, + 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, + 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, + 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, + 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, + 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, + 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, + 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, + 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, + 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, + 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, + 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, + 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, + 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, + 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, + 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, + 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, + 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, + 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, + 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, + 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, + 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff +}; diff --git a/reactos/lib/crtdll/ctype/ct_upper.c b/reactos/lib/crtdll/ctype/ct_upper.c new file mode 100644 index 00000000000..5926201973c --- /dev/null +++ b/reactos/lib/crtdll/ctype/ct_upper.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +unsigned char __dj_ctype_toupper[] = { + 0x00, + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, + 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, + 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, + 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, + 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, + 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, + 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, + 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, + 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, + 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, + 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, + 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, + 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, + 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, + 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, + 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, + 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, + 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, + 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, + 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, + 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, + 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, + 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, + 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, + 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff +}; diff --git a/reactos/lib/crtdll/ctype/isalnum.c b/reactos/lib/crtdll/ctype/isalnum.c new file mode 100644 index 00000000000..4c1afc9646c --- /dev/null +++ b/reactos/lib/crtdll/ctype/isalnum.c @@ -0,0 +1,16 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/putch.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include + +#undef isalnum +int isalnum(int c) +{ + return ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9')); +} diff --git a/reactos/lib/crtdll/ctype/isalpha.c b/reactos/lib/crtdll/ctype/isalpha.c new file mode 100644 index 00000000000..bbca268a25a --- /dev/null +++ b/reactos/lib/crtdll/ctype/isalpha.c @@ -0,0 +1,17 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/putch.c + * PURPOSE: Checks if a character is alphanumeric + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include + +#undef isalpha +int isalpha(int c) +{ + return (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z'); +} diff --git a/reactos/lib/crtdll/ctype/isascii.c b/reactos/lib/crtdll/ctype/isascii.c new file mode 100644 index 00000000000..1fbfc3f5b3b --- /dev/null +++ b/reactos/lib/crtdll/ctype/isascii.c @@ -0,0 +1,30 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/getch.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include + +#undef isascii +int isascii(int c) +{ + return ( (unsigned)(c) <0x80 ) ; +} + +int __isascii(int c) +{ + return ( (unsigned)(c) <0x80 ) ; +} + + + + + + + + diff --git a/reactos/lib/crtdll/ctype/iscntrl.c b/reactos/lib/crtdll/ctype/iscntrl.c new file mode 100644 index 00000000000..78739e25c49 --- /dev/null +++ b/reactos/lib/crtdll/ctype/iscntrl.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef iscntrl +int iscntrl(int c) +{ + return ((c >=0x00 && c <= 0x1f) || c == 0x7f) ; +} diff --git a/reactos/lib/crtdll/ctype/iscsym.c b/reactos/lib/crtdll/ctype/iscsym.c new file mode 100644 index 00000000000..8a2d6aff730 --- /dev/null +++ b/reactos/lib/crtdll/ctype/iscsym.c @@ -0,0 +1,40 @@ + +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/ctype/iscsym.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include + +#undef iscsym +int +iscsym (int c) +{ + return __iscsym(c); +} + +int +__iscsym (int c) +{ + return (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || ( c == '_' ); +} + +#undef iscsymf +int +iscsymf (int c) +{ + return __iscsymf(c); +} + +int +__iscsymf (int c) +{ + return (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || ( c == '_' ); +} + + diff --git a/reactos/lib/crtdll/ctype/isctype.c b/reactos/lib/crtdll/ctype/isctype.c new file mode 100644 index 00000000000..a8867a8dd29 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isctype.c @@ -0,0 +1,290 @@ + +#include + + + +#define __dj_ISUPPER 0x1 +#define __dj_ISLOWER 0x2 +#define __dj_ISDIGIT 0x4 +#define __dj_ISSPACE 0x8 +#define __dj_ISPUNCT 0x10 +#define __dj_ISCNTRL 0x20 +#define __dj_ISBLANK 0x40 +#define __dj_ISXDIGIT 0x80 +#define __dj_ISPRINT (__dj_ISBLANK|__dj_ISPUNCT|__dj_ISUPPER|__dj_ISLOWER|__dj_ISDIGIT) +#define __dj_ISALNUM (__dj_ISUPPER|__dj_ISLOWER|__dj_ISDIGIT) +#define __dj_ISGRAPH (__dj_ISPUNCT|__dj_ISUPPER|__dj_ISLOWER|__dj_ISDIGIT) +#define __dj_ISALPHA (0x0100|__dj_ISUPPER|__dj_ISLOWER) + + +unsigned short __dj_ctype_flags[] = { + 0, /* CTRL+?, 0xffff */ + __dj_ISCNTRL, /* CTRL+@, 0x00 */ + __dj_ISCNTRL, /* CTRL+A, 0x01 */ + __dj_ISCNTRL, /* CTRL+B, 0x02 */ + __dj_ISCNTRL, /* CTRL+C, 0x03 */ + __dj_ISCNTRL, /* CTRL+D, 0x04 */ + __dj_ISCNTRL, /* CTRL+E, 0x05 */ + __dj_ISCNTRL, /* CTRL+F, 0x06 */ + __dj_ISCNTRL, /* CTRL+G, 0x07 */ + __dj_ISCNTRL, /* CTRL+H, 0x08 */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+I, 0x09 */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+J, 0x0a */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+K, 0x0b */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+L, 0x0c */ + __dj_ISCNTRL | __dj_ISSPACE, /* CTRL+M, 0x0d */ + __dj_ISCNTRL, /* CTRL+N, 0x0e */ + __dj_ISCNTRL, /* CTRL+O, 0x0f */ + __dj_ISCNTRL, /* CTRL+P, 0x10 */ + __dj_ISCNTRL, /* CTRL+Q, 0x11 */ + __dj_ISCNTRL, /* CTRL+R, 0x12 */ + __dj_ISCNTRL, /* CTRL+S, 0x13 */ + __dj_ISCNTRL, /* CTRL+T, 0x14 */ + __dj_ISCNTRL, /* CTRL+U, 0x15 */ + __dj_ISCNTRL, /* CTRL+V, 0x16 */ + __dj_ISCNTRL, /* CTRL+W, 0x17 */ + __dj_ISCNTRL, /* CTRL+X, 0x18 */ + __dj_ISCNTRL, /* CTRL+Y, 0x19 */ + __dj_ISCNTRL, /* CTRL+Z, 0x1a */ + __dj_ISCNTRL, /* CTRL+[, 0x1b */ + __dj_ISCNTRL, /* CTRL+\, 0x1c */ + __dj_ISCNTRL, /* CTRL+], 0x1d */ + __dj_ISCNTRL, /* CTRL+^, 0x1e */ + __dj_ISCNTRL, /* CTRL+_, 0x1f */ + __dj_ISPRINT | __dj_ISSPACE, /* ` ', 0x20 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `!', 0x21 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x22 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `#', 0x23 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `$', 0x24 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `%', 0x25 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `&', 0x26 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x27 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `(', 0x28 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `)', 0x29 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `*', 0x2a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `+', 0x2b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `,', 0x2c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `-', 0x2d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `.', 0x2e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `/', 0x2f */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `0', 0x30 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `1', 0x31 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `2', 0x32 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `3', 0x33 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `4', 0x34 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `5', 0x35 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `6', 0x36 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `7', 0x37 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `8', 0x38 */ + __dj_ISALNUM | __dj_ISDIGIT | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISXDIGIT, /* `9', 0x39 */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `:', 0x3a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `;', 0x3b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `<', 0x3c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `=', 0x3d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `>', 0x3e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `?', 0x3f */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `@', 0x40 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `A', 0x41 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `B', 0x42 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `C', 0x43 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `D', 0x44 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `E', 0x45 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER | __dj_ISXDIGIT, /* `F', 0x46 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `G', 0x47 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `H', 0x48 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `I', 0x49 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `J', 0x4a */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `K', 0x4b */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `L', 0x4c */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `M', 0x4d */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `N', 0x4e */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `O', 0x4f */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `P', 0x50 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Q', 0x51 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `R', 0x52 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `S', 0x53 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `T', 0x54 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `U', 0x55 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `V', 0x56 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `W', 0x57 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `X', 0x58 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Y', 0x59 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISPRINT | __dj_ISUPPER, /* `Z', 0x5a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `[', 0x5b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x5c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `]', 0x5d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `^', 0x5e */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `_', 0x5f */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* 0x60 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `a', 0x61 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `b', 0x62 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `c', 0x63 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `d', 0x64 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `e', 0x65 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT | __dj_ISXDIGIT, /* `f', 0x66 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `g', 0x67 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `h', 0x68 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `i', 0x69 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `j', 0x6a */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `k', 0x6b */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `l', 0x6c */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `m', 0x6d */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `n', 0x6e */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `o', 0x6f */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `p', 0x70 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `q', 0x71 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `r', 0x72 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `s', 0x73 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `t', 0x74 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `u', 0x75 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `v', 0x76 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `w', 0x77 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `x', 0x78 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `y', 0x79 */ + __dj_ISALNUM | __dj_ISALPHA | __dj_ISGRAPH | __dj_ISLOWER | __dj_ISPRINT, /* `z', 0x7a */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `{', 0x7b */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `|', 0x7c */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `}', 0x7d */ + __dj_ISGRAPH | __dj_ISPRINT | __dj_ISPUNCT, /* `~', 0x7e */ + __dj_ISCNTRL, /* 0x7f */ + 0, /* 0x80 */ + 0, /* 0x81 */ + 0, /* 0x82 */ + 0, /* 0x83 */ + 0, /* 0x84 */ + 0, /* 0x85 */ + 0, /* 0x86 */ + 0, /* 0x87 */ + 0, /* 0x88 */ + 0, /* 0x89 */ + 0, /* 0x8a */ + 0, /* 0x8b */ + 0, /* 0x8c */ + 0, /* 0x8d */ + 0, /* 0x8e */ + 0, /* 0x8f */ + 0, /* 0x90 */ + 0, /* 0x91 */ + 0, /* 0x92 */ + 0, /* 0x93 */ + 0, /* 0x94 */ + 0, /* 0x95 */ + 0, /* 0x96 */ + 0, /* 0x97 */ + 0, /* 0x98 */ + 0, /* 0x99 */ + 0, /* 0x9a */ + 0, /* 0x9b */ + 0, /* 0x9c */ + 0, /* 0x9d */ + 0, /* 0x9e */ + 0, /* 0x9f */ + 0, /* 0xa0 */ + 0, /* 0xa1 */ + 0, /* 0xa2 */ + 0, /* 0xa3 */ + 0, /* 0xa4 */ + 0, /* 0xa5 */ + 0, /* 0xa6 */ + 0, /* 0xa7 */ + 0, /* 0xa8 */ + 0, /* 0xa9 */ + 0, /* 0xaa */ + 0, /* 0xab */ + 0, /* 0xac */ + 0, /* 0xad */ + 0, /* 0xae */ + 0, /* 0xaf */ + 0, /* 0xb0 */ + 0, /* 0xb1 */ + 0, /* 0xb2 */ + 0, /* 0xb3 */ + 0, /* 0xb4 */ + 0, /* 0xb5 */ + 0, /* 0xb6 */ + 0, /* 0xb7 */ + 0, /* 0xb8 */ + 0, /* 0xb9 */ + 0, /* 0xba */ + 0, /* 0xbb */ + 0, /* 0xbc */ + 0, /* 0xbd */ + 0, /* 0xbe */ + 0, /* 0xbf */ + 0, /* 0xc0 */ + 0, /* 0xc1 */ + 0, /* 0xc2 */ + 0, /* 0xc3 */ + 0, /* 0xc4 */ + 0, /* 0xc5 */ + 0, /* 0xc6 */ + 0, /* 0xc7 */ + 0, /* 0xc8 */ + 0, /* 0xc9 */ + 0, /* 0xca */ + 0, /* 0xcb */ + 0, /* 0xcc */ + 0, /* 0xcd */ + 0, /* 0xce */ + 0, /* 0xcf */ + 0, /* 0xd0 */ + 0, /* 0xd1 */ + 0, /* 0xd2 */ + 0, /* 0xd3 */ + 0, /* 0xd4 */ + 0, /* 0xd5 */ + 0, /* 0xd6 */ + 0, /* 0xd7 */ + 0, /* 0xd8 */ + 0, /* 0xd9 */ + 0, /* 0xda */ + 0, /* 0xdb */ + 0, /* 0xdc */ + 0, /* 0xdd */ + 0, /* 0xde */ + 0, /* 0xdf */ + 0, /* 0xe0 */ + 0, /* 0xe1 */ + 0, /* 0xe2 */ + 0, /* 0xe3 */ + 0, /* 0xe4 */ + 0, /* 0xe5 */ + 0, /* 0xe6 */ + 0, /* 0xe7 */ + 0, /* 0xe8 */ + 0, /* 0xe9 */ + 0, /* 0xea */ + 0, /* 0xeb */ + 0, /* 0xec */ + 0, /* 0xed */ + 0, /* 0xee */ + 0, /* 0xef */ + 0, /* 0xf0 */ + 0, /* 0xf1 */ + 0, /* 0xf2 */ + 0, /* 0xf3 */ + 0, /* 0xf4 */ + 0, /* 0xf5 */ + 0, /* 0xf6 */ + 0, /* 0xf7 */ + 0, /* 0xf8 */ + 0, /* 0xf9 */ + 0, /* 0xfa */ + 0, /* 0xfb */ + 0, /* 0xfc */ + 0, /* 0xfd */ + 0, /* 0xfe */ + 0, /* 0xff */ +}; + + + +int _isctype(int c, int t) +{ + + return (__dj_ctype_flags[(c & 0xFF)]&t == t ); +} + +unsigned short *_pctype = __dj_ctype_flags; + +int __mb_cur_max = 2; \ No newline at end of file diff --git a/reactos/lib/crtdll/ctype/isdigit.c b/reactos/lib/crtdll/ctype/isdigit.c new file mode 100644 index 00000000000..e8228959eaa --- /dev/null +++ b/reactos/lib/crtdll/ctype/isdigit.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isdigit +int isdigit(int c) +{ + return (c >= '0' && c <= '9'); +} diff --git a/reactos/lib/crtdll/ctype/isgraph.c b/reactos/lib/crtdll/ctype/isgraph.c new file mode 100644 index 00000000000..be8233f5177 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isgraph.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isgraph +int isgraph(int c) +{ + return 0; +} diff --git a/reactos/lib/crtdll/ctype/islower.c b/reactos/lib/crtdll/ctype/islower.c new file mode 100644 index 00000000000..99e9eea98a0 --- /dev/null +++ b/reactos/lib/crtdll/ctype/islower.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef islower +int islower(int c) +{ + return (c >= 'a' && c <= 'z'); +} diff --git a/reactos/lib/crtdll/ctype/isprint.c b/reactos/lib/crtdll/ctype/isprint.c new file mode 100644 index 00000000000..2e899744237 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isprint.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isprint +int isprint(int c) +{ + return c; +} diff --git a/reactos/lib/crtdll/ctype/ispunct.c b/reactos/lib/crtdll/ctype/ispunct.c new file mode 100644 index 00000000000..b3e8399c7fd --- /dev/null +++ b/reactos/lib/crtdll/ctype/ispunct.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef ispunct +int ispunct(int c) +{ + return (c == '.'); +} diff --git a/reactos/lib/crtdll/ctype/isspace.c b/reactos/lib/crtdll/ctype/isspace.c new file mode 100644 index 00000000000..605a86ebaa6 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isspace.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isspace +int isspace(int c) +{ + return ( c == ' ' || c == '\t' ); +} diff --git a/reactos/lib/crtdll/ctype/isupper.c b/reactos/lib/crtdll/ctype/isupper.c new file mode 100644 index 00000000000..2b1c09f0514 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isupper.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isupper +int isupper(int c) +{ + return (c >= 'A' && c <= 'Z' ); +} diff --git a/reactos/lib/crtdll/ctype/isxdigit.c b/reactos/lib/crtdll/ctype/isxdigit.c new file mode 100644 index 00000000000..3123107eae4 --- /dev/null +++ b/reactos/lib/crtdll/ctype/isxdigit.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef isxdigit +int isxdigit(int c) +{ + return (c >= 'A' && c <= 'F') || (c >= 'a' && c <= 'f') || ( c >= '0' && c >= '9' ); +} diff --git a/reactos/lib/crtdll/ctype/toascii.c b/reactos/lib/crtdll/ctype/toascii.c new file mode 100644 index 00000000000..b7d4a6e9fb1 --- /dev/null +++ b/reactos/lib/crtdll/ctype/toascii.c @@ -0,0 +1,14 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +#undef toascii +int toascii(int c) +{ + return (c); +} + +int __toascii(int c) +{ + return (c); +} diff --git a/reactos/lib/crtdll/ctype/tolower.c b/reactos/lib/crtdll/ctype/tolower.c new file mode 100644 index 00000000000..760a8b98253 --- /dev/null +++ b/reactos/lib/crtdll/ctype/tolower.c @@ -0,0 +1,7 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#undef tolower +int tolower(int c) +{ + return (c >= 'A' && c <= 'Z') ? c - ( 'A' - 'a' ) : c; +} diff --git a/reactos/lib/crtdll/ctype/toupper.c b/reactos/lib/crtdll/ctype/toupper.c new file mode 100644 index 00000000000..c0eaefbb8a7 --- /dev/null +++ b/reactos/lib/crtdll/ctype/toupper.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef toupper +int toupper(int c) +{ + return (c >= 'a' && c <= 'z') ? c + 'A' - 'a' : c; +} diff --git a/reactos/lib/crtdll/direct/chdir.c b/reactos/lib/crtdll/direct/chdir.c new file mode 100644 index 00000000000..39e651a5c3e --- /dev/null +++ b/reactos/lib/crtdll/direct/chdir.c @@ -0,0 +1,25 @@ +#include +#include +#include + +char _SetCurrentDirectory(char *dir); +int _GetCurrentDirectory(int count,char *buffer); + +#undef chdir +int chdir( const char *_path ) +{ + return _chdir(_path); +} + +int _chdir( const char *_path ) +{ + if ( _path[1] == ':') + _chdrive(tolower(_path[0] - 'a')+1); + if ( !SetCurrentDirectory((char *)_path) ) + return -1; + + return 0; +} + + + diff --git a/reactos/lib/crtdll/direct/chdrive.c b/reactos/lib/crtdll/direct/chdrive.c new file mode 100644 index 00000000000..4f3b39b0806 --- /dev/null +++ b/reactos/lib/crtdll/direct/chdrive.c @@ -0,0 +1,25 @@ +#include +#include +#include + +int cur_drive = 0; + + + +int _chdrive( int drive ) +{ + char d[3]; + if (!( drive >= 1 && drive <= 26 )) + return -1; + + if ( cur_drive != drive ) { + cur_drive = drive; + d[0] = toupper(cur_drive + '@'); + d[1] = ':'; + d[2] = 0; + SetCurrentDirectory(d); + } + + + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/direct/getcwd.c b/reactos/lib/crtdll/direct/getcwd.c new file mode 100644 index 00000000000..6012f7a4414 --- /dev/null +++ b/reactos/lib/crtdll/direct/getcwd.c @@ -0,0 +1,33 @@ +#include +#include +#include + + + +#undef getcwd +char *getcwd( char *buffer, int maxlen ) +{ + return _getcwd(buffer,maxlen); +} + +char *_getcwd( char *buffer, int maxlen ) +{ + char *cwd; + int len; + if ( buffer == NULL ) { + cwd = malloc(MAX_PATH); + len = MAX_PATH; + } + else { + cwd = buffer; + len = maxlen; + } + + + if ( GetCurrentDirectory(len,cwd) == 0 ) + return NULL; + + + return cwd; +} + diff --git a/reactos/lib/crtdll/direct/getdfree.c b/reactos/lib/crtdll/direct/getdfree.c new file mode 100644 index 00000000000..333229339a0 --- /dev/null +++ b/reactos/lib/crtdll/direct/getdfree.c @@ -0,0 +1,19 @@ +#include +#include +#include + + +unsigned int _getdiskfree(unsigned int _drive, struct _diskfree_t *_diskspace) +{ + char RootPathName[10]; + RootPathName[0] = toupper(_drive +'@'); + RootPathName[1] = ':'; + RootPathName[2] = '\\'; + RootPathName[3] = 0; + if ( _diskspace == NULL ) + return 0; + + if ( !GetDiskFreeSpaceA(RootPathName,&_diskspace->sectors_per_cluster,&_diskspace->bytes_per_sector,&_diskspace->avail_clusters,&_diskspace->total_clusters ) ) + return 0; + return _diskspace->avail_clusters; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/direct/getdrive.c b/reactos/lib/crtdll/direct/getdrive.c new file mode 100644 index 00000000000..d2ebb96c739 --- /dev/null +++ b/reactos/lib/crtdll/direct/getdrive.c @@ -0,0 +1,18 @@ +#include +#include + +extern int cur_drive; + + + +int _getdrive( void ) +{ + char Buffer[MAX_PATH]; + + if ( cur_drive == 0 ) { + GetCurrentDirectory(MAX_PATH,Buffer); + cur_drive = toupper(Buffer[0] - '@'); + } + + return cur_drive; +} diff --git a/reactos/lib/crtdll/direct/mkdir.c b/reactos/lib/crtdll/direct/mkdir.c new file mode 100644 index 00000000000..059eab6e41a --- /dev/null +++ b/reactos/lib/crtdll/direct/mkdir.c @@ -0,0 +1,14 @@ +#include +#include + +#undef mkdir +int mkdir( const char *_path ) +{ + return _mkdir(_path); +} +int _mkdir( const char *_path ) +{ + if (!CreateDirectoryA(_path,NULL)) + return -1; + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/direct/rmdir.c b/reactos/lib/crtdll/direct/rmdir.c new file mode 100644 index 00000000000..8890006dac8 --- /dev/null +++ b/reactos/lib/crtdll/direct/rmdir.c @@ -0,0 +1,15 @@ +#include +#include + +#undef rmdir +int rmdir( const char *_path ) +{ + return _rmdir(_path); +} + +int _rmdir( const char *_path ) +{ + if (!RemoveDirectoryA(_path)) + return -1; + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/dirent/dirent.c b/reactos/lib/crtdll/dirent/dirent.c new file mode 100644 index 00000000000..54104d449d3 --- /dev/null +++ b/reactos/lib/crtdll/dirent/dirent.c @@ -0,0 +1,316 @@ +/* + * dirent.c + * + * Derived from DIRLIB.C by Matt J. Weinstein + * This note appears in the DIRLIB.H + * DIRLIB.H by M. J. Weinstein Released to public domain 1-Jan-89 + * + * Updated by Jeremy Bettis + * Significantly revised and rewinddir, seekdir and telldir added by Colin + * Peters + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +#include +/* #include */ +#include +#include +#include +#include +#include + +#include + +#define SUFFIX "*" +#define SLASH "\\" +#define streq(a,b) (strcmp(a,b)==0) + +/* + * opendir + * + * Returns a pointer to a DIR structure appropriately filled in to begin + * searching a directory. + */ +DIR* +opendir(const char* szPath) +{ + DIR* nd; + struct stat statDir; + + errno = 0; + + if (!szPath) + { + errno = EFAULT; + return (DIR*) 0; + } + + if (szPath[0] == '\0') + { + errno = ENOTDIR; + return (DIR*) 0; + } + + /* Attempt to determine if the given path really is a directory. */ + if (_stat (szPath, &statDir)) + { + /* Error, stat should have set an error value. */ + return (DIR*) 0; + } + + if (!S_ISDIR(statDir.st_mode)) + { + /* Error, stat reports not a directory. */ + errno = ENOTDIR; + return (DIR*) 0; + } + + /* Allocate enough space to store DIR structure and the complete + * directory path given. */ + nd = (DIR*) malloc (sizeof(DIR) + strlen(szPath) + strlen(SLASH) + + strlen(SUFFIX)); + + if (!nd) + { + /* Error, out of memory. */ + errno = ENOMEM; + return (DIR*) 0; + } + + /* Create the search expression. */ + strcpy(nd->dd_name, szPath); + + /* Add on a slash if the path does not end with one. */ + if (nd->dd_name[0] != '\0' && + nd->dd_name[strlen(nd->dd_name)-1] != '/' && + nd->dd_name[strlen(nd->dd_name)-1] != '\\') + { + strcat(nd->dd_name, SLASH); + } + + /* Add on the search pattern */ + strcat(nd->dd_name, SUFFIX); + + /* Initialize handle to -1 so that a premature closedir doesn't try + * to call _findclose on it. */ + nd->dd_handle = -1; + + /* Initialize the status. */ + nd->dd_stat = 0; + + /* Initialize the dirent structure. ino and reclen are invalid under + * Win32, and name simply points at the appropriate part of the + * findfirst_t structure. */ + nd->dd_dir.d_ino = 0; + nd->dd_dir.d_reclen = 0; + nd->dd_dir.d_namlen = 0; + nd->dd_dir.d_name = nd->dd_dta.name; + + return nd; +} + + +/* + * readdir + * + * Return a pointer to a dirent structure filled with the information on the + * next entry in the directory. + */ +struct dirent * +readdir( DIR *dirp ) +{ + errno = 0; + + /* Check for valid DIR struct. */ + if (!dirp) + { + errno = EFAULT; + return (struct dirent*) 0; + } + + if (dirp->dd_dir.d_name != dirp->dd_dta.name) + { + /* The structure does not seem to be set up correctly. */ + errno = EINVAL; + return (struct dirent*) 0; + } + + if (dirp->dd_stat < 0) + { + /* We have already returned all files in the directory + * (or the structure has an invalid dd_stat). */ + return (struct dirent *) 0; + } + else if (dirp->dd_stat == 0) + { + /* We haven't started the search yet. */ + /* Start the search */ + dirp->dd_handle = _findfirst(dirp->dd_name, &(dirp->dd_dta)); + + if (dirp->dd_handle == -1) + { + /* Whoops! Seems there are no files in that + * directory. */ + dirp->dd_stat = -1; + } + else + { + dirp->dd_stat = 1; + } + } + else + { + /* Get the next search entry. */ + if (_findnext(dirp->dd_handle, &(dirp->dd_dta))) + { + /* We are off the end or otherwise error. */ + _findclose (dirp->dd_handle); + dirp->dd_handle = -1; + dirp->dd_stat = -1; + } + else + { + /* Update the status to indicate the correct + * number. */ + dirp->dd_stat++; + } + } + + if (dirp->dd_stat > 0) + { + /* Successfully got an entry. Everything about the file is + * already appropriately filled in except the length of the + * file name. */ + dirp->dd_dir.d_namlen = strlen(dirp->dd_dir.d_name); + return &dirp->dd_dir; + } + + return (struct dirent*) 0; +} + + +/* + * closedir + * + * Frees up resources allocated by opendir. + */ +int +closedir (DIR* dirp) +{ + int rc; + + errno = 0; + rc = 0; + + if (!dirp) + { + errno = EFAULT; + return -1; + } + + if (dirp->dd_handle != -1) + { + rc = _findclose(dirp->dd_handle); + } + + /* Delete the dir structure. */ + free (dirp); + + return rc; +} + +/* + * rewinddir + * + * Return to the beginning of the directory "stream". We simply call findclose + * and then reset things like an opendir. + */ +void +rewinddir (DIR* dirp) +{ + errno = 0; + + if (!dirp) + { + errno = EFAULT; + return; + } + + if (dirp->dd_handle != -1) + { + _findclose(dirp->dd_handle); + } + + dirp->dd_handle = -1; + dirp->dd_stat = 0; +} + +/* + * telldir + * + * Returns the "position" in the "directory stream" which can be used with + * seekdir to go back to an old entry. We simply return the value in stat. + */ +long +telldir (DIR* dirp) +{ + errno = 0; + + if (!dirp) + { + errno = EFAULT; + return -1; + } + return dirp->dd_stat; +} + +/* + * seekdir + * + * Seek to an entry previously returned by telldir. We rewind the directory + * and call readdir repeatedly until either dd_stat is the position number + * or -1 (off the end). This is not perfect, in that the directory may + * have changed while we weren't looking. But that is probably the case with + * any such system. + */ +void +seekdir (DIR* dirp, long lPos) +{ + errno = 0; + + if (!dirp) + { + errno = EFAULT; + return; + } + + if (lPos < -1) + { + /* Seeking to an invalid position. */ + errno = EINVAL; + return; + } + else if (lPos == -1) + { + /* Seek past end. */ + if (dirp->dd_handle != -1) + { + _findclose (dirp->dd_handle); + } + dirp->dd_handle = -1; + dirp->dd_stat = -1; + } + else + { + /* Rewind and read forward to the appropriate index. */ + rewinddir (dirp); + + while ((dirp->dd_stat < lPos) && readdir(dirp)) + ; + } +} + diff --git a/reactos/lib/crtdll/float/fpreset.c b/reactos/lib/crtdll/float/fpreset.c new file mode 100644 index 00000000000..384ecfcd7a7 --- /dev/null +++ b/reactos/lib/crtdll/float/fpreset.c @@ -0,0 +1,7 @@ +#include + +void _fpreset( void ) +{ + return; +} + diff --git a/reactos/lib/crtdll/io/access.c b/reactos/lib/crtdll/io/access.c new file mode 100644 index 00000000000..bcc65527abf --- /dev/null +++ b/reactos/lib/crtdll/io/access.c @@ -0,0 +1,33 @@ +#include +#include + +#define F_OK 0x01 +#define R_OK 0x02 +#define W_OK 0x04 +#define X_OK 0x08 +#define D_OK 0x10 + +int access(const char *_path, int _amode) +{ + return _access(_path,_amode); +} + +int _access( const char *_path, int _amode ) +{ + DWORD Attributes = GetFileAttributesA(_path); + + if ( Attributes == -1 ) + return -1; + + if ( _amode & W_OK == W_OK ) { + if ( (Attributes & FILE_ATTRIBUTE_READONLY) == FILE_ATTRIBUTE_READONLY ) + return -1; + } + if ( _amode & D_OK == D_OK ) { + if ( (Attributes & FILE_ATTRIBUTE_DIRECTORY) != FILE_ATTRIBUTE_DIRECTORY ) + return 0; + } + + return 0; + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/close.c b/reactos/lib/crtdll/io/close.c new file mode 100644 index 00000000000..d2fa19b63a7 --- /dev/null +++ b/reactos/lib/crtdll/io/close.c @@ -0,0 +1,16 @@ +#include +#include +#include + + +int close(int _fd) +{ + return _close(_fd); +} + +int _close(int _fd) +{ + CloseHandle(filehnd(_fd)); + return __fileno_close(_fd); + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/create.c b/reactos/lib/crtdll/io/create.c new file mode 100644 index 00000000000..bd382e9218b --- /dev/null +++ b/reactos/lib/crtdll/io/create.c @@ -0,0 +1,8 @@ +#include +#include + +#undef creat +int creat(const char *filename, int mode) +{ + return open(filename,_O_CREAT|_O_TRUNC,mode); +} diff --git a/reactos/lib/crtdll/io/dup.c b/reactos/lib/crtdll/io/dup.c new file mode 100644 index 00000000000..b0168a8e927 --- /dev/null +++ b/reactos/lib/crtdll/io/dup.c @@ -0,0 +1,13 @@ +#include +#include + +#undef dup +int dup( int handle ) +{ + return _dup(handle); +} + +int _dup( int handle ) +{ + return _open_osfhandle(filehnd(handle), 0666); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/dup2.c b/reactos/lib/crtdll/io/dup2.c new file mode 100644 index 00000000000..504338848b7 --- /dev/null +++ b/reactos/lib/crtdll/io/dup2.c @@ -0,0 +1,14 @@ +#include +#include + +#undef dup2 +int dup2( int handle1, int handle2 ) +{ + return _dup2(handle1,handle2); +} + + +int _dup2( int handle1, int handle2 ) +{ + return __fileno_dup2( handle1, handle2 ); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/find.c b/reactos/lib/crtdll/io/find.c new file mode 100644 index 00000000000..841541cac96 --- /dev/null +++ b/reactos/lib/crtdll/io/find.c @@ -0,0 +1,253 @@ +#include +#include +#include +#include + +//UnixTimeToFileTime +//FileTimeToUnixTime +/* + * DOS file system functions + * + * Copyright 1993 Erik Bos + * Copyright 1996 Alexandre Julliard + */ + + +void UnixTimeToFileTime( time_t unix_time, FILETIME *filetime, DWORD remainder ); +time_t FileTimeToUnixTime( const FILETIME *filetime, DWORD *remainder ); + + +long _findfirst(char *_name, struct _finddata_t *result) +{ + WIN32_FIND_DATA FindFileData; + char dir[MAX_PATH]; + + + long hFindFile; + + if ( _name == NULL || _name[0] == 0 ) { + GetCurrentDirectory(MAX_PATH,dir); + strcat(dir,"\\*.*"); + } + else + strcpy(dir,_name); + hFindFile = FindFirstFile( dir, &FindFileData ); + result->attrib = FindFileData.dwFileAttributes; + + + result->time_create = FileTimeToUnixTime( &FindFileData.ftCreationTime,NULL); + result->time_access = FileTimeToUnixTime( &FindFileData.ftLastAccessTime,NULL); + result->time_write = FileTimeToUnixTime( &FindFileData.ftLastWriteTime,NULL); + result->size = FindFileData.nFileSizeLow; + strncpy(result->name,&FindFileData.cFileName,260); + return hFindFile; +} + +int _findnext(long handle, struct _finddata_t *result) +{ + WIN32_FIND_DATA FindFileData; + if (handle == -1 ) + return -1; + + if ( !FindNextFile(handle, &FindFileData ) ) + return -1; + + result->attrib = FindFileData.dwFileAttributes; + result->time_create = FileTimeToUnixTime( &FindFileData.ftCreationTime,NULL); + result->time_access = FileTimeToUnixTime( &FindFileData.ftLastAccessTime,NULL); + result->time_write = FileTimeToUnixTime( &FindFileData.ftLastWriteTime,NULL); + result->size = FindFileData.nFileSizeLow; + strncpy(result->name,&FindFileData.cFileName,260); + return 0; +} +int _findclose(long handle) +{ + return FindClose(handle); +} + + +/*********************************************************************** + * DOSFS_UnixTimeToFileTime + * + * Convert a Unix time to FILETIME format. + * The FILETIME structure is a 64-bit value representing the number of + * 100-nanosecond intervals since January 1, 1601, 0:00. + * 'remainder' is the nonnegative number of 100-ns intervals + * corresponding to the time fraction smaller than 1 second that + * couldn't be stored in the time_t value. + */ +void UnixTimeToFileTime( time_t unix_time, FILETIME *filetime, + DWORD remainder ) +{ + /* NOTES: + + CONSTANTS: + The time difference between 1 January 1601, 00:00:00 and + 1 January 1970, 00:00:00 is 369 years, plus the leap years + from 1604 to 1968, excluding 1700, 1800, 1900. + This makes (1968 - 1600) / 4 - 3 = 89 leap days, and a total + of 134774 days. + + Any day in that period had 24 * 60 * 60 = 86400 seconds. + + The time difference is 134774 * 86400 * 10000000, which can be written + 116444736000000000 + 27111902 * 2^32 + 3577643008 + 413 * 2^48 + 45534 * 2^32 + 54590 * 2^16 + 32768 + + If you find that these constants are buggy, please change them in all + instances in both conversion functions. + + VERSIONS: + There are two versions, one of them uses long long variables and + is presumably faster but not ISO C. The other one uses standard C + data types and operations but relies on the assumption that negative + numbers are stored as 2's complement (-1 is 0xffff....). If this + assumption is violated, dates before 1970 will not convert correctly. + This should however work on any reasonable architecture where WINE + will run. + + DETAILS: + + Take care not to remove the casts. I have tested these functions + (in both versions) for a lot of numbers. I would be interested in + results on other compilers than GCC. + + The operations have been designed to account for the possibility + of 64-bit time_t in future UNICES. Even the versions without + internal long long numbers will work if time_t only is 64 bit. + A 32-bit shift, which was necessary for that operation, turned out + not to work correctly in GCC, besides giving the warning. So I + used a double 16-bit shift instead. Numbers are in the ISO version + represented by three limbs, the most significant with 32 bit, the + other two with 16 bit each. + + As the modulo-operator % is not well-defined for negative numbers, + negative divisors have been avoided in DOSFS_FileTimeToUnixTime. + + There might be quicker ways to do this in C. Certainly so in + assembler. + + Claus Fischer, fischer@iue.tuwien.ac.at + */ + + + + + unsigned long a0; /* 16 bit, low bits */ + unsigned long a1; /* 16 bit, medium bits */ + unsigned long a2; /* 32 bit, high bits */ + + /* Copy the unix time to a2/a1/a0 */ + a0 = unix_time & 0xffff; + a1 = (unix_time >> 16) & 0xffff; + /* This is obsolete if unix_time is only 32 bits, but it does not hurt. + Do not replace this by >> 32, it gives a compiler warning and it does + not work. */ + a2 = (unix_time >= 0 ? (unix_time >> 16) >> 16 : + ~((~unix_time >> 16) >> 16)); + + /* Multiply a by 10000000 (a = a2/a1/a0) + Split the factor into 10000 * 1000 which are both less than 0xffff. */ + a0 *= 10000; + a1 = a1 * 10000 + (a0 >> 16); + a2 = a2 * 10000 + (a1 >> 16); + a0 &= 0xffff; + a1 &= 0xffff; + + a0 *= 1000; + a1 = a1 * 1000 + (a0 >> 16); + a2 = a2 * 1000 + (a1 >> 16); + a0 &= 0xffff; + a1 &= 0xffff; + + /* Add the time difference and the remainder */ + a0 += 32768 + (remainder & 0xffff); + a1 += 54590 + (remainder >> 16 ) + (a0 >> 16); + a2 += 27111902 + (a1 >> 16); + a0 &= 0xffff; + a1 &= 0xffff; + + /* Set filetime */ + filetime->dwLowDateTime = (a1 << 16) + a0; + filetime->dwHighDateTime = a2; +} + + +/*********************************************************************** + * DOSFS_FileTimeToUnixTime + * + * Convert a FILETIME format to Unix time. + * If not NULL, 'remainder' contains the fractional part of the filetime, + * in the range of [0..9999999] (even if time_t is negative). + */ +time_t FileTimeToUnixTime( const FILETIME *filetime, DWORD *remainder ) +{ + /* Read the comment in the function DOSFS_UnixTimeToFileTime. */ + + unsigned long a0; /* 16 bit, low bits */ + unsigned long a1; /* 16 bit, medium bits */ + unsigned long a2; /* 32 bit, high bits */ + unsigned long r; /* remainder of division */ + unsigned int carry; /* carry bit for subtraction */ + int negative; /* whether a represents a negative value */ + + /* Copy the time values to a2/a1/a0 */ + a2 = (unsigned long)filetime->dwHighDateTime; + a1 = ((unsigned long)filetime->dwLowDateTime ) >> 16; + a0 = ((unsigned long)filetime->dwLowDateTime ) & 0xffff; + + /* Subtract the time difference */ + if (a0 >= 32768 ) a0 -= 32768 , carry = 0; + else a0 += (1 << 16) - 32768 , carry = 1; + + if (a1 >= 54590 + carry) a1 -= 54590 + carry, carry = 0; + else a1 += (1 << 16) - 54590 - carry, carry = 1; + + a2 -= 27111902 + carry; + + /* If a is negative, replace a by (-1-a) */ + negative = (a2 >= ((unsigned long)1) << 31); + if (negative) + { + /* Set a to -a - 1 (a is a2/a1/a0) */ + a0 = 0xffff - a0; + a1 = 0xffff - a1; + a2 = ~a2; + } + + /* Divide a by 10000000 (a = a2/a1/a0), put the rest into r. + Split the divisor into 10000 * 1000 which are both less than 0xffff. */ + a1 += (a2 % 10000) << 16; + a2 /= 10000; + a0 += (a1 % 10000) << 16; + a1 /= 10000; + r = a0 % 10000; + a0 /= 10000; + + a1 += (a2 % 1000) << 16; + a2 /= 1000; + a0 += (a1 % 1000) << 16; + a1 /= 1000; + r += (a0 % 1000) * 10000; + a0 /= 1000; + + /* If a was negative, replace a by (-1-a) and r by (9999999 - r) */ + if (negative) + { + /* Set a to -a - 1 (a is a2/a1/a0) */ + a0 = 0xffff - a0; + a1 = 0xffff - a1; + a2 = ~a2; + + r = 9999999 - r; + } + + if (remainder) *remainder = r; + + /* Do not replace this by << 32, it gives a compiler warning and it does + not work. */ + return ((((time_t)a2) << 16) << 16) + (a1 << 16) + a0; + +} + diff --git a/reactos/lib/crtdll/io/fmode.c b/reactos/lib/crtdll/io/fmode.c new file mode 100644 index 00000000000..1175dde3f6e --- /dev/null +++ b/reactos/lib/crtdll/io/fmode.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef _fmode +int _fmode = O_TEXT; + +unsigned int fmode_dll = &_fmode; diff --git a/reactos/lib/crtdll/io/isatty.c b/reactos/lib/crtdll/io/isatty.c new file mode 100644 index 00000000000..4bb04934d25 --- /dev/null +++ b/reactos/lib/crtdll/io/isatty.c @@ -0,0 +1,8 @@ +#include + +#undef isatty + +int isatty( int handle ) +{ + return (handle & 3); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/lseek.c b/reactos/lib/crtdll/io/lseek.c new file mode 100644 index 00000000000..474624161ec --- /dev/null +++ b/reactos/lib/crtdll/io/lseek.c @@ -0,0 +1,17 @@ +#include +#include +#include + +#undef lseek +long lseek(int _fildes, long _offset, int _whence) +{ + return _lseek(_fildes,_offset,_whence); +} + +long _lseek(int _fildes, long _offset, int _whence) +{ + //return _llseek(filehnd(_fildes),_offset,_whence); +} + + + diff --git a/reactos/lib/crtdll/io/mktemp.c b/reactos/lib/crtdll/io/mktemp.c new file mode 100644 index 00000000000..d0531d9f80e --- /dev/null +++ b/reactos/lib/crtdll/io/mktemp.c @@ -0,0 +1,74 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/io/mktemp.c + * PURPOSE: Makes a temp file based on a template + * PROGRAMER: DJ Delorie + Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Appropriated for the Reactos Kernel + */ + +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include +#include +#include + + +char * +mktemp (char *_template) +{ + static int count = 0; + char *cp, *dp; + int i, len, xcount, loopcnt; + + + + len = strlen (_template); + cp = _template + len; + + xcount = 0; + while (xcount < 6 && cp > _template && cp[-1] == 'X') + xcount++, cp--; + + if (xcount) { + dp = cp; + while (dp > _template && dp[-1] != '/' && dp[-1] != '\\' && dp[-1] != ':') + dp--; + + /* Keep the first characters of the template, but turn the rest into + Xs. */ + while (cp > dp + 8 - xcount) { + *--cp = 'X'; + xcount = (xcount >= 6) ? 6 : 1 + xcount; + } + + /* If dots occur too early -- squash them. */ + while (dp < cp) { + if (*dp == '.') *dp = 'a'; + dp++; + } + + /* Try to add ".tmp" to the filename. Truncate unused Xs. */ + if (cp + xcount + 3 < _template + len) + strcpy (cp + xcount, ".tmp"); + else + cp[xcount] = 0; + + /* This loop can run up to 2<<(5*6) times, or about 10^9 times. */ + for (loopcnt = 0; loopcnt < (1 << (5 * xcount)); loopcnt++) { + int c = count++; + for (i = 0; i < xcount; i++, c >>= 5) + cp[i] = "abcdefghijklmnopqrstuvwxyz012345"[c & 0x1f]; + if (_access(_template,0) == -1) + return _template; + } + } + + /* Failure: truncate the template and return NULL. */ + *_template = 0; + return 0; +} diff --git a/reactos/lib/crtdll/io/open.c b/reactos/lib/crtdll/io/open.c new file mode 100644 index 00000000000..8c07c47a44e --- /dev/null +++ b/reactos/lib/crtdll/io/open.c @@ -0,0 +1,254 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/cputs.c + * PURPOSE: Opens a file and translates handles to fileno + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include +#include +#include +#include +#include +#include +#include + +typedef struct _fileno_modes_type +{ + HANDLE hFile; + int mode; + int fd; +} fileno_modes_type; + +extern fileno_modes_type *fileno_modes; + +char __is_text_file(FILE *p) { + return (!((p)->_flag&_IOSTRG) && (fileno_modes[(p)->_file].mode&O_TEXT)); +} + + +extern int maxfno; + + +int __fileno_alloc(HANDLE hFile, int mode); + +// fixme +#undef open +int open(const char *_path, int _oflag,...) +{ + return _open(_path,_oflag); +} + +int _open(const char *_path, int _oflag,...) +{ + + HANDLE hFile; + DWORD dwDesiredAccess = 0; + DWORD dwShareMode = 0; + DWORD dwCreationDistribution = 0; + DWORD dwFlagsAndAttributes = 0; + + if (( _oflag & _S_IREAD ) == _S_IREAD) + dwShareMode = FILE_SHARE_READ; + else if ( ( _oflag & _S_IWRITE) == _S_IWRITE ) { + dwShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE; + } + +/* + +_O_BINARY Opens file in binary (untranslated) mode. (See fopen for a description of binary mode.) +_O_TEXT Opens file in text (translated) mode. (For more information, see Text and Binary Mode File I/O and fopen.) + +*/ + if (( _oflag & _O_RDWR ) == _O_RDWR ) + dwDesiredAccess |= GENERIC_WRITE|GENERIC_READ; + else if (( _oflag & O_RDONLY ) == O_RDONLY ) + dwDesiredAccess |= GENERIC_READ; + else if (( _oflag & _O_WRONLY ) == _O_WRONLY ) + dwDesiredAccess |= GENERIC_WRITE; + + if (( _oflag & _S_IREAD ) == _S_IREAD ) + dwShareMode |= FILE_SHARE_READ; + + if (( _oflag & _S_IWRITE ) == _S_IWRITE ) + dwShareMode |= FILE_SHARE_WRITE; + + if (( _oflag & (_O_CREAT | _O_EXCL ) ) == (_O_CREAT | _O_EXCL) ) + dwCreationDistribution |= CREATE_NEW; + + else if (( _oflag & (O_TRUNC | O_CREAT ) ) == (O_TRUNC | O_CREAT) ) + dwCreationDistribution |= CREATE_ALWAYS; + + else if (( _oflag & _O_APPEND ) == _O_APPEND ) + dwCreationDistribution |= OPEN_EXISTING; + else if (( _oflag & _O_CREAT ) == _O_CREAT ) + dwCreationDistribution |= OPEN_ALWAYS; + else + dwCreationDistribution |= OPEN_EXISTING; + +// if (( _oflag & _O_TRUNC ) == _O_TRUNC ) +// dwCreationDistribution |= TRUNCATE_EXISTING; + + if (( _oflag & _O_RANDOM ) == _O_RANDOM ) + dwFlagsAndAttributes |= FILE_FLAG_RANDOM_ACCESS; + if (( _oflag & _O_SEQUENTIAL ) == _O_SEQUENTIAL ) + dwFlagsAndAttributes |= FILE_FLAG_SEQUENTIAL_SCAN; + + if (( _oflag & _O_TEMPORARY ) == _O_TEMPORARY ) + dwFlagsAndAttributes |= FILE_FLAG_DELETE_ON_CLOSE; + + if (( _oflag & _O_SHORT_LIVED ) == _O_SHORT_LIVED ) + dwFlagsAndAttributes |= FILE_FLAG_DELETE_ON_CLOSE; + + hFile = CreateFileA( + _path, + dwDesiredAccess, + dwShareMode, + NULL, + dwCreationDistribution, + dwFlagsAndAttributes, + NULL + ); + if ( hFile == (HANDLE)-1 ) + return -1; + return __fileno_alloc(hFile,_oflag); + +// _O_APPEND Moves file pointer to end of file before every write operation. + +} + + +fileno_modes_type *fileno_modes = NULL; + +int maxfno = 5; +int minfno = 5; + + +int +__fileno_alloc(HANDLE hFile, int mode) +{ + + int i; + /* Check for bogus values */ + if (hFile < 0) + return -1; + + for(i=minfno;i= maxfno ) + return (void *)-1; + + if ( fileno_modes[fileno].fd == -1 ) + return (void *)-1; + return fileno_modes[fileno].hFile; +} + +int __fileno_dup2( int handle1, int handle2 ) +{ + if ( handle1 >= maxfno ) + return -1; + + if ( handle1 < 0 ) + return -1; + if ( handle2 >= maxfno ) + return -1; + + if ( handle2 < 0 ) + return -1; + + memcpy(&fileno_modes[handle1],&fileno_modes[handle2],sizeof(fileno_modes)); + + + return handle1; +} + +int __fileno_setmode(int _fd, int _newmode) +{ + int m; + if ( _fd < 0 ) + return -1; + + if ( _fd >= maxfno ) + return -1; + + m = fileno_modes[_fd].mode; + fileno_modes[_fd].mode = _newmode; + return m; +} + +int __fileno_close(int _fd) +{ + if ( _fd < 0 ) + return -1; + + if ( _fd >= maxfno ) + return -1; + + fileno_modes[_fd].fd = -1; + fileno_modes[_fd].hFile = (HANDLE)-1; + +} + +int _open_osfhandle (void *osfhandle, int flags ) +{ + return __fileno_alloc((HANDLE)osfhandle, flags); +} diff --git a/reactos/lib/crtdll/io/read.c b/reactos/lib/crtdll/io/read.c new file mode 100644 index 00000000000..a0bfbae5611 --- /dev/null +++ b/reactos/lib/crtdll/io/read.c @@ -0,0 +1,26 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/io/read.c + * PURPOSE: Reads a file + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include + +size_t read(int _fd, void *_buf, size_t _nbyte) +{ + return _read(_fd,_buf,_nbyte); +} +size_t _read(int _fd, void *_buf, size_t _nbyte) +{ + size_t _rbyte; + if ( !ReadFile(filehnd(_fd),_buf,_nbyte,&_rbyte,NULL) ) { + printf("%d\n",GetLastError()); + return -1; + } + + return _rbyte; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/setmode.c b/reactos/lib/crtdll/io/setmode.c new file mode 100644 index 00000000000..f5b9ff58dc2 --- /dev/null +++ b/reactos/lib/crtdll/io/setmode.c @@ -0,0 +1,24 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/io/setmode.c + * PURPOSE: Sets the file translation mode + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ + +#include +#include +#include + +#undef setmode +int setmode(int _fd, int _newmode) +{ + return _setmode(_fd, _newmode); +} + +int _setmode(int _fd, int _newmode) +{ + return __fileno_setmode(_fd, _newmode); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/unlink.c b/reactos/lib/crtdll/io/unlink.c new file mode 100644 index 00000000000..fb99928aaef --- /dev/null +++ b/reactos/lib/crtdll/io/unlink.c @@ -0,0 +1,23 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/io/unlink.c + * PURPOSE: Deletes a file + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include + +int unlink( const char *filename ) +{ + return _unlink(filename); +} + +int _unlink( const char *filename ) +{ + if ( !DeleteFile(filename) ) + return -1; + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/io/write.c b/reactos/lib/crtdll/io/write.c new file mode 100644 index 00000000000..7a615d1aafc --- /dev/null +++ b/reactos/lib/crtdll/io/write.c @@ -0,0 +1,27 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/io/write.c + * PURPOSE: Writes to a file + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include +#include + +int write(int _fd, const void *_buf,int _nbyte) +{ + return _write(_fd,_buf,_nbyte); +} + +size_t _write(int _fd, const void *_buf, size_t _nbyte) +{ + size_t _wbyte; + if ( !WriteFile(filehnd(_fd),_buf,_nbyte,&_wbyte,NULL) ) { + printf("%d\n",GetLastError()); + return -1; + } + return _wbyte; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/libc/atexit.h b/reactos/lib/crtdll/libc/atexit.h new file mode 100644 index 00000000000..b3a9f0103ad --- /dev/null +++ b/reactos/lib/crtdll/libc/atexit.h @@ -0,0 +1,33 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_libc_atexit_h__ +#define __dj_include_libc_dosexec_h__ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +struct __atexit { + struct __atexit *__next; + void (*__function)(void); +}; + +extern struct __atexit *__atexit_ptr; + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* __dj_include_libc_dosexec_h__ */ diff --git a/reactos/lib/crtdll/libc/file.h b/reactos/lib/crtdll/libc/file.h new file mode 100644 index 00000000000..c80ffb53f03 --- /dev/null +++ b/reactos/lib/crtdll/libc/file.h @@ -0,0 +1,64 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_libc_file_h__ +#define __dj_include_libc_file_h__ + +#include +#include + + +//#include + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +#ifndef _IORMONCL +#define _IORMONCL 004000 /* remove on close, for temp files */ +#endif +/* if _flag & _IORMONCL, ._name_to_remove needs freeing */ + +#ifndef _IOUNGETC +#define _IOUNGETC 010000 /* there is an ungetc'ed character in the buffer */ +#endif + +int _flsbuf(int, FILE*); +int _filbuf(FILE *); +void _fwalk(void (*)(FILE *)); + + + +char __is_text_file(FILE *p); + +int _doprnt(const char *fmt, va_list args, FILE *f); +int _doscan(FILE *iop, const char *fmt, void **argp); + +void *filehnd(int fileno); +int __fileno_dup2( int handle1, int handle2 ); +int __fileno_setmode(int _fd, int _newmode); +int __fileno_close(int _fd); + +#undef fileno +#define fileno(f) (f->_file) +#undef feof +#define feof(f) (((f)->_flag&_IOEOF)!=0) +#undef ferror +#define ferror(f) (((f)->_flag&_IOERR)!=0) + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* __dj_include_libc_file_h__ */ diff --git a/reactos/lib/crtdll/makefile b/reactos/lib/crtdll/makefile index 8428531d3d6..c6cae19679d 100644 --- a/reactos/lib/crtdll/makefile +++ b/reactos/lib/crtdll/makefile @@ -1,5 +1,18 @@ all: crtdll.a + +CTYPE_OBJECTS = ctype/ct_flags.o ctype/ct_lower.o ctype/ct_upper.o ctype/isalnum.o \ + ctype/isalpha.o ctype/isascii.o ctype/iscntrl.o ctype/isdigit.o ctype/isgraph.o \ + ctype/islower.o ctype/isprint.o ctype/ispunct.o ctype/isspace.o ctype/isupper.o \ + ctype/isxdigit.o ctype/toascii.o ctype/tolower.o ctype/toupper.o + +CONIO_OBJECTS = conio/cputs.o conio/getch.o conio/getche.o conio/putch.o conio/ungetch.o + +DIRECT_OBJECTS = direct/chdir.o direct/chdrive.o direct/getcwd.o direct/getdrive.o \ + direct/rmdir.o direct/mkdir.o direct/getdfree.o + +MISC_OBJECTS = misc/sleep.o misc/crt1.o misc/getargs.o misc/crtfmode.o + STRING_OBJECTS = string/memchr.o string/memcmp.o string/strcat.o \ string/strchr.o string/strcmp.o string/strcoll.o \ string/strcpy.o string/strcspn.o string/memcpy.o \ @@ -7,18 +20,60 @@ STRING_OBJECTS = string/memchr.o string/memcmp.o string/strcat.o \ string/strncpy.o string/strpbrk.o string/strrchr.o \ string/strspn.o string/strstr.o string/strtok.o \ string/strxfrm.o string/memmove.o string/memset.o \ - string/strdup.o + string/strdup.o string/strlwr.o string/strupr.o \ + string/str_old.o string/strerror.o + +WCHAR_OBJECTS = wchar/wcscat.o wchar/wcschr.o wchar/wcscmp.o \ + wchar/wcscoll.o wchar/wcscpy.o wchar/wcscspn.o \ + wchar/wcsdup.o wchar/wcsicmp.o wchar/wcslen.o \ + wchar/wcslwr.o wchar/wcsncat.o wchar/wcsncmp.o \ + wchar/wcsncpy.o + +STDIO_OBJECTS = stdio/vsprintf.o stdio/getenv.o stdio/doprnt.o stdio/doscan.o \ + stdio/puts.o stdio/fclose.o stdio/feof.o stdio/ferror.o \ + stdio/fflush.o stdio/fgetc.o stdio/fgetpos.o stdio/fgets.o stdio/flsbuf.o \ + stdio/fopen.o stdio/fprintf.o stdio/fputc.o stdio/fputs.o \ + stdio/fread.o stdio/freopen.o stdio/fscanf.o stdio/fseek.o \ + stdio/fsetpos.o stdio/ftell.o stdio/fwalk.o stdio/fwrite.o stdio/getc.o \ + stdio/getchar.o stdio/gets.o stdio/getw.o stdio/perror.o stdio/printf.o \ + stdio/putc.o stdio/putchar.o stdio/puts.o stdio/putw.o \ + stdio/remove.o stdio/rename.o stdio/rewind.o stdio/allocfil.o\ + stdio/scanf.o stdio/setbuf.o stdio/setbuffe.o \ + stdio/setlineb.o stdio/setvbuf.o stdio/sprintf.o stdio/sscanf.o \ + stdio/stdiohk.o stdio/stdhnd.o stdio/tempnam.o stdio/tmpfile.o stdio/tmpnam.o \ + stdio/ungetc.o stdio/vfprintf.o stdio/vprintf.o stdio/vsprintf.o -STDIO_OBJECTS = stdio/vsprintf.o +IO_OBJECTS = io/access.o io/close.o io/create.o io/dup.o io/dup2.o io/find.o io/isatty.o io/lseek.o \ + io/open.o io/read.o io/setmode.o io/unlink.o io/write.o io/fmode.o -STDLIB_OBJECTS = stdlib/malloc.o +STDLIB_OBJECTS = stdlib/abort.o stdlib/abs.o stdlib/atexit.o stdlib/atof.o stdlib/atoi.o stdlib/atold.o \ + stdlib/bsearch.o stdlib/calloc.o stdlib/div.o stdlib/errno.o stdlib/exit.o \ + stdlib/fullpath.o stdlib/labs.o stdlib/ldiv.o stdlib/llabs.o stdlib/lldiv.o \ + stdlib/makepath.o stdlib/malloc.o stdlib/putenv.o stdlib/qsort.o \ + stdlib/rand.o stdlib/senv.o stdlib/splitp.o stdlib/strtod.o stdlib/strtol.o \ + stdlib/strtoul.o stdlib/strtold.o + +PROCESS_OBJECTS = process/spawnl.o process/spawnlp.o process/spawnlpe.o process/spawnvpe.o process/spawnvp.o \ + process/spawnv.o process/spawnve.o process/spawnle.o process/execl.o process/execlp.o process/execlpe.o \ + process/execvpe.o process/execvp.o process/execv.o process/execle.o + +TIME_OBJECTS = time/ctime.o time/difftime.o time/strftime.o time/time.o + +FLOAT_OBJECTS = float/fpreset.o + +SYS_STAT_OBJECTS = sys_stat/fstat.o sys_stat/stat.o + +OBJECTS = $(CTYPE_OBJECTS) $(CONIO_OBJECTS) $(DIRECT_OBJECTS) $(MISC_OBJECTS) \ + $(STRING_OBJECTS) $(WCHAR_OBJECTS) $(STDIO_OBJECTS) $(STDLIB_OBJECTS) \ + $(IO_OBJECTS) $(PROCESS_OBJECTS) $(TIME_OBJECTS) $(FLOAT_OBJECTS) \ + $(SYS_STAT_OBJECTS) -OBJECTS = $(STRING_OBJECTS) $(STDIO_OBJECTS) $(STDLIB_OBJECTS) crtdll.a: $(OBJECTS) - $(AR) rcs crtdll.a $(OBJECTS) + $(CC) $(CFLAGS) -c $< -o $@ + $(AR) vrcs crtdll.a $(OBJECTS) dummy: -include ../../rules.mak +include ../../Rules.mak diff --git a/reactos/lib/crtdll/math/ftol.c b/reactos/lib/crtdll/math/ftol.c new file mode 100644 index 00000000000..d0f8a50015f --- /dev/null +++ b/reactos/lib/crtdll/math/ftol.c @@ -0,0 +1,3 @@ +long __cdecl ftol(double fl) { + return (long)fl; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/misc/CRT_noglob.c b/reactos/lib/crtdll/misc/CRT_noglob.c new file mode 100644 index 00000000000..ec44ff0afdf --- /dev/null +++ b/reactos/lib/crtdll/misc/CRT_noglob.c @@ -0,0 +1,18 @@ +/* + * noglob.c + * + * This file defines _CRT_glob to have a value of 0, which will + * turn off command line globbing. It is compiled into a separate object + * file which you can add to your link line to turn off globbing like + * this: + * + * gcc -o foo.exe foo.o noglob.o + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +int _CRT_glob = 0; + diff --git a/reactos/lib/crtdll/misc/CRTfmode.c b/reactos/lib/crtdll/misc/CRTfmode.c new file mode 100644 index 00000000000..11a13fdf87c --- /dev/null +++ b/reactos/lib/crtdll/misc/CRTfmode.c @@ -0,0 +1,21 @@ +/* + * CRTfmode.c + * + * Sets _CRT_fmode to be zero, which will cause _mingw32_init_fmode to leave + * all file modes in their default state (basically text mode). + * + * This file is part of the Mingw32 package. + * + * THIS FILE IS IN THE PUBLIC DOMAIN. + * + * Contributers: + * Created by Colin Peters + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +unsigned int _CRT_fmode = 0; + diff --git a/reactos/lib/crtdll/misc/CRTglob.c b/reactos/lib/crtdll/misc/CRTglob.c new file mode 100644 index 00000000000..53debd1d3cb --- /dev/null +++ b/reactos/lib/crtdll/misc/CRTglob.c @@ -0,0 +1,19 @@ +/* + * CRTglob.c + * + * This object file defines _CRT_glob to have a value of -1, which will + * turn on command line globbing by default. If you want to turn off + * command line globbing include a line + * + * int _CRT_glob = 0; + * + * in one of your source modules. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +int _CRT_glob = -1; + diff --git a/reactos/lib/crtdll/misc/CRTinit.c b/reactos/lib/crtdll/misc/CRTinit.c new file mode 100644 index 00000000000..cfdedf15841 --- /dev/null +++ b/reactos/lib/crtdll/misc/CRTinit.c @@ -0,0 +1,33 @@ +/* + * CRTinit.c + * + * A dummy version of _CRT_INIT for MS compatibility. Programs, or more often + * dlls, which use the static version of the MSVC run time are supposed to + * call _CRT_INIT to initialize the run time library in DllMain. This does + * not appear to be necessary when using crtdll or the dll versions of the + * MSVC runtime, so the dummy call simply does nothing. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +void +_CRT_INIT () +{ +} + diff --git a/reactos/lib/crtdll/misc/GetArgs.c b/reactos/lib/crtdll/misc/GetArgs.c new file mode 100644 index 00000000000..974ab363920 --- /dev/null +++ b/reactos/lib/crtdll/misc/GetArgs.c @@ -0,0 +1,86 @@ +#include +#include +#include + + +char *acmdln_dll; +unsigned int commode_dll; + +unsigned int fmode_dll; +unsigned int winmajor_dll; +unsigned int winminor_dll; +unsigned int winver_dll; +unsigned int osver_dll; + +#undef __argv +#undef __argc + +char *xargv[1024]; + +char **__argv = xargv; +int __argc = 0; +unsigned int *__argc_dll = &__argc; +char ***__argv_dll = &__argv; + +char *xenv; +char **_environ; +char *** _environ_dll = &_environ; +#undef environ +char **environ; + + +int __GetMainArgs(int *argc,char ***argv,char **env,int flag) +{ + char *cmdline; + int i,afterlastspace; + DWORD version; + +// acmdln_dll = cmdline = strdup( GetCommandLineA() ); + + version = GetVersion(); + osver_dll = version >> 16; + winminor_dll = version & 0xFF; + winmajor_dll = (version>>8) & 0xFF; + winver_dll = ((version >> 8) & 0xFF) + ((version & 0xFF) << 8); + + + /* missing threading init */ + + i=0; + + afterlastspace=0; + while (cmdline[i]) { + if (cmdline[i]==' ') { + __argc++; + cmdline[i]='\0'; + __argv[__argc-1] = strdup( cmdline+afterlastspace); + i++; + while (cmdline[i]==' ') + i++; + if (cmdline[i]) + afterlastspace=i; + } else + i++; + } + + __argc++; + cmdline[i]='\0'; + __argv[__argc-1] = strdup( cmdline+afterlastspace); + + + *argc = __argc; + *argv = __argv; + + + xenv = GetEnvironmentStringsA(); + _environ = &xenv; + _environ_dll = &_environ; + environ = &xenv; + env = &xenv; + return 0; +} + +int _chkstk() +{ + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/misc/crt1.c b/reactos/lib/crtdll/misc/crt1.c new file mode 100644 index 00000000000..222a40b094f --- /dev/null +++ b/reactos/lib/crtdll/misc/crt1.c @@ -0,0 +1,166 @@ +/* + * crt1.c + * + * Source code for the startup proceedures used by all programs. This code + * is compiled to make crt0.o, which should be located in the library path. + * + * This code is part of the Mingw32 package. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +#include +#include +#include +#include +#include +#include +#include + +/* NOTE: The code for initializing the _argv, _argc, and environ variables + * has been moved to a separate .c file which is included in both + * crt1.c and dllcrt1.c. This means changes in the code don't have to + * be manually synchronized, but it does lead to this not-generally- + * a-good-idea use of include. */ +#include "init.c" + +extern int main(int, char**, char**); + +/* + * Setup the default file handles to have the _CRT_fmode mode, as well as + * any new files created by the user. + */ +extern unsigned int _CRT_fmode; + +void +_mingw32_init_fmode () +{ + /* Don't set the file mode if the user hasn't set any value for it. */ + if (_CRT_fmode) + { + _fmode = _CRT_fmode; + + /* + * This overrides the default file mode settings for stdin, + * stdout and stderr. At first I thought you would have to + * test with isatty, but it seems that the DOS console at + * least is smart enough to handle _O_BINARY stdout and + * still display correctly. + */ + if (stdin) + { + _setmode (_fileno(stdin), _CRT_fmode); + } + if (stdout) + { + _setmode (_fileno(stdout), _CRT_fmode); + } + if (stderr) + { + _setmode (_fileno(stderr), _CRT_fmode); + } + } +} + + +/* + * The function mainCRTStartup is the entry point for all console programs. + */ +int +mainCRTStartup () +{ + int nRet; + + /* + * I have been told that this is the correct thing to do. You + * have to uncomment the prototype of SetUnhandledExceptionFilter + * in the GNU Win32 API headers for this to work. The type it + * expects is a pointer to a function of the same type as + * UnhandledExceptionFilter, which is prototyped just above + * (see Functions.h). + */ + SetUnhandledExceptionFilter (NULL); + /* + * Initialize errno. + */ + errno = 0; + + /* + * Initialize floating point unit. + */ + _fpreset (); /* Supplied by the runtime library. */ + + /* + * Set up __argc, __argv and _environ. + */ + _mingw32_init_mainargs(); + + + /* + * Sets the default file mode for stdin, stdout and stderr, as well + * as files later opened by the user, to _CRT_fmode. + * NOTE: DLLs don't do this because that would be rude! + */ + _mingw32_init_fmode(); + + /* + * Call the main function. If the user does not supply one + * the one in the 'libmingw32.a' library will be linked in, and + * that one calls WinMain. See main.c in the 'lib' dir + * for more details. + */ + + nRet = cmdmain(_argc, _argv, environ); + + /* + * Perform exit processing for the C library. This means + * flushing output and calling 'atexit' registered functions. + */ + _cexit(); + + ExitProcess (nRet); + + return 0; +} + +/* + * For now the GUI startup function is the same as the console one. + * This simply gets rid of the annoying warning about not being able + * to find WinMainCRTStartup when linking GUI applications. + */ +int +WinMainCRTStartup () +{ + return mainCRTStartup(); +} + +/* With the EGCS build from Mumit Khan (or apparently b19 from Cygnus) this + * is no longer necessary. */ +#if 0 +#ifdef __GNUC__ +/* + * This section terminates the list of imports under GCC. If you do not + * include this then you will have problems when linking with DLLs. + * + */ +asm (".section .idata$3\n" ".long 0,0,0,0,0,0,0,0"); +#endif +#endif + + diff --git a/reactos/lib/crtdll/misc/dllcrt1.c b/reactos/lib/crtdll/misc/dllcrt1.c new file mode 100644 index 00000000000..de7ea379536 --- /dev/null +++ b/reactos/lib/crtdll/misc/dllcrt1.c @@ -0,0 +1,105 @@ +/* + * dllcrt1.c + * + * Initialization code for DLLs. + * + * This file is part of the Mingw32 package. + * + * Contributors: + * Created by Colin Peters + * DLL support adapted from Gunther Ebert + * + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +#include +#include +#include +#include + +/* See note in crt0.c */ +#include "init.c" + +/* Unlike normal crt0, I don't initialize the FPU, because the process + * should have done that already. I also don't set the file handle modes, + * because that would be rude. */ + +#ifdef __GNUC__ +extern void __main(); +extern void __do_global_dtors(); +#endif + +extern BOOL WINAPI DllMain(HANDLE, DWORD, LPVOID); + +BOOL WINAPI +DllMainCRTStartup (HANDLE hDll, DWORD dwReason, LPVOID lpReserved) +{ + BOOL bRet; + + if (dwReason == DLL_PROCESS_ATTACH) + { + _mingw32_init_mainargs(); + +#ifdef __GNUC__ + /* From libgcc.a, calls global class constructors. */ + __main(); +#endif + } + + /* + * Call the user-supplied DllMain subroutine + * NOTE: DllMain is optional, so libmingw32.a includes a stub + * which will be used if the user does not supply one. + */ + bRet = DllMain(hDll, dwReason, lpReserved); + +#ifdef __GNUC__ + if (dwReason == DLL_PROCESS_DETACH) + { + /* From libgcc.a, calls global class destructors. */ + __do_global_dtors(); + } +#endif + + return bRet; +} + +/* + * For the moment a dummy atexit. Atexit causes problems in DLLs, especially + * if they are dynamically loaded. For now atexit inside a DLL does nothing. + * NOTE: We need this even if the DLL author never calls atexit because + * the global constructor function __do_global_ctors called from __main + * will attempt to register __do_global_dtors using atexit. + * Thanks to Andrey A. Smirnov for pointing this one out. + */ +int +atexit (void (*pfn)()) +{ + return 0; +} + +/* With the EGCS snapshot from Mumit Khan (or b19 from Cygnus I hear) this + * is no longer necessary. */ +#if 0 +#ifdef __GNUC__ +/* + * This section terminates the list of imports under GCC. If you do not + * include this then you will have problems when linking with DLLs. + */ +asm (".section .idata$3\n" ".long 0,0,0,0,0,0,0,0"); +#endif +#endif diff --git a/reactos/lib/crtdll/misc/dllmain.c b/reactos/lib/crtdll/misc/dllmain.c new file mode 100644 index 00000000000..8fc7e27af77 --- /dev/null +++ b/reactos/lib/crtdll/misc/dllmain.c @@ -0,0 +1,32 @@ +/* + * dllmain.c + * + * A stub DllMain function which will be called by DLLs which do not + * have a user supplied DllMain. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +#include + +BOOL WINAPI DllMain (HANDLE hDll, DWORD dwReason, LPVOID lpReserved) +{ + return TRUE; +} + diff --git a/reactos/lib/crtdll/misc/gccmain.c b/reactos/lib/crtdll/misc/gccmain.c new file mode 100644 index 00000000000..8cc03aa8878 --- /dev/null +++ b/reactos/lib/crtdll/misc/gccmain.c @@ -0,0 +1,85 @@ +/* + * gccmain.c + * + * A separate version of __main, __do_global_ctors and __do_global_dtors for + * Mingw32 for use with Cygwin32 b19. Hopefully this object file will only + * be linked if the libgcc.a doesn't include __main, __do_global_dtors and + * __do_global_ctors. + * + * This file is part of the Mingw32 package. + * + * Contributors: + * Code supplied by Stan Cox + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +/* Needed for the atexit prototype. */ +#include + +typedef void (*func_ptr) (void); +extern func_ptr __CTOR_LIST__[]; +extern func_ptr __DTOR_LIST__[]; + +void +__do_global_dtors (void) +{ + static func_ptr *p = __DTOR_LIST__ + 1; + + /* + * Call each destructor in the destructor list until a null pointer + * is encountered. + */ + while (*p) + { + (*(p)) (); + p++; + } +} + +void +__do_global_ctors (void) +{ + unsigned long nptrs = (unsigned long) __CTOR_LIST__[0]; + unsigned i; + + /* + * If the first entry in the constructor list is -1 then the list + * is terminated with a null entry. Otherwise the first entry was + * the number of pointers in the list. + */ + if (nptrs == -1) + { + for (nptrs = 0; __CTOR_LIST__[nptrs + 1] != 0; nptrs++) + ; + } + + /* + * Go through the list backwards calling constructors. + */ + for (i = nptrs; i >= 1; i--) + { + __CTOR_LIST__[i] (); + } + + /* + * Register the destructors for processing on exit. + */ + atexit (__do_global_dtors); +} + +static int initialized = 0; + +void +__main (void) +{ + if (! initialized) + { + initialized = 1; + __do_global_ctors (); + } +} + diff --git a/reactos/lib/crtdll/misc/init.c b/reactos/lib/crtdll/misc/init.c new file mode 100644 index 00000000000..1945d258b7e --- /dev/null +++ b/reactos/lib/crtdll/misc/init.c @@ -0,0 +1,75 @@ +/* + * init.c + * + * Code to initialize standard file handles and command line arguments. + * This file is #included in both crt1.c and dllcrt1.c. + * + * This file is part of the Mingw32 package. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +/* + * Access to a standard 'main'-like argument count and list. Also included + * is a table of environment variables. + */ +int _argc = 0; +char** _argv = 0; + +/* NOTE: Thanks to Pedro A. Aranda Gutiirrez for pointing + * this out to me. GetMainArgs (used below) takes a fourth argument + * which is an int that controls the globbing of the command line. If + * _CRT_glob is non-zero the command line will be globbed (e.g. *.* + * expanded to be all files in the startup directory). In the mingw32 + * library a _CRT_glob variable is defined as being -1, enabling + * this command line globbing by default. To turn it off and do all + * command line processing yourself (and possibly escape bogons in + * MS's globbing code) include a line in one of your source modules + * defining _CRT_glob and setting it to zero, like this: + * int _CRT_glob = 0; + */ +extern int _CRT_glob; + +#ifdef __MSVCRT__ +extern void __getmainargs(int *, char***, char***, int); +#else +extern void __GetMainArgs(int *, char***, char***, int); +#endif + +/* + * Initialize the _argc, _argv and environ variables. + */ +static void +_mingw32_init_mainargs () +{ + /* The environ variable is provided directly in stdlib.h through + * a dll function call. */ + char** dummy_environ; + + /* + * Microsoft's runtime provides a function for doing just that. + */ +#ifdef __MSVCRT__ + (void) __getmainargs(&_argc, &_argv, &dummy_environ, _CRT_glob); +#else + /* CRTDLL version */ + (void) __GetMainArgs(&_argc, &_argv, &dummy_environ, _CRT_glob); +#endif +} + diff --git a/reactos/lib/crtdll/misc/main.c b/reactos/lib/crtdll/misc/main.c new file mode 100644 index 00000000000..989c7fb6979 --- /dev/null +++ b/reactos/lib/crtdll/misc/main.c @@ -0,0 +1,95 @@ +/* + * main.c + * + * Extra startup code for applications which do not have a main function + * of their own (but do have a WinMain). Generally these are GUI + * applications, but they don't *have* to be. + * + * This file is part of the Mingw32 package. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:43 $ + * + */ + +#include +#include +#include + +#define ISSPACE(a) (a == ' ' || a == '\t') + +extern int PASCAL WinMain (HANDLE hInst, HANDLE hPrevInst, LPSTR szCmdLine, + int nShow); + +int +main (int argc, char* argv[], char* environ[]) +{ + char* szCmd; + STARTUPINFO startinfo; + int nRet; + + /* Get the command line passed to the process. */ + szCmd = GetCommandLineA(); + GetStartupInfoA(&startinfo); + + /* Strip off the name of the application and any leading + * whitespace. */ + if (szCmd) + { + while(ISSPACE(*szCmd)) + { + szCmd++; + } + + /* On my system I always get the app name enclosed + * in quotes... */ + if (*szCmd == '\"') + { + do + { + szCmd++; + } + while (*szCmd != '\"' && *szCmd != '\0'); + + if (*szCmd == '\"') + { + szCmd++; + } + } + else + { + /* If no quotes then assume first token is program + * name. */ + while (!ISSPACE(*szCmd) && *szCmd != '\0') + { + szCmd++; + } + } + + while (ISSPACE(*szCmd)) + { + szCmd++; + } + } + + nRet = WinMain (GetModuleHandle(NULL), NULL, szCmd, + (startinfo.dwFlags & STARTF_USESHOWWINDOW) ? + startinfo.wShowWindow : SW_SHOWDEFAULT); + + return nRet; +} + diff --git a/reactos/lib/crtdll/misc/sleep.c b/reactos/lib/crtdll/misc/sleep.c new file mode 100644 index 00000000000..301edcffde8 --- /dev/null +++ b/reactos/lib/crtdll/misc/sleep.c @@ -0,0 +1,7 @@ +#include + + +void sleep(unsigned long timeout) +{ + Sleep((timeout)?timeout:1); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/misc/unwind.c b/reactos/lib/crtdll/misc/unwind.c new file mode 100644 index 00000000000..38e9027fc2c --- /dev/null +++ b/reactos/lib/crtdll/misc/unwind.c @@ -0,0 +1,10 @@ +void _global_unwind2( PEXCEPTION_FRAME frame ) +{ + RtlUnwind( frame, 0, NULL, 0 ); +} + + +void _local_unwind2( PEXCEPTION_FRAME endframe, DWORD nr ) +{ + TRACE(crtdll,"(%p,%ld)\n",endframe,nr); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/process/Cwait.c b/reactos/lib/crtdll/process/Cwait.c new file mode 100644 index 00000000000..2217f14c765 --- /dev/null +++ b/reactos/lib/crtdll/process/Cwait.c @@ -0,0 +1,20 @@ +#include +#include + +int _cwait( int *termstat, int procHandle, int action ) +{ + DWORD RetVal; + RetVal = WaitForSingleObject((HANDLE)procHandle, INFINITE); + if (RetVal == WAIT_FAILED || RetVal == WAIT_ABANDONED) { + //errno = ECHILD; + return -1; + } + if ( RetVal == WAIT_OBJECT_0 ) { + GetExitCodeProcess((HANDLE)procHandle, termstat); + return procHandle; + } + + + return -1; + // WAIT_TIMEOUT +} \ No newline at end of file diff --git a/reactos/lib/crtdll/process/System.c b/reactos/lib/crtdll/process/System.c new file mode 100644 index 00000000000..861f3ca62c5 --- /dev/null +++ b/reactos/lib/crtdll/process/System.c @@ -0,0 +1,16 @@ +#include +#include + +int system(const char *command) +{ + char CmdLine[MAX_PATH]; + char *comspec = getenv("COMSPEC"); + if ( comspec == NULL ) + comspec = "cmd.exe"; + strcpy(CmdLine,comspec); + strcat(CmdLine," /C "); + if ( !WinExec(CmdLine,SW_SHOWNORMAL) < 31 ) + return -1; + + return 0; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/process/execl.c b/reactos/lib/crtdll/process/execl.c new file mode 100644 index 00000000000..f971024031f --- /dev/null +++ b/reactos/lib/crtdll/process/execl.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +extern char *const *_environ; + +int execl(const char *path, const char *argv0, ...) +{ + return spawnve(P_OVERLAY, path, (char *const*)&argv0, _environ); +} diff --git a/reactos/lib/crtdll/process/execle.c b/reactos/lib/crtdll/process/execle.c new file mode 100644 index 00000000000..c68ec0f0868 --- /dev/null +++ b/reactos/lib/crtdll/process/execle.c @@ -0,0 +1,17 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + + +#include + +#define scan_ptr() \ + const char **ptr; \ + union { const char **ccpp; const char *ccp; } u; \ + for (ptr = &argv0; *ptr; ptr++); \ + u.ccp = *++ptr; \ + ptr = u.ccpp; + +int execle(const char *path, const char *argv0, ... /*, const char **envp */) +{ + scan_ptr(); + return spawnve(P_OVERLAY, path, (char *const *)&argv0, (char *const *)ptr); +} diff --git a/reactos/lib/crtdll/process/execlp.c b/reactos/lib/crtdll/process/execlp.c new file mode 100644 index 00000000000..45c11924729 --- /dev/null +++ b/reactos/lib/crtdll/process/execlp.c @@ -0,0 +1,11 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + + +extern char * const *_environ; + +int execlp(const char *path, const char *argv0, ...) +{ + return spawnvpe(P_OVERLAY, path, (char * const *)&argv0, _environ); +} diff --git a/reactos/lib/crtdll/process/execlpe.c b/reactos/lib/crtdll/process/execlpe.c new file mode 100644 index 00000000000..da5f70848e5 --- /dev/null +++ b/reactos/lib/crtdll/process/execlpe.c @@ -0,0 +1,17 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + + +#define scan_ptr() \ + const char **ptr; \ + union { const char **ccpp; const char *ccp; } u; \ + for (ptr = &argv0; *ptr; ptr++); \ + u.ccp = *++ptr; \ + ptr = u.ccpp; + +int execlpe(const char *path, const char *argv0, ... /*, const char **envp */) +{ + scan_ptr(); + return spawnvpe(P_OVERLAY, path, (char * const *)&argv0, (char * const *)ptr); +} diff --git a/reactos/lib/crtdll/process/execv.c b/reactos/lib/crtdll/process/execv.c new file mode 100644 index 00000000000..893cf85533a --- /dev/null +++ b/reactos/lib/crtdll/process/execv.c @@ -0,0 +1,11 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +//#include +#include + +extern char * const *_environ; + +int execv(const char *path, const char * const *argv) +{ + return spawnve(P_OVERLAY, path, argv, _environ); +} diff --git a/reactos/lib/crtdll/process/execve.c b/reactos/lib/crtdll/process/execve.c new file mode 100644 index 00000000000..38b4a96b7c2 --- /dev/null +++ b/reactos/lib/crtdll/process/execve.c @@ -0,0 +1,9 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +//#include +//#include +#include + +int execve(const char *path,const char * const argv[], char * const envp[]) +{ + return spawnve(P_OVERLAY, path, argv, envp); +} diff --git a/reactos/lib/crtdll/process/execvp.c b/reactos/lib/crtdll/process/execvp.c new file mode 100644 index 00000000000..cdaad875545 --- /dev/null +++ b/reactos/lib/crtdll/process/execvp.c @@ -0,0 +1,11 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +//#include +#include + +extern char *const *_environ; + +int execvp(const char *path,const char * const argv[]) +{ + return spawnvpe(P_OVERLAY, path, argv, _environ); +} diff --git a/reactos/lib/crtdll/process/execvpe.c b/reactos/lib/crtdll/process/execvpe.c new file mode 100644 index 00000000000..d4af43ebcff --- /dev/null +++ b/reactos/lib/crtdll/process/execvpe.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + + +#include + +int execvpe(const char *path,const char * const argv[],const char * const envp[]) +{ + return spawnvpe(P_OVERLAY, path, argv, envp); +} + + +int _execvpe(const char *path,const char * const argv[],const char * const envp[]) +{ + return spawnvpe(P_OVERLAY, path, argv, envp); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/process/spawnl.c b/reactos/lib/crtdll/process/spawnl.c new file mode 100644 index 00000000000..0397fb90413 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnl.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +extern char **_environ; + +int spawnl(int mode, const char *path, const char *argv0, ...) +{ + return spawnve(mode, path, (char * const *)&argv0, _environ); +} diff --git a/reactos/lib/crtdll/process/spawnle.c b/reactos/lib/crtdll/process/spawnle.c new file mode 100644 index 00000000000..157caad1fe5 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnle.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +#define scan_ptr() \ + const char **ptr; \ + union { const char **ccpp; const char *ccp; } u; \ + for (ptr = &argv0; *ptr; ptr++); \ + u.ccp = *++ptr; \ + ptr = u.ccpp; + +int spawnle(int mode, const char *path, const char *argv0, ... /*, const char **envp */) +{ + scan_ptr(); + return spawnve(mode, path, (char * const *)&argv0, (char * const *)ptr); +} diff --git a/reactos/lib/crtdll/process/spawnlp.c b/reactos/lib/crtdll/process/spawnlp.c new file mode 100644 index 00000000000..8813e5cf3a3 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnlp.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +extern char **_environ; + +int spawnlp(int mode, const char *path, const char *argv0, ...) +{ + return spawnvpe(mode, path, (char * const *)&argv0, (char * const *)_environ); +} diff --git a/reactos/lib/crtdll/process/spawnlpe.c b/reactos/lib/crtdll/process/spawnlpe.c new file mode 100644 index 00000000000..908e2f4bc24 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnlpe.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include +#define scan_ptr() \ + const char **ptr; \ + union { const char **ccpp; const char *ccp; } u; \ + for (ptr = &argv0; *ptr; ptr++); \ + u.ccp = *++ptr; \ + ptr = u.ccpp; + +int spawnlpe(int mode, const char *path, const char *argv0, ... /*, const char **envp */) +{ + scan_ptr(); + return spawnvpe(mode, path, (char * const *)&argv0, (char * const *)ptr); +} diff --git a/reactos/lib/crtdll/process/spawnv.c b/reactos/lib/crtdll/process/spawnv.c new file mode 100644 index 00000000000..a41b777fff2 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnv.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +extern char **_environ; + +int spawnv(int mode, const char *path,const char *const argv[]) +{ + return spawnve(mode, path, (char * const *)argv, _environ); +} diff --git a/reactos/lib/crtdll/process/spawnve.c b/reactos/lib/crtdll/process/spawnve.c new file mode 100644 index 00000000000..c848475154f --- /dev/null +++ b/reactos/lib/crtdll/process/spawnve.c @@ -0,0 +1,42 @@ +#include +#include +#include +#include + +int _p_overlay = 2; + +int spawnve(int mode, const char *path,const char *const argv[],const char *const envp[]) +{ + + char ApplicationName[MAX_PATH]; + char CommandLine[1024]; + PROCESS_INFORMATION ProcessInformation; + STARTUPINFO StartupInfo; + + int i = 0; + CommandLine[0] = 0; + while(argv[i] != NULL ) { + strcat(CommandLine,argv[i]); + strcat(CommandLine," "); + i++; + } + strcpy(ApplicationName,argv[0]); + + fflush(stdout); /* just in case */ + StartupInfo.cb = sizeof(STARTUPINFO); + StartupInfo.lpReserved= NULL; + StartupInfo.dwFlags = 0; + + +// if ( CreateProcessA(ApplicationName,CommandLine,NULL,NULL,TRUE,CREATE_NEW_CONSOLE|NORMAL_PRIORITY_CLASS,NULL,*envp,&StartupInfo,&ProcessInformation) ) { +// errno = GetLastError(); +// return -1; +// } + + + if (mode == P_OVERLAY) + exit(i); + +// _P_NOWAIT or _P_NOWAITO + return ProcessInformation.hProcess; +} diff --git a/reactos/lib/crtdll/process/spawnvp.c b/reactos/lib/crtdll/process/spawnvp.c new file mode 100644 index 00000000000..34b39ccba75 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnvp.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include + +extern char **_environ; + +int spawnvp(int mode, const char *path,const char *const argv[]) +{ + return spawnvpe(mode, path, (char * const *)argv, _environ); +} diff --git a/reactos/lib/crtdll/process/spawnvpe.c b/reactos/lib/crtdll/process/spawnvpe.c new file mode 100644 index 00000000000..4ba9a2ec148 --- /dev/null +++ b/reactos/lib/crtdll/process/spawnvpe.c @@ -0,0 +1,23 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include +#include + + +int spawnvpe(int mode, const char *path,const char *const argv[],const char *const envp[]) +{ + + char rpath[300]; + union {const char * const *cpcp; char **cpp; } u; + u.cpcp = envp; +/* + if (!__dosexec_find_on_path(path, u.cpp, rpath)) + { + errno = ENOENT; + return -1; + } + else +*/ + return spawnve(mode, rpath, argv, envp); + +} diff --git a/reactos/lib/crtdll/stdio/allocfil.c b/reactos/lib/crtdll/stdio/allocfil.c new file mode 100644 index 00000000000..e438eb816a3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/allocfil.c @@ -0,0 +1,94 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include +//#include +//#include + +FILE * __alloc_file(void); + + +/* A FILE* is considered "free" if its flag is zero. */ + +#define __FILE_REC_MAX 20 +typedef struct __file_rec { + struct __file_rec *next; + int count; + FILE *files[__FILE_REC_MAX]; +} __file_rec; + +extern __file_rec *__file_rec_list; + +FILE *__alloc_file(void) +{ + __file_rec *fr = __file_rec_list; + __file_rec **last_fr = &__file_rec_list; + FILE *rv=0; + int i; + + /* Try to find an empty slot */ + while (fr) + { + last_fr = &(fr->next); + + /* If one of the existing slots is available, return it */ + for (i=0; icount; i++) + if (fr->files[i]->_flag == 0) + return fr->files[i]; + + /* If this one is full, go to the next */ + if (fr->count == __FILE_REC_MAX) + fr = fr->next; + else + /* it isn't full, we can add to it */ + break; + } + if (!fr) + { + /* add another one to the end, make it empty */ + fr = *last_fr = (__file_rec *)malloc(sizeof(__file_rec)); + if (fr == 0) + return 0; + fr->next = 0; + fr->count = 0; + } + /* fr is a pointer to a rec with empty slots in it */ + rv = fr->files[fr->count] = (FILE *)malloc(sizeof(FILE)); + if (rv == 0) + return 0; + memset(rv, 0, sizeof(FILE)); + fr->count ++; + return rv; +} + + +int _fcloseall( void ) +{ + __file_rec *fr = __file_rec_list; + __file_rec **last_fr = &__file_rec_list; + + int total_closed; + int i = 0; + + /* Try to find an empty slot */ + while (fr) + { + last_fr = &(fr->next); + + /* If one of the existing slots is available, return it */ + for (i=0; icount; i++) + if (fr->files[i]->_flag != 0) { + fclose(fr->files[i]); + total_closed++; + } + + /* If this one is full, go to the next */ + if (fr->count == __FILE_REC_MAX) + fr = fr->next; + else + /* it isn't full, we can add to it */ + break; + } + return total_closed; +} diff --git a/reactos/lib/crtdll/stdio/clearerr.c b/reactos/lib/crtdll/stdio/clearerr.c new file mode 100644 index 00000000000..da87ede740f --- /dev/null +++ b/reactos/lib/crtdll/stdio/clearerr.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef clearerr +void +clearerr(FILE *f) +{ + f->_flag &= ~(_IOERR|_IOEOF); +} diff --git a/reactos/lib/crtdll/stdio/doprnt.c b/reactos/lib/crtdll/stdio/doprnt.c new file mode 100644 index 00000000000..ad4a15a9436 --- /dev/null +++ b/reactos/lib/crtdll/stdio/doprnt.c @@ -0,0 +1,319 @@ + + + + +/* + * 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 +#include + +//#undef isdigit + +size_t strnlen( const char *string, size_t count ); + + +static int skip_atoi(const char **s) +{ + int i=0; + + while (isdigit(**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' */ + + +static int __res; + +int do_div(int *n,int base) { + +__res = ((unsigned long) *n) % (unsigned) base; +*n = ((unsigned long) *n) / (unsigned) base; +return __res; +} + +static char * number(FILE * f, 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) + putc( ' ',f); + if (sign) + putc( sign,f); + if (type & SPECIAL) + if (base==8) + putc( '0',f); + else if (base==16) { + putc( '0', f); + putc( digits[33],f); + } + if (!(type & LEFT)) + while (size-- > 0) + putc( c,f); + while (i < precision--) + putc( '0', f); + while (i-- > 0) + putc( tmp[i],f); + while (size-- > 0) + putc( ' ', f); + __res = 0; + return 0; +} + +int _doprnt(const char *fmt, va_list args, FILE *f) +{ + int len; + unsigned long num; + int i, base; + + 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 (; *fmt ; ++fmt) { + if (*fmt != '%') { + putc(*fmt,f); + 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 (isdigit(*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 (isdigit(*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) + putc(' ',f); + putc((unsigned char) va_arg(args, int),f); + while (--field_width > 0) + putc( ' ',f); + continue; + + case 'w': + sw = va_arg(args,short int *); +// DPRINT("L %x\n",sw); + if (sw==NULL) + { +// CHECKPOINT; + s = ""; + while ((*s)!=0) + { + putc( *s++,f); + } +// CHECKPOINT; +// DbgPrint("str %x\n",str); + } + else + { + while ((*sw)!=0) + { + putc( (char)(*sw++),f); + } + } +// CHECKPOINT; + continue; + + case 's': + s = va_arg(args, char *); + if (!s) + s = ""; + + len = strnlen(s, precision); + + if (!(flags & LEFT)) + while (len < field_width--) + putc( ' ', f); + for (i = 0; i < len; ++i) + putc( *s++,f); + while (len < field_width--) + putc( ' ', f); + continue; + + case 'p': + if (field_width == -1) { + field_width = 2*sizeof(void *); + flags |= ZEROPAD; + } + number(f, + (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 != '%') + putc( '%', f); + if (*fmt) + putc( *fmt, f); + 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); + number(f, num, base, field_width, precision, flags); + } + //putc('\0',f); + return 0; +} + + + diff --git a/reactos/lib/crtdll/stdio/doscan.c b/reactos/lib/crtdll/stdio/doscan.c new file mode 100644 index 00000000000..0246644d423 --- /dev/null +++ b/reactos/lib/crtdll/stdio/doscan.c @@ -0,0 +1,404 @@ +/* Copyright (C) 1997 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include + +long double +_atold(const char *ascii); + + +// dubious variable +int _fltused = 0; + +int +_doscan_low(FILE *iop, int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), + const char *fmt, void **argp); + +//#include + +#define SPC 01 +#define STP 02 + +#define SHORT 0 +#define REGULAR 1 +#define LONG 2 +#define LONGDOUBLE 4 +#define INT 0 +#define FLOAT 1 + + + +static int _innum(int **ptr, int type, int len, int size, FILE *iop, + int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), + int *eofptr); +static int _instr(char *ptr, int type, int len, FILE *iop, + int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), + int *eofptr); +static const char *_getccl(const unsigned char *s); + +static char _sctab[256] = { + 0,0,0,0,0,0,0,0, + 0,SPC,SPC,SPC,SPC,SPC,0,0, + 0,0,0,0,0,0,0,0, + 0,0,0,0,0,0,0,0, + SPC,0,0,0,0,0,0,0, + 0,0,0,0,0,0,0,0, + 0,0,0,0,0,0,0,0, + 0,0,0,0,0,0,0,0, +}; + +static int nchars = 0; + +int +_doscan(FILE *iop, const char *fmt, void **argp) +{ + return(_doscan_low(iop, fgetc, ungetc, fmt, argp)); +} + +int +_doscan_low(FILE *iop, int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), + const char *fmt, void **argp) +{ + register int ch; + int nmatch, len, ch1; + int **ptr, fileended, size; + + nchars = 0; + nmatch = 0; + fileended = 0; + for (;;) switch (ch = *fmt++) { + case '\0': + return (nmatch); + case '%': + if ((ch = *fmt++) == '%') + goto def; + ptr = 0; + if (ch != '*') + ptr = (int **)argp++; + else + ch = *fmt++; + len = 0; + size = REGULAR; + while (isdigit(ch)) { + len = len*10 + ch - '0'; + ch = *fmt++; + } + if (len == 0) + len = 30000; + + if (ch=='l') + { + size = LONG; + ch = *fmt++; + if (ch=='l') + { + size = LONGDOUBLE; /* for long long 'll' format */ + ch = *fmt++; + } + } + else if (ch=='h') { + size = SHORT; + ch = *fmt++; + } else if (ch=='L') { + size = LONGDOUBLE; + ch = *fmt++; + } else if (ch=='[') + fmt = _getccl((const unsigned char *)fmt); + if (isupper(ch)) { + /* ch = tolower(ch); + gcc gives warning: ANSI C forbids braced + groups within expressions */ + ch += 'a' - 'A'; + if (size==LONG) + size = LONGDOUBLE; + else if (size != LONGDOUBLE) + size = LONG; + } + if (ch == '\0') + return(-1); + + if (ch == 'n') + { + if (!ptr) + break; + if (size==LONG) + **(long**)ptr = nchars; + else if (size==SHORT) + **(short**)ptr = nchars; + else if (size==LONGDOUBLE) + **(long**)ptr = nchars; + else + **(int**)ptr = nchars; + break; + } + + if (_innum(ptr, ch, len, size, iop, scan_getc, scan_ungetc, + &fileended)) + { + if (ptr) + nmatch++; + } + else + { + if (fileended && nmatch==0) + return(-1); + return(nmatch); + } + break; + case ' ': + case '\n': + case '\t': + case '\r': + case '\f': + case '\v': + while (((nchars++, ch1 = scan_getc(iop))!=EOF) && (_sctab[ch1] & SPC)) + ; + if (ch1 != EOF) + { + scan_ungetc(ch1, iop); + } + nchars--; + break; + + default: + def: + ch1 = scan_getc(iop); + if (ch1 != EOF) nchars++; + if (ch1 != ch) { + if (ch1==EOF) + return(nmatch? nmatch: -1); + scan_ungetc(ch1, iop); + nchars--; + return(nmatch); + } + } +} + +static int +_innum(int **ptr, int type, int len, int size, FILE *iop, + int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), int *eofptr) +{ + register char *np; + char numbuf[64]; + register int c, base; + int expseen, scale, negflg, c1, ndigit; + long lcval; + int cpos; + + if (type=='c' || type=='s' || type=='[') + return(_instr(ptr? *(char **)ptr: (char *)NULL, type, len, + iop, scan_getc, scan_ungetc, eofptr)); + lcval = 0; + ndigit = 0; + scale = INT; + if (type=='e'||type=='f'||type=='g') + scale = FLOAT; + base = 10; + if (type=='o') + base = 8; + else if (type=='x') + base = 16; + np = numbuf; + expseen = 0; + negflg = 0; + while (((nchars++, c = scan_getc(iop)) != EOF) && (_sctab[c] & SPC)) + ; + if (c == EOF) nchars--; + if (c=='-') { + negflg++; + *np++ = c; + c = scan_getc(iop); + nchars++; + len--; + } else if (c=='+') { + len--; + c = scan_getc(iop); + nchars++; + } + cpos = 0; + for ( ; --len>=0; *np++ = c, c = scan_getc(iop), nchars++) { + cpos++; + if (c == '0' && cpos == 1 && type == 'i') + base = 8; + if ((c == 'x' || c == 'X') && (type == 'i' || type == 'x') + && cpos == 2 && lcval == 0) + { + base = 16; + continue; + } + if (isdigit(c) + || (base==16 && (('a'<=c && c<='f') || ('A'<=c && c<='F')))) { + ndigit++; + if (base==8) + lcval <<=3; + else if (base==10) + lcval = ((lcval<<2) + lcval)<<1; + else + lcval <<= 4; + c1 = c; + if (isdigit(c)) + c -= '0'; + else if ('a'<=c && c<='f') + c -= 'a'-10; + else + c -= 'A'-10; + lcval += c; + c = c1; + continue; + } else if (c=='.') { + if (base!=10 || scale==INT) + break; + ndigit++; + continue; + } else if ((c=='e'||c=='E') && expseen==0) { + if (base!=10 || scale==INT || ndigit==0) + break; + expseen++; + *np++ = c; + c = scan_getc(iop); + nchars++; + if (c!='+'&&c!='-'&&('0'>c||c>'9')) + break; + } else + break; + } + if (negflg) + lcval = -lcval; + if (c != EOF) { + scan_ungetc(c, iop); + *eofptr = 0; + } else + *eofptr = 1; + nchars--; + if (np==numbuf || (negflg && np==numbuf+1) ) /* gene dykes*/ + return(0); + if (ptr==NULL) + return(1); + *np++ = 0; + switch((scale<<4) | size) { + + case (FLOAT<<4) | SHORT: + case (FLOAT<<4) | REGULAR: + **(float **)ptr = (float)atof(numbuf); + break; + + case (FLOAT<<4) | LONG: + **(double **)ptr = atof(numbuf); + break; + + case (FLOAT<<4) | LONGDOUBLE: + **(long double **)ptr = _atold(numbuf); + break; + + case (INT<<4) | SHORT: + **(short **)ptr = (short)lcval; + break; + + case (INT<<4) | REGULAR: + **(int **)ptr = (int)lcval; + break; + + case (INT<<4) | LONG: + **(long **)ptr = lcval; + break; + + case (INT<<4) | LONGDOUBLE: + **(long **)ptr = lcval; + break; + } + return(1); +} + +static int +_instr(char *ptr, int type, int len, FILE *iop, + int (*scan_getc)(FILE *), int (*scan_ungetc)(int, FILE *), int *eofptr) +{ + register int ch; + register char *optr; + int ignstp; + + *eofptr = 0; + optr = ptr; + if (type=='c' && len==30000) + len = 1; + ignstp = 0; + if (type=='s') + ignstp = SPC; + while ((nchars++, ch = scan_getc(iop)) != EOF && _sctab[ch] & ignstp) + ; + ignstp = SPC; + if (type=='c') + ignstp = 0; + else if (type=='[') + ignstp = STP; + while (ch!=EOF && (_sctab[ch]&ignstp)==0) { + if (ptr) + *ptr++ = ch; + if (--len <= 0) + break; + ch = scan_getc(iop); + nchars++; + } + if (ch != EOF) { + if (len > 0) + { + scan_ungetc(ch, iop); + nchars--; + } + *eofptr = 0; + } else + { + nchars--; + *eofptr = 1; + } + if (!ptr) + return(1); + if (ptr!=optr) { + if (type!='c') + *ptr++ = '\0'; + return(1); + } + return(0); +} + +static const char * +_getccl(const unsigned char *s) +{ + register int c, t; + + t = 0; + if (*s == '^') { + t++; + s++; + } + for (c = 0; c < (sizeof _sctab / sizeof _sctab[0]); c++) + if (t) + _sctab[c] &= ~STP; + else + _sctab[c] |= STP; + if ((c = *s) == ']' || c == '-') { /* first char is special */ + if (t) + _sctab[c] |= STP; + else + _sctab[c] &= ~STP; + s++; + } + while ((c = *s++) != ']') { + if (c==0) + return((const char *)--s); + else if (c == '-' && *s != ']' && s[-2] < *s) { + for (c = s[-2] + 1; c < *s; c++) + if (t) + _sctab[c] |= STP; + else + _sctab[c] &= ~STP; + } else if (t) + _sctab[c] |= STP; + else + _sctab[c] &= ~STP; + } + return((const char *)s); +} diff --git a/reactos/lib/crtdll/stdio/fclose.c b/reactos/lib/crtdll/stdio/fclose.c new file mode 100644 index 00000000000..4b00dc818ae --- /dev/null +++ b/reactos/lib/crtdll/stdio/fclose.c @@ -0,0 +1,45 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +#include +#include +//#include +#include + +#ifndef __dj_include_stdio_h_ +#define _name_to_remove _tmpfname +#endif + +int +fclose(FILE *f) +{ + int r; + + r = EOF; + if (!f) + return r; + if (f->_flag & (_IOREAD|_IOWRT|_IORW) + && !(f->_flag&_IOSTRG)) + { + r = fflush(f); + if (_close(fileno(f)) < 0) + r = EOF; + if (f->_flag&_IOMYBUF) + free(f->_base); + } + if (f->_flag & _IORMONCL && f->_name_to_remove) + { + remove(f->_name_to_remove); + free(f->_name_to_remove); + f->_name_to_remove = 0; + } + f->_cnt = 0; + f->_base = 0; + f->_ptr = 0; + f->_bufsiz = 0; + f->_flag = 0; + f->_file = -1; + return r; +} diff --git a/reactos/lib/crtdll/stdio/fdopen.c b/reactos/lib/crtdll/stdio/fdopen.c new file mode 100644 index 00000000000..a19f3a8a8ba --- /dev/null +++ b/reactos/lib/crtdll/stdio/fdopen.c @@ -0,0 +1,55 @@ +#include + +FILE *fdopen(int handle, char *mode) +{ + FILE *file; + int rw; + + if ( handle == 0 ) + return stdin; + + if ( handle == 1 ) + return stdout; + + if ( handle == 2 ) + return stderr; + + if ( handle == 3 ) + return stdaux; + + if ( handle == 4 ) + return stdprn; + + file = __alloc_file(); + if (f == NULL) + return NULL; + file->_file = handle; + + rw = (mode[1] == '+') || (mode[1] && (mode[2] == '+')); + + if (*mode == 'a') + lseek(fd, 0, SEEK_END); + + file->_cnt = 0; + file->_file = handle; + file->_bufsiz = 0; + if (rw) + file->_flag = _IORW; + else if (*mode == 'r') + file->_flag = _IOREAD; + else + file->_flag = _IOWRT; + + file->_base = f->_ptr = NULL; + return file; +} + + + + + + + + + + \ No newline at end of file diff --git a/reactos/lib/crtdll/stdio/feof.c b/reactos/lib/crtdll/stdio/feof.c new file mode 100644 index 00000000000..e9d8122c324 --- /dev/null +++ b/reactos/lib/crtdll/stdio/feof.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef feof +int +feof(FILE *stream) +{ + return stream->_flag & _IOEOF; +} diff --git a/reactos/lib/crtdll/stdio/ferror.c b/reactos/lib/crtdll/stdio/ferror.c new file mode 100644 index 00000000000..5727f47ed76 --- /dev/null +++ b/reactos/lib/crtdll/stdio/ferror.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef ferror +int +ferror(FILE *stream) +{ + return stream->_flag & _IOERR; +} diff --git a/reactos/lib/crtdll/stdio/fflush.c b/reactos/lib/crtdll/stdio/fflush.c new file mode 100644 index 00000000000..5f3273f6d38 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fflush.c @@ -0,0 +1,56 @@ +/* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +#include +#include +//#include +#include +#include + +int +fflush(FILE *f) +{ + char *base; + int n, rn; + + if (f == NULL) + { + int e = errno; + + errno = 0; + _fwalk((void (*)(FILE *))fflush); + if (errno) + return EOF; + errno = e; + return 0; + } + + f->_flag &= ~_IOUNGETC; + if ((f->_flag&(_IONBF|_IOWRT))==_IOWRT + && (base = f->_base) != NULL + && (rn = n = f->_ptr - base) > 0) + { + f->_ptr = base; + f->_cnt = (f->_flag&(_IOLBF|_IONBF)) ? 0 : f->_bufsiz; + do { + n = _write(fileno(f), base, rn); + if (n <= 0) { + f->_flag |= _IOERR; + return EOF; + } + rn -= n; + base += n; + } while (rn > 0); + } + if (f->_flag & _IORW) + { + f->_cnt = 0; + f->_flag &= ~(_IOWRT|_IOREAD); + f->_ptr = f->_base; + } + return 0; +} diff --git a/reactos/lib/crtdll/stdio/fgetc.c b/reactos/lib/crtdll/stdio/fgetc.c new file mode 100644 index 00000000000..1d6f413bebc --- /dev/null +++ b/reactos/lib/crtdll/stdio/fgetc.c @@ -0,0 +1,9 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +fgetc(FILE *f) +{ + return getc(f); +} diff --git a/reactos/lib/crtdll/stdio/fgetpos.c b/reactos/lib/crtdll/stdio/fgetpos.c new file mode 100644 index 00000000000..fb3c3c19cbb --- /dev/null +++ b/reactos/lib/crtdll/stdio/fgetpos.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +fgetpos(FILE *stream, fpos_t *pos) +{ + if (stream && pos) + { + *pos = (fpos_t)ftell(stream); + return 0; + } + errno = EFAULT; + return 1; +} diff --git a/reactos/lib/crtdll/stdio/fgets.c b/reactos/lib/crtdll/stdio/fgets.c new file mode 100644 index 00000000000..05ddd9565f6 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fgets.c @@ -0,0 +1,22 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +char * +fgets(char *s, int n, FILE *f) +{ + int c=0; + char *cs; + + cs = s; + while (--n>0 && (c = getc(f)) != EOF) + { + *cs++ = c; + if (c == '\n') + break; + } + if (c == EOF && cs == s) + return NULL; + *cs++ = '\0'; + return s; +} diff --git a/reactos/lib/crtdll/stdio/filbuf.c b/reactos/lib/crtdll/stdio/filbuf.c new file mode 100644 index 00000000000..66f9b5813e8 --- /dev/null +++ b/reactos/lib/crtdll/stdio/filbuf.c @@ -0,0 +1,110 @@ +/* Copyright (C) 1997 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +//#include +#include +//#include +#include +//#include +#include + +/* Note: We set _fillsize to 512, and use that for reading instead of + _bufsize, for performance reasons. We double _fillsize each time + we read here, and reset it to 512 each time we call fseek. That + way, we don't waste time reading data we won't use, or doing lots + of small reads we could optimize. If we do lots of seeking, we'll + end up maintaining small read sizes, but if we don't seek, we'll + eventually read blocks as large as the transfer buffer. */ + +int +_filbuf(FILE *f) +{ + int size, fillsize; + char c; + + if (f->_flag & _IORW) + f->_flag |= _IOREAD; + + if ((f->_flag&_IOREAD) == 0) + return EOF; + if (f->_flag&(_IOSTRG|_IOEOF)) + return EOF; + f->_flag &= ~_IOUNGETC; + + if (f->_base==NULL && (f->_flag&_IONBF)==0) { +// size = _go32_info_block.size_of_transfer_buffer; + size = 512; + if ((f->_base = malloc(size)) == NULL) + { + f->_flag |= _IONBF; + f->_flag &= ~(_IOFBF|_IOLBF); + } + else + { + f->_flag |= _IOMYBUF; + f->_bufsiz = size; +// f->_fillsize = 512; + } + } + + if (f->_flag&_IONBF) + f->_base = &c; + + if (f == stdin) { + if (stdout->_flag&_IOLBF) + fflush(stdout); + if (stderr->_flag&_IOLBF) + fflush(stderr); + } + + /* don't read too much! */ + //if (f->_fillsize > f->_bufsiz) + // f->_fillsize = f->_bufsiz; + + /* This next bit makes it so that the cumulative amount read always + aligns with file cluster boundaries; i.e. 512, then 2048 + (512+1536), then 4096 (2048+2048) etc. */ + //fillsize = f->_fillsize; + fillsize = f->_bufsiz; + if (fillsize == 1024 && f->_bufsiz >= 1536) + fillsize = 1536; + + f->_cnt = _read(fileno(f), f->_base, + f->_flag & _IONBF ? 1 : fillsize); + + /* Read more next time, if we don't seek */ +// if (f->_fillsize < f->_bufsiz) +// f->_fillsize *= 2; + + if(__is_text_file(f) && f->_cnt>0) + { + /* truncate text file at Ctrl-Z */ + char *cz=memchr(f->_base, 0x1A, f->_cnt); + if(cz) + { + int newcnt = cz - f->_base; + lseek(fileno(f), -(f->_cnt - newcnt), SEEK_CUR); + f->_cnt = newcnt; + } + } + f->_ptr = f->_base; + if (f->_flag & _IONBF) + f->_base = NULL; + if (--f->_cnt < 0) { + if (f->_cnt == -1) { + f->_flag |= _IOEOF; + if (f->_flag & _IORW) + f->_flag &= ~_IOREAD; + } else + f->_flag |= _IOERR; + f->_cnt = 0; + return EOF; + } + return *f->_ptr++ & 0377; +} + + diff --git a/reactos/lib/crtdll/stdio/flsbuf.c b/reactos/lib/crtdll/stdio/flsbuf.c new file mode 100644 index 00000000000..1cbfedc4669 --- /dev/null +++ b/reactos/lib/crtdll/stdio/flsbuf.c @@ -0,0 +1,100 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +//#include +//#include +#include +#include + +int +_flsbuf(int c, FILE *f) +{ + char *base; + int n, rn; + char c1; + int size; + + if (f->_flag & _IORW) + { + f->_flag |= _IOWRT; + f->_flag &= ~(_IOEOF|_IOREAD); + } + + if ((f->_flag&_IOWRT)==0) + return EOF; + + /* if the buffer is not yet allocated, allocate it */ + if ((base = f->_base) == NULL && (f->_flag & _IONBF) == 0) + { +// size = _go32_info_block.size_of_transfer_buffer; + size = 512; + if ((f->_base = base = malloc (size)) == NULL) + { + f->_flag |= _IONBF; + f->_flag &= ~(_IOFBF|_IOLBF); + } + else + { + f->_flag |= _IOMYBUF; + f->_cnt = f->_bufsiz = size; + f->_ptr = base; + rn = 0; + if (f == stdout && isatty (fileno (stdout))) + f->_flag |= _IOLBF; + } + } + + if (f->_flag & _IOLBF) + { + /* in line-buffering mode we get here on each character */ + *f->_ptr++ = c; + rn = f->_ptr - base; + if (c == '\n' || rn >= f->_bufsiz) + { + /* time for real flush */ + f->_ptr = base; + f->_cnt = 0; + } + else + { + /* we got here because _cnt is wrong, so fix it */ + /* Negative _cnt causes all output functions + to call _flsbuf for each character, thus realizing line-buffering */ + f->_cnt = -rn; + return c; + } + } + else if (f->_flag & _IONBF) + { + c1 = c; + rn = 1; + base = &c1; + f->_cnt = 0; + } + else /* _IOFBF */ + { + rn = f->_ptr - base; + f->_ptr = base; + f->_cnt = f->_bufsiz; + } + while (rn > 0) + { + n = _write(fileno(f), base, rn); + if (n <= 0) + { + f->_flag |= _IOERR; + return EOF; + } + rn -= n; + base += n; + } + if ((f->_flag&(_IOLBF|_IONBF)) == 0) + { + f->_cnt--; + *f->_ptr++ = c; + } + return c; +} diff --git a/reactos/lib/crtdll/stdio/fopen.c b/reactos/lib/crtdll/stdio/fopen.c new file mode 100644 index 00000000000..a2121282968 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fopen.c @@ -0,0 +1,78 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +#include +//#include +#include +//#include +//#include + +FILE * __alloc_file(void); + +extern int _fmode; + +FILE * +fopen(const char *file, const char *mode) +{ + FILE *f; + int fd, rw, oflags = 0; + char tbchar; + + if (file == 0) + return 0; + if (mode == 0) + return 0; + + f = __alloc_file(); + if (f == NULL) + return NULL; + + rw = (mode[1] == '+') || (mode[1] && (mode[2] == '+')); + + switch (*mode) + { + case 'a': + oflags = O_CREAT | (rw ? O_RDWR : O_WRONLY); + break; + case 'r': + oflags = rw ? O_RDWR : O_RDONLY; + break; + case 'w': + oflags = O_TRUNC | O_CREAT | (rw ? O_RDWR : O_WRONLY); + break; + default: + return (NULL); + } + if (mode[1] == '+') + tbchar = mode[2]; + else + tbchar = mode[1]; + if (tbchar == 't') + oflags |= O_TEXT; + else if (tbchar == 'b') + oflags |= O_BINARY; + else + oflags |= (_fmode & (O_TEXT|O_BINARY)); + + fd = _open(file, oflags, 0); + if (fd < 0) + return NULL; + + if (*mode == 'a') + lseek(fd, 0, SEEK_END); + + f->_cnt = 0; + f->_file = fd; + f->_bufsiz = 0; + if (rw) + f->_flag = _IORW; + else if (*mode == 'r') + f->_flag = _IOREAD; + else + f->_flag = _IOWRT; + + f->_base = f->_ptr = NULL; + return f; +} diff --git a/reactos/lib/crtdll/stdio/fprintf.c b/reactos/lib/crtdll/stdio/fprintf.c new file mode 100644 index 00000000000..fbca105d4ed --- /dev/null +++ b/reactos/lib/crtdll/stdio/fprintf.c @@ -0,0 +1,26 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +fprintf(register FILE *iop, const char *fmt, ...) +{ + int len; + char localbuf[BUFSIZ]; + + if (iop->_flag & _IONBF) + { + iop->_flag &= ~_IONBF; + iop->_ptr = iop->_base = localbuf; + iop->_bufsiz = BUFSIZ; + len = _doprnt(fmt, (&fmt)+1, iop); + fflush(iop); + iop->_flag |= _IONBF; + iop->_base = NULL; + iop->_bufsiz = 0; + iop->_cnt = 0; + } + else + len = _doprnt(fmt, (&fmt)+1, iop); + return ferror(iop) ? EOF : len; +} diff --git a/reactos/lib/crtdll/stdio/fputc.c b/reactos/lib/crtdll/stdio/fputc.c new file mode 100644 index 00000000000..6dd5e9b58f8 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fputc.c @@ -0,0 +1,9 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +fputc(int c, FILE *fp) +{ + return putc(c, fp); +} diff --git a/reactos/lib/crtdll/stdio/fputs.c b/reactos/lib/crtdll/stdio/fputs.c new file mode 100644 index 00000000000..60b030b4b33 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fputs.c @@ -0,0 +1,42 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +int +fputs(const char *s, FILE *f) +{ + /* + int r = 0; + int c; + int unbuffered; + char localbuf[BUFSIZ]; + + unbuffered = f->_flag & _IONBF; + if (unbuffered) + { + f->_flag &= ~_IONBF; + f->_ptr = f->_base = localbuf; + f->_bufsiz = BUFSIZ; + } + + while ((c = *s++)) + r = putc(c, f); + + if (unbuffered) + { + fflush(f); + f->_flag |= _IONBF; + f->_base = NULL; + f->_bufsiz = 0; + f->_cnt = 0; + } + + return(r); + */ + int r = 0; + if ( !WriteFile(filehnd(f->_file),s,strlen(s),&r,NULL) ) + return -1; + + return r; +} diff --git a/reactos/lib/crtdll/stdio/fread.c b/reactos/lib/crtdll/stdio/fread.c new file mode 100644 index 00000000000..5bf9163ccb8 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fread.c @@ -0,0 +1,89 @@ +/* Copyright (C) 1997 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include + +#define _fillsize _bufsiz + +size_t +fread(void *vptr, size_t size, size_t count, FILE *iop) +{ + char *ptr = (char *)vptr; + int s; + int c; + + /* grow if we know we're asking for a lot, even if it's in the + buffer, since we'll probably read chunks this size for a while */ + while (size*count > iop->_fillsize + && iop->_fillsize < iop->_bufsiz) + { + if (iop->_fillsize < 512) + iop->_fillsize = 512; + iop->_fillsize *= 2; + } + + s = size * count; + if(!__is_text_file(iop)) + { + while (s > 0) { + if (iop->_cnt < s) { + if (iop->_cnt > 0) { + memcpy(ptr, iop->_ptr, iop->_cnt); + ptr += iop->_cnt; + s -= iop->_cnt; + } + /* + * filbuf clobbers _cnt & _ptr, + * so don't waste time setting them. + */ + if ((c = _filbuf(iop)) == EOF) + break; + *ptr++ = c; + s--; + } + if (iop->_cnt >= s) { + memcpy(ptr, iop->_ptr, s); + iop->_ptr += s; + iop->_cnt -= s; + return count; + } + } + } + else + { + while (s > 0) { + if (iop->_cnt < s) { + while (iop->_cnt > 0) { + if ((c = *iop->_ptr++) != '\r') + { + *ptr++ = c; + s--; + } + iop->_cnt--; + } + if ((c = _filbuf(iop)) == EOF) + break; + if (c != '\r') + { + *ptr++ = c; + s--; + } + } + if (iop->_cnt >= s) { + while (s > 0 && iop->_cnt > 0) { + if ((c = *iop->_ptr++) != '\r') + { + *ptr++ = c; + s--; + } + iop->_cnt--; + } + } + } /* end while */ + } + return size != 0 ? count - ((s + size - 1) / size) : 0; +} + diff --git a/reactos/lib/crtdll/stdio/freopen.c b/reactos/lib/crtdll/stdio/freopen.c new file mode 100644 index 00000000000..6940e852764 --- /dev/null +++ b/reactos/lib/crtdll/stdio/freopen.c @@ -0,0 +1,68 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +//#include +#include +#include + +extern int _fmode; + +FILE * +freopen(const char *file, const char *mode, FILE *f) +{ + int fd, rw, oflags=0; + char tbchar; + + if (file == 0 || mode == 0 || f == 0) + return 0; + + rw = (mode[1] == '+'); + + fclose(f); + + switch (*mode) { + case 'a': + oflags = O_CREAT | (rw ? O_RDWR : O_WRONLY); + break; + case 'r': + oflags = rw ? O_RDWR : O_RDONLY; + break; + case 'w': + oflags = O_TRUNC | O_CREAT | (rw ? O_RDWR : O_WRONLY); + break; + default: + return NULL; + } + if (mode[1] == '+') + tbchar = mode[2]; + else + tbchar = mode[1]; + if (tbchar == 't') + oflags |= O_TEXT; + else if (tbchar == 'b') + oflags |= O_BINARY; + else + oflags |= (_fmode & (O_TEXT|O_BINARY)); + + fd = _open(file, oflags, 0666); + if (fd < 0) + return NULL; + + if (*mode == 'a') + lseek(fd, 0, SEEK_END); + + f->_cnt = 0; + f->_file = fd; + f->_bufsiz = 0; + if (rw) + f->_flag = _IORW; + else if (*mode == 'r') + f->_flag = _IOREAD; + else + f->_flag = _IOWRT; + + f->_base = f->_ptr = NULL; + return f; +} diff --git a/reactos/lib/crtdll/stdio/frlist.c b/reactos/lib/crtdll/stdio/frlist.c new file mode 100644 index 00000000000..2eaacbd75e3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/frlist.c @@ -0,0 +1,11 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +//#include + +static __file_rec __initial_file_rec = { + 0, + 5, +{ stdin, stdout, stderr, stdprn, stdaux } +}; + +__file_rec *__file_rec_list = &__initial_file_rec; diff --git a/reactos/lib/crtdll/stdio/fscanf.c b/reactos/lib/crtdll/stdio/fscanf.c new file mode 100644 index 00000000000..7b69cdde5e4 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fscanf.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +int +fscanf(FILE *f, const char *fmt, ...) +{ + int r; + va_list a=0; + va_start(a, fmt); + r = _doscan(f, fmt, a); + va_end(a); + return r; +} diff --git a/reactos/lib/crtdll/stdio/fseek.c b/reactos/lib/crtdll/stdio/fseek.c new file mode 100644 index 00000000000..939718b36e7 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fseek.c @@ -0,0 +1,57 @@ +/* Copyright (C) 1997 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ + +#include +#include +#include +#include + +#define _fillsize _bufsiz + +int +fseek(FILE *f, long offset, int ptrname) +{ + long p = -1; /* can't happen? */ + + /* See comment in filbuf.c */ + f->_fillsize = 512; + + f->_flag &= ~_IOEOF; + if (f->_flag & _IOREAD) + { + if (f->_base && !(f->_flag & _IONBF)) + { + p = ftell(f); + if (ptrname == SEEK_CUR) + { + offset += p; + ptrname = SEEK_SET; + } + /* check if the target position is in the buffer and + optimize seek by moving inside the buffer */ + if (ptrname == SEEK_SET && (f->_flag & (_IOUNGETC|_IORW)) == 0 + && p-offset <= f->_ptr-f->_base && offset-p <= f->_cnt) + { + f->_ptr+=offset-p; + f->_cnt+=p-offset; + return 0; + } + } + + if (f->_flag & _IORW) + f->_flag &= ~_IOREAD; + + p = lseek(fileno(f), offset, ptrname); + f->_cnt = 0; + f->_ptr = f->_base; + f->_flag &= ~_IOUNGETC; + } + else if (f->_flag & (_IOWRT|_IORW)) + { + p = fflush(f); + return lseek(fileno(f), offset, ptrname) == -1 || p == EOF ? + -1 : 0; + } + return p==-1 ? -1 : 0; +} diff --git a/reactos/lib/crtdll/stdio/fsetpos.c b/reactos/lib/crtdll/stdio/fsetpos.c new file mode 100644 index 00000000000..63001cb96eb --- /dev/null +++ b/reactos/lib/crtdll/stdio/fsetpos.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +fsetpos(FILE *stream, const fpos_t *pos) +{ + if (stream && pos) + { + fseek(stream, (long)(*pos), SEEK_SET); + return 0; + } + errno = EFAULT; + return 1; +} diff --git a/reactos/lib/crtdll/stdio/ftell.c b/reactos/lib/crtdll/stdio/ftell.c new file mode 100644 index 00000000000..d597bc5acfb --- /dev/null +++ b/reactos/lib/crtdll/stdio/ftell.c @@ -0,0 +1,35 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +//#include +#include +#include +#include + + +long +ftell(FILE *f) +{ + long tres; + int adjust=0; + + if (f->_cnt < 0) + f->_cnt = 0; + if (f->_flag&_IOREAD) + { + adjust = - f->_cnt; + } + else if (f->_flag&(_IOWRT|_IORW)) + { + if (f->_flag&_IOWRT && f->_base && (f->_flag&_IONBF)==0) + adjust = f->_ptr - f->_base; + } + else + return -1; + tres = lseek(fileno(f), 0L, 1); + if (tres<0) + return tres; + tres += adjust; + return tres; +} diff --git a/reactos/lib/crtdll/stdio/fwalk.c b/reactos/lib/crtdll/stdio/fwalk.c new file mode 100644 index 00000000000..4d4a8622942 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fwalk.c @@ -0,0 +1,25 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +//#include + +#define __FILE_REC_MAX 20 +typedef struct __file_rec { + struct __file_rec *next; + int count; + FILE *files[__FILE_REC_MAX]; +} __file_rec; + +__file_rec *__file_rec_list; + +void +_fwalk(void (*func)(FILE *)) +{ + __file_rec *fr; + int i; + + for (fr=__file_rec_list; fr; fr=fr->next) + for (i=0; icount; i++) + if (fr->files[i]->_flag) + func(fr->files[i]); +} diff --git a/reactos/lib/crtdll/stdio/fwrite.c b/reactos/lib/crtdll/stdio/fwrite.c new file mode 100644 index 00000000000..350dff692a0 --- /dev/null +++ b/reactos/lib/crtdll/stdio/fwrite.c @@ -0,0 +1,88 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include + +size_t +fwrite(const void *vptr, size_t size, size_t count, FILE *f) +{ + const char *ptr = (const char *)vptr; + register int s; + + s = size * count; + if(!__is_text_file(f)) + { + if (f->_flag & _IOLBF) + while (s > 0) { + if (--f->_cnt > -f->_bufsiz && *(const char *)ptr != '\n') + *f->_ptr++ = *(const char *)ptr++; + else if (_flsbuf(*(const char *)ptr++, f) == EOF) + break; + s--; + } + else while (s > 0) { + if (f->_cnt < s) { + if (f->_cnt > 0) { + memcpy(f->_ptr, ptr, f->_cnt); + ptr += f->_cnt; + f->_ptr += f->_cnt; + s -= f->_cnt; + } + if (_flsbuf(*(const unsigned char *)ptr++, f) == EOF) + break; + s--; + } + if (f->_cnt >= s) { + memcpy(f->_ptr, ptr, s); + f->_ptr += s; + f->_cnt -= s; + return count; + } + } + } + else + { + if (f->_flag & _IOLBF) + { + while (s > 0) { + if (*ptr=='\n') + { + if (--f->_cnt > -f->_bufsiz) + *f->_ptr++ = '\r'; + else + if (_flsbuf('\r', f) == EOF) + break; + } + if (--f->_cnt > -f->_bufsiz && *ptr != '\n') + *f->_ptr++ = *ptr++; + else if (_flsbuf(*(const unsigned char *)ptr++, f) == EOF) + break; + s--; + } + } + else + { + while (s > 0) + { + if (*ptr == '\n') + { + if(--f->_cnt >= 0) + *f->_ptr++ = '\r'; + else + if (_flsbuf('\r', f) == EOF) + break; + } + if (--f->_cnt >= 0) + *f->_ptr++ = *ptr++; + else + if (_flsbuf(*(const unsigned char *)ptr++, f) == EOF) + break; + s--; + } + } + } + return size != 0 ? count - ((s + size - 1) / size) : 0; +} + diff --git a/reactos/lib/crtdll/stdio/getc.c b/reactos/lib/crtdll/stdio/getc.c new file mode 100644 index 00000000000..4ce616df089 --- /dev/null +++ b/reactos/lib/crtdll/stdio/getc.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +#undef getc +int getc(FILE *f) +{ + int c; + DWORD NumberOfBytesRead; + if ( !ReadFile(filehnd(f->_file),&c, 1, &NumberOfBytesRead, NULL) ) + return -1; + if ( NumberOfBytesRead == 0 ) + return -1; + return c; +} diff --git a/reactos/lib/crtdll/stdio/getchar.c b/reactos/lib/crtdll/stdio/getchar.c new file mode 100644 index 00000000000..e087c430f02 --- /dev/null +++ b/reactos/lib/crtdll/stdio/getchar.c @@ -0,0 +1,10 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef getchar +int +getchar(void) +{ + return getc(stdin); +} diff --git a/reactos/lib/crtdll/stdio/getenv.c b/reactos/lib/crtdll/stdio/getenv.c new file mode 100644 index 00000000000..fbbb27a8834 --- /dev/null +++ b/reactos/lib/crtdll/stdio/getenv.c @@ -0,0 +1,16 @@ +#include +#include + +void *malloc(size_t size); + + + +char *getenv(const char *name) +{ + char *buffer; + buffer = (char *)malloc(MAX_PATH); + buffer[0] = 0; + if ( GetEnvironmentVariableA(name,buffer,MAX_PATH) == 0 ) + return NULL; + return buffer; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/stdio/gets.c b/reactos/lib/crtdll/stdio/gets.c new file mode 100644 index 00000000000..cccdf637213 --- /dev/null +++ b/reactos/lib/crtdll/stdio/gets.c @@ -0,0 +1,17 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +char * +gets(char *s) +{ + int c; + char *cs; + + cs = s; + while ((c = getchar()) != '\n' && c != EOF) + *cs++ = c; + if (c == EOF && cs==s) + return NULL; + *cs++ = '\0'; + return s; +} diff --git a/reactos/lib/crtdll/stdio/getw.c b/reactos/lib/crtdll/stdio/getw.c new file mode 100644 index 00000000000..a8dd3818150 --- /dev/null +++ b/reactos/lib/crtdll/stdio/getw.c @@ -0,0 +1,18 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +getw(FILE *f) +{ + int i; + char *p; + int w; + + p = (char *)&w; + for (i=sizeof(int); --i>=0;) + *p++ = getc(f); + if (feof(f)) + return EOF; + return w; +} diff --git a/reactos/lib/crtdll/stdio/perror.c b/reactos/lib/crtdll/stdio/perror.c new file mode 100644 index 00000000000..7e55f7521b3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/perror.c @@ -0,0 +1,13 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + + + +void +perror(const char *s) +{ + + fprintf(stderr, "%s: %s\n", s, _strerror(NULL)); +} diff --git a/reactos/lib/crtdll/stdio/printf.c b/reactos/lib/crtdll/stdio/printf.c new file mode 100644 index 00000000000..0666bfb2e10 --- /dev/null +++ b/reactos/lib/crtdll/stdio/printf.c @@ -0,0 +1,19 @@ +/* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +int +printf(const char *fmt, ...) +{ + int len; + + len = _doprnt(fmt, (&fmt)+1, stdout); + + /* People were confused when printf() didn't flush stdout, + so we'll do it to reduce confusion */ + if (stdout->_flag & _IOLBF) + fflush(stdout); + + return ferror(stdout) ? EOF : len; +} diff --git a/reactos/lib/crtdll/stdio/putc.c b/reactos/lib/crtdll/stdio/putc.c new file mode 100644 index 00000000000..7db1d620ab1 --- /dev/null +++ b/reactos/lib/crtdll/stdio/putc.c @@ -0,0 +1,28 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +#undef putc +int putc(int c, FILE *fp) +{ + + int r; + +// if(c =='\n' && __is_text_file(fp)) +// putc('\r',fp); + + + if ( ((fp->_flag) & _IOSTRG) == _IOSTRG) { + if(fp->_cnt>0) + { + fp->_cnt--; + return((unsigned char)(*(fp->_ptr++)=(unsigned char)c)); + } + return(_flsbuf(c,fp)); + } + if ( !WriteFile(filehnd(fp->_file),&c,1,&r,NULL) ) + return -1; + return r; + +} diff --git a/reactos/lib/crtdll/stdio/putchar.c b/reactos/lib/crtdll/stdio/putchar.c new file mode 100644 index 00000000000..d2a2fab8c2c --- /dev/null +++ b/reactos/lib/crtdll/stdio/putchar.c @@ -0,0 +1,22 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/conio/getch.c + * PURPOSE: Writes a character to stdout + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include + +#undef putc +#undef putchar +int +putchar(int c) +{ + int r = putc(c, stdout); + if (stdout->_flag & _IOLBF) + fflush(stdout); + return r; +} diff --git a/reactos/lib/crtdll/stdio/puts.c b/reactos/lib/crtdll/stdio/puts.c new file mode 100644 index 00000000000..6df4b63a4e3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/puts.c @@ -0,0 +1,21 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +#undef putchar +int +puts(const char *s) +{ + /* + int c; + + while ((c = *s++)) + putchar(c); + return putchar('\n'); + */ + int r = 0; + if ( !WriteFile(filehnd(stdout->_file),s,strlen(s),&r,NULL) ) + return -1; + + return putchar('\n');; +} diff --git a/reactos/lib/crtdll/stdio/putw.c b/reactos/lib/crtdll/stdio/putw.c new file mode 100644 index 00000000000..6d6f0966698 --- /dev/null +++ b/reactos/lib/crtdll/stdio/putw.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +putw(int w, FILE *f) +{ + char *p; + int i; + + p = (char *)&w; + for (i=sizeof(int); --i>=0;) + putc(*p++, f); + return ferror(f); +} diff --git a/reactos/lib/crtdll/stdio/remove.c b/reactos/lib/crtdll/stdio/remove.c new file mode 100644 index 00000000000..6003fb1981b --- /dev/null +++ b/reactos/lib/crtdll/stdio/remove.c @@ -0,0 +1,9 @@ +#include + +int remove(const char *fn) +{ + if (!DeleteFileA(fn)) + return -1; + return 0; +} + \ No newline at end of file diff --git a/reactos/lib/crtdll/stdio/rename.c b/reactos/lib/crtdll/stdio/rename.c new file mode 100644 index 00000000000..d4b1ecbcbe1 --- /dev/null +++ b/reactos/lib/crtdll/stdio/rename.c @@ -0,0 +1,18 @@ +#include +#include +#include + +int rename(const char *old, const char *new) +{ + return _rename(old,new); +} + +int _rename(const char *old, const char *new) +{ + if ( !MoveFile(old,new) ) + return -1; + + return 0; +} + + diff --git a/reactos/lib/crtdll/stdio/rewind.c b/reactos/lib/crtdll/stdio/rewind.c new file mode 100644 index 00000000000..9a9a6817fe3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/rewind.c @@ -0,0 +1,17 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include +#include +#include + + +void rewind(FILE *f) +{ + fflush(f); + lseek(fileno(f), 0L, SEEK_SET); + f->_cnt = 0; + f->_ptr = f->_base; + f->_flag &= ~(_IOERR|_IOEOF); + if (f->_flag & _IORW) + f->_flag &= ~(_IOREAD|_IOWRT); +} diff --git a/reactos/lib/crtdll/stdio/scanf.c b/reactos/lib/crtdll/stdio/scanf.c new file mode 100644 index 00000000000..b907273084e --- /dev/null +++ b/reactos/lib/crtdll/stdio/scanf.c @@ -0,0 +1,15 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +int +scanf(const char *fmt, ...) +{ + int r; + va_list a=0; + va_start(a, fmt); + r = _doscan(stdin, fmt, a); + va_end(a); + return r; +} diff --git a/reactos/lib/crtdll/stdio/setbuf.c b/reactos/lib/crtdll/stdio/setbuf.c new file mode 100644 index 00000000000..1fc7117193a --- /dev/null +++ b/reactos/lib/crtdll/stdio/setbuf.c @@ -0,0 +1,13 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +void +setbuf(FILE *f, char *buf) +{ + if (buf) + setvbuf(f, buf, _IOFBF, BUFSIZ); + else + setvbuf(f, 0, _IONBF, BUFSIZ); +} diff --git a/reactos/lib/crtdll/stdio/setbuffe.c b/reactos/lib/crtdll/stdio/setbuffe.c new file mode 100644 index 00000000000..b69622908d3 --- /dev/null +++ b/reactos/lib/crtdll/stdio/setbuffe.c @@ -0,0 +1,12 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include + +void setbuffer(FILE *f, void *buf, int size) +{ + if (buf) + setvbuf(f, buf, _IOFBF, size); + else + setvbuf(f, 0, _IONBF, 0); +} diff --git a/reactos/lib/crtdll/stdio/setlineb.c b/reactos/lib/crtdll/stdio/setlineb.c new file mode 100644 index 00000000000..c75ef4dd20d --- /dev/null +++ b/reactos/lib/crtdll/stdio/setlineb.c @@ -0,0 +1,7 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +void setlinebuf(FILE *f) +{ + setvbuf(f, 0, _IOLBF, BUFSIZ); +} diff --git a/reactos/lib/crtdll/stdio/setvbuf.c b/reactos/lib/crtdll/stdio/setvbuf.c new file mode 100644 index 00000000000..78dd0fc6888 --- /dev/null +++ b/reactos/lib/crtdll/stdio/setvbuf.c @@ -0,0 +1,55 @@ +/* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include + +#define _fillsize _bufsiz + +int setvbuf(FILE *f, char *buf, int type, size_t len) +{ + int mine=0; + if (!f) + return -1; + fflush(f); + switch (type) + { + case _IOFBF: + case _IOLBF: + if (len <= 0) + return -1; + if (buf == 0) + { + buf = (char *)malloc(len); + if (buf == 0) + return -1; + mine = 1; + } + f->_fillsize = len; /* make it read in `len'-byte chunks */ + /* FALLTHROUGH */ + case _IONBF: + if (f->_base != NULL && f->_flag & _IOMYBUF) + free(f->_base); + f->_cnt = 0; + + f->_flag &= ~(_IONBF|_IOFBF|_IOLBF|_IOUNGETC); + f->_flag |= type; + if (type != _IONBF) + { + if (mine) + f->_flag |= _IOMYBUF; + f->_ptr = f->_base = buf; + f->_bufsiz = len; + } + else + { + f->_base = 0; + f->_bufsiz = 0; + } + return 0; + default: + return -1; + } +} diff --git a/reactos/lib/crtdll/stdio/sprintf.c b/reactos/lib/crtdll/stdio/sprintf.c new file mode 100644 index 00000000000..87039b9a91e --- /dev/null +++ b/reactos/lib/crtdll/stdio/sprintf.c @@ -0,0 +1,19 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + + +int +sprintf(char *str, const char *fmt, ...) +{ + FILE _strbuf; + int len; + + _strbuf._flag = _IOWRT|_IOSTRG; + _strbuf._ptr = str; + _strbuf._cnt = INT_MAX; + len = _doprnt(fmt, &(fmt)+1, &_strbuf); + *_strbuf._ptr = 0; + return len; +} diff --git a/reactos/lib/crtdll/stdio/sscanf.c b/reactos/lib/crtdll/stdio/sscanf.c new file mode 100644 index 00000000000..a2f5651080d --- /dev/null +++ b/reactos/lib/crtdll/stdio/sscanf.c @@ -0,0 +1,26 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +//#include + +int +sscanf(const char *str, const char *fmt, ...) +{ + int r; + va_list a=0; + FILE _strbuf; + + va_start(a, fmt); + + _strbuf._flag = _IOREAD|_IOSTRG; + _strbuf._ptr = (char *)str; + _strbuf._base = (char *)str; + _strbuf._cnt = 0; + while (*str++) + _strbuf._cnt++; + _strbuf._bufsiz = _strbuf._cnt; + r = _doscan(&_strbuf, fmt, a); + va_end(a); + return r; +} diff --git a/reactos/lib/crtdll/stdio/stdhnd.c b/reactos/lib/crtdll/stdio/stdhnd.c new file mode 100644 index 00000000000..2abf82b6d84 --- /dev/null +++ b/reactos/lib/crtdll/stdio/stdhnd.c @@ -0,0 +1,39 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +//#include + + +FILE _iob[] = +{ + // stdin +{ + NULL, 0, NULL, + _IOREAD | _IOLBF , + 0, 0,0, NULL +}, + // stdout +{ + NULL, 0, NULL, + _IOWRT | _IOFBF |_IOSTRG, + 1,0,0, NULL +}, + // stderr +{ + NULL, 0, NULL, + _IOWRT | _IONBF, + 2,0,0, NULL +}, + // stdaux +{ + NULL, 0, NULL, + _IORW | _IONBF, + 3,0,0, NULL +}, + // stdprn +{ + NULL, 0, NULL, + _IOWRT | _IONBF, + 4, 0,0,NULL +} +}; diff --git a/reactos/lib/crtdll/stdio/stdiohk.c b/reactos/lib/crtdll/stdio/stdiohk.c new file mode 100644 index 00000000000..db059c2df76 --- /dev/null +++ b/reactos/lib/crtdll/stdio/stdiohk.c @@ -0,0 +1,19 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +//#include + +static void fcloseall_helper(FILE *f) +{ + fflush(f); + if (fileno(f) > 2) + fclose(f); +} + +void __stdio_cleanup_proc(void); +void __stdio_cleanup_proc(void) +{ + _fwalk(fcloseall_helper); +} + +void (*__stdio_cleanup_hook)(void) = __stdio_cleanup_proc; diff --git a/reactos/lib/crtdll/stdio/tempnam.c b/reactos/lib/crtdll/stdio/tempnam.c new file mode 100644 index 00000000000..8d6a8c23516 --- /dev/null +++ b/reactos/lib/crtdll/stdio/tempnam.c @@ -0,0 +1,17 @@ +#include +#include + + + +char *_tempnam(const char *dir,const char *prefix ) +{ + char *TempFileName; + TempFileName = malloc(MAX_PATH); + GetTempFileName( + dir, + prefix, + 98, + TempFileName + ); + return TempFileName; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/stdio/tmpfile.c b/reactos/lib/crtdll/stdio/tmpfile.c new file mode 100644 index 00000000000..9803ceee85a --- /dev/null +++ b/reactos/lib/crtdll/stdio/tmpfile.c @@ -0,0 +1,68 @@ +/* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1997 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1998 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +//#include +#include +#include +#include +#include +#include +//#include +#include +#include +#include + +#ifndef __dj_include_stdio_h_ +#define _name_to_remove _tmpfname +#endif + +FILE * __alloc_file(void); + +FILE * +tmpfile(void) +{ + int temp_fd; + FILE *f; + char *temp_name = tmpnam(0); + char *n_t_r = (char *)malloc(L_tmpnam); + + if (!n_t_r) + return 0; + + /* We could have a race condition, whereby another program + (in another virtual machine, or if the temporary file is + in a directory which is shared via a network) opens the + file returned by `tmpnam' between the call above and the + moment when we actually open the file below. This loop + retries the call to `tmpnam' until we actually succeed + to create the file which didn't exist before. */ + do { + errno = 0; + temp_fd = _open(temp_name, 0, SH_DENYRW); + } while (temp_fd == -1 && errno != ENOENT && (temp_name = tmpnam(0)) != 0); + + if (temp_name == 0) + return 0; + + /* This should have been fdopen(temp_fd, "wb+"), but `fdopen' + is non-ANSI. So we need to dump some of its guts here. Sigh... */ + f = __alloc_file(); + if (f) + { + f->_file = temp_fd; + f->_cnt = 0; + f->_bufsiz = 0; + f->_flag = _IORMONCL | _IORW; + f->_name_to_remove = n_t_r; + strcpy(f->_name_to_remove, temp_name); + f->_base = f->_ptr = NULL; + } + else + { + close(temp_fd); + remove(temp_name); + free(n_t_r); + } + return f; +} diff --git a/reactos/lib/crtdll/stdio/tmpnam.c b/reactos/lib/crtdll/stdio/tmpnam.c new file mode 100644 index 00000000000..3da55c6f888 --- /dev/null +++ b/reactos/lib/crtdll/stdio/tmpnam.c @@ -0,0 +1,24 @@ +#include +#include +#include + +char * +_tmpnam(char *s); + +char * +tmpnam(char *s) +{ + return _tmpnam(s); +} + + +char * +_tmpnam(char *s) +{ + char PathName[MAX_PATH]; + static char static_buf[MAX_PATH]; + GetTempPath(MAX_PATH,PathName); + GetTempFileNameA(PathName, "ARI",007,static_buf); + strcpy(s,static_buf); + return s; +} diff --git a/reactos/lib/crtdll/stdio/ungetc.c b/reactos/lib/crtdll/stdio/ungetc.c new file mode 100644 index 00000000000..b38f9dc6253 --- /dev/null +++ b/reactos/lib/crtdll/stdio/ungetc.c @@ -0,0 +1,32 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +ungetc(int c, FILE *f) +{ + if (c == EOF + || (f->_flag & (_IOREAD|_IORW)) == 0 + || f->_ptr == NULL + || f->_base == NULL) + return EOF; + + if (f->_ptr == f->_base) + { + if (f->_cnt == 0) + f->_ptr++; + else + return EOF; + } + + f->_cnt++; + f->_ptr--; + if(*f->_ptr != c) + { + f->_flag |= _IOUNGETC; + *f->_ptr = c; + } + + return c; +} diff --git a/reactos/lib/crtdll/stdio/vfprintf.c b/reactos/lib/crtdll/stdio/vfprintf.c new file mode 100644 index 00000000000..8b4f5e690f8 --- /dev/null +++ b/reactos/lib/crtdll/stdio/vfprintf.c @@ -0,0 +1,27 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +int +vfprintf(FILE *f, const char *fmt, va_list ap) +{ + int len; + char localbuf[BUFSIZ]; + + if (f->_flag & _IONBF) + { + f->_flag &= ~_IONBF; + f->_ptr = f->_base = localbuf; + f->_bufsiz = BUFSIZ; + len = _doprnt(fmt, ap, f); + (void)fflush(f); + f->_flag |= _IONBF; + f->_base = NULL; + f->_bufsiz = 0; + f->_cnt = 0; + } + else + len = _doprnt(fmt, ap, f); + return (ferror(f) ? EOF : len); +} diff --git a/reactos/lib/crtdll/stdio/vprintf.c b/reactos/lib/crtdll/stdio/vprintf.c new file mode 100644 index 00000000000..c9e71d9bb31 --- /dev/null +++ b/reactos/lib/crtdll/stdio/vprintf.c @@ -0,0 +1,13 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include + +int +vprintf(const char *fmt, va_list ap) +{ + int len; + + len = _doprnt(fmt, ap, stdout); + return (ferror(stdout) ? EOF : len); +} diff --git a/reactos/lib/crtdll/stdio/vsprintf.c b/reactos/lib/crtdll/stdio/vsprintf.c index c8039b03f72..425725acade 100644 --- a/reactos/lib/crtdll/stdio/vsprintf.c +++ b/reactos/lib/crtdll/stdio/vsprintf.c @@ -1,340 +1,19 @@ -/* - * 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 - */ - +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include #include +#include +#include -#include -#include -#include - -unsigned long simple_strtoul(const char *cp,char **endp,unsigned int base) +int +vsprintf(char *str, const char *fmt, va_list ap) { - unsigned long result = 0,value; + FILE f; + int len; - 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; + f._flag = _IOWRT|_IOSTRG; + f._ptr = str; + f._cnt = INT_MAX; + len = _doprnt(fmt, ap, &f); + *f._ptr = 0; + return len; } - -/* 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); - if (sw==NULL) - { -// CHECKPOINT; - s = ""; - while ((*s)!=0) - { - *str++ = *s++; - } -// CHECKPOINT; -// DbgPrint("str %x\n",str); - } - else - { - while ((*sw)!=0) - { - *str++ = (char)(*sw++); - } - } -// CHECKPOINT; - 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/lib/crtdll/stdlib/Exit.c b/reactos/lib/crtdll/stdlib/Exit.c new file mode 100644 index 00000000000..606f660853b --- /dev/null +++ b/reactos/lib/crtdll/stdlib/Exit.c @@ -0,0 +1,48 @@ +#include +#include +#include +#include +#include + +void _exit(int _status); + +struct __atexit *__atexit_ptr = 0; + +void +exit(int status) +{ + //int i; + struct __atexit *a = __atexit_ptr; + __atexit_ptr = 0; /* to prevent infinite loops */ + while (a) + { + (a->__function)(); + a = a->__next; + } +/* + if (__stdio_cleanup_hook) + __stdio_cleanup_hook(); + for (i=0; i +#include +#include + +static char msg[] = "Abort!\r\n"; + +void +abort() +{ + _write(stderr->_file, msg, sizeof(msg)-1); + _exit(1); +} diff --git a/reactos/lib/crtdll/stdlib/abs.c b/reactos/lib/crtdll/stdlib/abs.c new file mode 100644 index 00000000000..3bd28bd8339 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/abs.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +int +abs(int j) +{ + return j<0 ? -j : j; +} diff --git a/reactos/lib/crtdll/stdlib/atexit.c b/reactos/lib/crtdll/stdlib/atexit.c new file mode 100644 index 00000000000..d9d4ba5561e --- /dev/null +++ b/reactos/lib/crtdll/stdlib/atexit.c @@ -0,0 +1,18 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +atexit(void (*a)(void)) +{ + struct __atexit *ap; + if (a == 0) + return -1; + ap = (struct __atexit *)malloc(sizeof(struct __atexit)); + if (!ap) + return -1; + ap->__next = __atexit_ptr; + ap->__function = a; + __atexit_ptr = ap; + return 0; +} diff --git a/reactos/lib/crtdll/stdlib/atof.c b/reactos/lib/crtdll/stdlib/atof.c new file mode 100644 index 00000000000..f9f7f98a911 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/atof.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +double +atof(const char *ascii) +{ + return strtod(ascii, 0); +} diff --git a/reactos/lib/crtdll/stdlib/atoi.c b/reactos/lib/crtdll/stdlib/atoi.c new file mode 100644 index 00000000000..ba4e2dfb6ff --- /dev/null +++ b/reactos/lib/crtdll/stdlib/atoi.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +int +atoi(const char *str) +{ + return (int)strtol(str, 0, 10); +} diff --git a/reactos/lib/crtdll/stdlib/atol.c b/reactos/lib/crtdll/stdlib/atol.c new file mode 100644 index 00000000000..2680abd0a8d --- /dev/null +++ b/reactos/lib/crtdll/stdlib/atol.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long +atol(const char *str) +{ + return strtol(str, 0, 10); +} diff --git a/reactos/lib/crtdll/stdlib/atold.c b/reactos/lib/crtdll/stdlib/atold.c new file mode 100644 index 00000000000..ce3f33ac434 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/atold.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long double +_atold(const char *ascii) +{ + return _strtold(ascii, 0); +} diff --git a/reactos/lib/crtdll/stdlib/bsearch.c b/reactos/lib/crtdll/stdlib/bsearch.c new file mode 100644 index 00000000000..48123456b77 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/bsearch.c @@ -0,0 +1,26 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +void * +bsearch(const void *key, const void *base0, size_t nelem, + size_t size, int (*cmp)(const void *ck, const void *ce)) +{ + char *base = unconst(base0, char *); + int lim, cmpval; + void *p; + + for (lim = nelem; lim != 0; lim >>= 1) + { + p = base + (lim >> 1) * size; + cmpval = (*cmp)(key, p); + if (cmpval == 0) + return p; + if (cmpval > 0) + { /* key > p: move right */ + base = (char *)p + size; + lim--; + } /* else move left */ + } + return 0; +} diff --git a/reactos/lib/crtdll/stdlib/calloc.c b/reactos/lib/crtdll/stdlib/calloc.c new file mode 100644 index 00000000000..1bb68c1a241 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/calloc.c @@ -0,0 +1,12 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +void * +calloc(size_t size, size_t nelem) +{ + void *rv = malloc(size*nelem); + if (rv) + memset(rv, 0, size*nelem); + return rv; +} diff --git a/reactos/lib/crtdll/stdlib/div.c b/reactos/lib/crtdll/stdlib/div.c new file mode 100644 index 00000000000..db56aef7169 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/div.c @@ -0,0 +1,24 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +div_t +div(int num, int denom) +{ + div_t r; + + if (num > 0 && denom < 0) { + num = -num; + denom = -denom; + } + r.quot = num / denom; + r.rem = num % denom; + if (num < 0 && denom > 0) + { + if (r.rem > 0) + { + r.quot++; + r.rem -= denom; + } + } + return r; +} diff --git a/reactos/lib/crtdll/stdlib/errno.c b/reactos/lib/crtdll/stdlib/errno.c new file mode 100644 index 00000000000..ac6f7266165 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/errno.c @@ -0,0 +1,13 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +#undef errno +int errno; +int _doserrno; + + +int _errno(void) +{ + return errno; +} + diff --git a/reactos/lib/crtdll/stdlib/fullpath.c b/reactos/lib/crtdll/stdlib/fullpath.c new file mode 100644 index 00000000000..35a68e7439e --- /dev/null +++ b/reactos/lib/crtdll/stdlib/fullpath.c @@ -0,0 +1,32 @@ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/crtdll/stdlib/fullpath.c + * PURPOSE: Gets the fullpathname + * PROGRAMER: Boudewijn Dekker + * UPDATE HISTORY: + * 28/12/98: Created + */ +#include +#include + +#undef fullpath +char *fullpath( char *absPath, const char *relPath, size_t maxLength ) +{ + return _fullpath(absPath,relPath,maxLength ); +} + +char *_fullpath( char *absPath, const char *relPath, size_t maxLength ) +{ + + + char *lpFilePart; + if ( GetFullPathName(relPath,maxLength,absPath,&lpFilePart) == 0 ) + return NULL; + + return absPath; +} + + + + diff --git a/reactos/lib/crtdll/stdlib/labs.c b/reactos/lib/crtdll/stdlib/labs.c new file mode 100644 index 00000000000..eb2fb7167b0 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/labs.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long +labs(long j) +{ + return j<0 ? -j : j; +} diff --git a/reactos/lib/crtdll/stdlib/ldiv.c b/reactos/lib/crtdll/stdlib/ldiv.c new file mode 100644 index 00000000000..43cfc32ba95 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/ldiv.c @@ -0,0 +1,25 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +ldiv_t +ldiv(long num, long denom) +{ + ldiv_t r; + + if (num > 0 && denom < 0) + { + num = -num; + denom = -denom; + } + r.quot = num / denom; + r.rem = num % denom; + if (num < 0 && denom > 0) + { + if (r.rem > 0) + { + r.quot++; + r.rem -= denom; + } + } + return r; +} diff --git a/reactos/lib/crtdll/stdlib/llabs.c b/reactos/lib/crtdll/stdlib/llabs.c new file mode 100644 index 00000000000..034a6f6cdd5 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/llabs.c @@ -0,0 +1,9 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +long long +llabs(long long j) +{ + return j<0 ? -j : j; +} diff --git a/reactos/lib/crtdll/stdlib/lldiv.c b/reactos/lib/crtdll/stdlib/lldiv.c new file mode 100644 index 00000000000..3c92ad537e7 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/lldiv.c @@ -0,0 +1,26 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +lldiv_t +lldiv(long long num, long long denom) +{ + lldiv_t r; + + if (num > 0 && denom < 0) + { + num = -num; + denom = -denom; + } + r.quot = num / denom; + r.rem = num % denom; + if (num < 0 && denom > 0) + { + if (r.rem > 0) + { + r.quot++; + r.rem -= denom; + } + } + return r; +} diff --git a/reactos/lib/crtdll/stdlib/makepath.c b/reactos/lib/crtdll/stdlib/makepath.c new file mode 100644 index 00000000000..6bc074fa1de --- /dev/null +++ b/reactos/lib/crtdll/stdlib/makepath.c @@ -0,0 +1,30 @@ +#include +#include + +void _makepath( char *path, const char *drive, const char *dir, const char *fname, const char *ext ) +{ + int dir_len; + if ( drive != NULL ) { + strcat(path,drive); + strcat(path,":"); + } + + if ( dir != NULL ) { + strcat(path,dir); + if ( *dir != '\\' ) + strcat(path,"\\"); + dir_len = strlen(dir); + if ( *(dir + dir_len - 1) != '\\' ) + strcat(path,"\\"); + } + if ( fname != NULL ) { + strcat(path,fname); + if ( ext != NULL ) { + if ( *ext != '.') + strcat(path,"."); + strcat(path,ext); + } + } + + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/stdlib/malloc.c b/reactos/lib/crtdll/stdlib/malloc.c index f368203c6e8..7789287c277 100644 --- a/reactos/lib/crtdll/stdlib/malloc.c +++ b/reactos/lib/crtdll/stdlib/malloc.c @@ -1,34 +1,37 @@ -/* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS system libraries - * FILE: lib/crtdll/stdlib/malloc.c - * PURPOSE: stdc memory allocation functions - * PROGRAMMER: ?? - */ - -/* INCLUDES ******************************************************************/ - #include -#include +#include +//#include +#include -/* FUNCTIONS *****************************************************************/ - -void* malloc(size_t size) +void* malloc(size_t _size) { - return(HeapAlloc(GetProcessHeap(), 0, size)); + return(HeapAlloc(GetProcessHeap(), + 0, + _size)); } -void free(void* ptr) +void free(void* _ptr) { - HeapFree(GetProcessHeap(), 0, ptr); + HeapFree(GetProcessHeap(), + 0, + _ptr); } -void* calloc(size_t nmemb, size_t size) +void* calloc(size_t _nmemb, size_t _size) { - return(HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, nmemb*size)); + return(HeapAlloc(GetProcessHeap(), + HEAP_ZERO_MEMORY, + _nmemb*_size)); } -void* realloc(void* ptr, size_t size) +void* realloc(void* _ptr, size_t _size) { - return(HeapReAlloc(GetProcessHeap(), 0, ptr, size)); + ExFreePool(_ptr); + return ExAllocatePool(NonPagedPool,_size ); +#if 0 + return(HeapReAlloc(GetProcessHeap(), + 0, + _ptr, + _size)); +#endif } diff --git a/reactos/lib/crtdll/stdlib/putenv.c b/reactos/lib/crtdll/stdlib/putenv.c new file mode 100644 index 00000000000..cb276f7ada6 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/putenv.c @@ -0,0 +1,30 @@ +#include +#include +#include + + + +int +putenv(const char *val) +{ + + char buffer[1024]; + char *epos; + + strcpy(buffer,val); + + + epos = strchr(buffer, '='); + if ( epos == NULL ) + return -1; + + *epos = 0; + + return SetEnvironmentVariableA(buffer,epos+1); +} + + + + + + \ No newline at end of file diff --git a/reactos/lib/crtdll/stdlib/qsort.c b/reactos/lib/crtdll/stdlib/qsort.c new file mode 100644 index 00000000000..456834ffe74 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/qsort.c @@ -0,0 +1,238 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +/*- + * Copyright (c) 1980, 1983 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms are permitted + * provided that: (1) source distributions retain this entire copyright + * notice and comment, and (2) distributions including binaries display + * the following acknowledgement: ``This product includes software + * developed by the University of California, Berkeley and its contributors'' + * in the documentation or other materials provided with the distribution + * and in all advertising materials mentioning features or use of this + * software. Neither the name of the University nor the names of its + * contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +/* + * qsort.c: + * Our own version of the system qsort routine which is faster by an average + * of 25%, with lows and highs of 10% and 50%. + * The THRESHold below is the insertion sort threshold, and has been adjusted + * for records of size 48 bytes. + * The MTHREShold is where we stop finding a better median. + */ + +#define THRESH 4 /* threshold for insertion */ +#define MTHRESH 6 /* threshold for median */ + +static int (*qcmp)(const void *, const void *); /* the comparison routine */ +static int qsz; /* size of each record */ +static int thresh; /* THRESHold in chars */ +static int mthresh; /* MTHRESHold in chars */ + +/* + * qst: + * Do a quicksort + * First, find the median element, and put that one in the first place as the + * discriminator. (This "median" is just the median of the first, last and + * middle elements). (Using this median instead of the first element is a big + * win). Then, the usual partitioning/swapping, followed by moving the + * discriminator into the right place. Then, figure out the sizes of the two + * partions, do the smaller one recursively and the larger one via a repeat of + * this code. Stopping when there are less than THRESH elements in a partition + * and cleaning up with an insertion sort (in our caller) is a huge win. + * All data swaps are done in-line, which is space-losing but time-saving. + * (And there are only three places where this is done). + */ + +static void +qst(char *base, char *max) +{ + char c, *i, *j, *jj; + int ii; + char *mid, *tmp; + int lo, hi; + + /* + * At the top here, lo is the number of characters of elements in the + * current partition. (Which should be max - base). + * Find the median of the first, last, and middle element and make + * that the middle element. Set j to largest of first and middle. + * If max is larger than that guy, then it's that guy, else compare + * max with loser of first and take larger. Things are set up to + * prefer the middle, then the first in case of ties. + */ + lo = max - base; /* number of elements as chars */ + do { + mid = i = base + qsz * ((lo / qsz) >> 1); + if (lo >= mthresh) + { + j = (qcmp((jj = base), i) > 0 ? jj : i); + if (qcmp(j, (tmp = max - qsz)) > 0) + { + /* switch to first loser */ + j = (j == jj ? i : jj); + if (qcmp(j, tmp) < 0) + j = tmp; + } + if (j != i) + { + ii = qsz; + do { + c = *i; + *i++ = *j; + *j++ = c; + } while (--ii); + } + } + /* + * Semi-standard quicksort partitioning/swapping + */ + for (i = base, j = max - qsz; ; ) + { + while (i < mid && qcmp(i, mid) <= 0) + i += qsz; + while (j > mid) + { + if (qcmp(mid, j) <= 0) + { + j -= qsz; + continue; + } + tmp = i + qsz; /* value of i after swap */ + if (i == mid) + { + /* j <-> mid, new mid is j */ + mid = jj = j; + } + else + { + /* i <-> j */ + jj = j; + j -= qsz; + } + goto swap; + } + if (i == mid) + { + break; + } + else + { + /* i <-> mid, new mid is i */ + jj = mid; + tmp = mid = i; /* value of i after swap */ + j -= qsz; + } + swap: + ii = qsz; + do { + c = *i; + *i++ = *jj; + *jj++ = c; + } while (--ii); + i = tmp; + } + /* + * Look at sizes of the two partitions, do the smaller + * one first by recursion, then do the larger one by + * making sure lo is its size, base and max are update + * correctly, and branching back. But only repeat + * (recursively or by branching) if the partition is + * of at least size THRESH. + */ + i = (j = mid) + qsz; + if ((lo = j - base) <= (hi = max - i)) + { + if (lo >= thresh) + qst(base, j); + base = i; + lo = hi; + } + else + { + if (hi >= thresh) + qst(i, max); + max = j; + } + } while (lo >= thresh); +} + +/* + * qsort: + * First, set up some global parameters for qst to share. Then, quicksort + * with qst(), and then a cleanup insertion sort ourselves. Sound simple? + * It's not... + */ + +void +qsort(void *base0, size_t n, size_t size, int (*compar)(const void *, const void *)) +{ + char *base = (char *)base0; + char c, *i, *j, *lo, *hi; + char *min, *max; + + if (n <= 1) + return; + qsz = size; + qcmp = compar; + thresh = qsz * THRESH; + mthresh = qsz * MTHRESH; + max = base + n * qsz; + if (n >= THRESH) + { + qst(base, max); + hi = base + thresh; + } + else + { + hi = max; + } + /* + * First put smallest element, which must be in the first THRESH, in + * the first position as a sentinel. This is done just by searching + * the first THRESH elements (or the first n if n < THRESH), finding + * the min, and swapping it into the first position. + */ + for (j = lo = base; (lo += qsz) < hi; ) + if (qcmp(j, lo) > 0) + j = lo; + if (j != base) + { + /* swap j into place */ + for (i = base, hi = base + qsz; i < hi; ) + { + c = *j; + *j++ = *i; + *i++ = c; + } + } + /* + * With our sentinel in place, we now run the following hyper-fast + * insertion sort. For each remaining element, min, from [1] to [n-1], + * set hi to the index of the element AFTER which this one goes. + * Then, do the standard insertion sort shift on a character at a time + * basis for each element in the frob. + */ + for (min = base; (hi = min += qsz) < max; ) + { + while (qcmp(hi -= qsz, min) > 0) + /* void */; + if ((hi += qsz) != min) { + for (lo = min + qsz; --lo >= min; ) + { + c = *lo; + for (i = j = lo; (j -= qsz) >= hi; i = j) + *i = *j; + *i = c; + } + } + } +} diff --git a/reactos/lib/crtdll/stdlib/rand.c b/reactos/lib/crtdll/stdlib/rand.c new file mode 100644 index 00000000000..3628947bd6c --- /dev/null +++ b/reactos/lib/crtdll/stdlib/rand.c @@ -0,0 +1,17 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +static unsigned long long next = 0; + +int +rand(void) +{ + next = next * 0x5deece66dLL + 11; + return (int)((next >> 16) & RAND_MAX); +} + +void +srand(unsigned seed) +{ + next = seed; +} diff --git a/reactos/lib/crtdll/stdlib/senv.c b/reactos/lib/crtdll/stdlib/senv.c new file mode 100644 index 00000000000..030abb39ad4 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/senv.c @@ -0,0 +1,28 @@ +#include +#include +#include + +void _searchenv(const char *file,const char *var,char *path ) +{ + char *env = getenv(var); + + char *x; + char *y; + char *FilePart; + x = strchr(env,'='); + if ( x != NULL ) { + *x = 0; + x++; + } + y = strchr(env,';'); + while ( y != NULL ) { + *y = 0; + if ( SearchPathA(x,file,NULL,MAX_PATH,path,&FilePart) > 0 ) { + return; + } + x = y+1; + y = strchr(env,';'); + } + return; + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/stdlib/splitp.c b/reactos/lib/crtdll/stdlib/splitp.c new file mode 100644 index 00000000000..8dbe18b20cc --- /dev/null +++ b/reactos/lib/crtdll/stdlib/splitp.c @@ -0,0 +1,42 @@ +#include +#include + +void _splitpath( const char *path, char *drive, char *dir, char *fname, char *ext ) +{ + char *tmp_drive; + char *tmp_dir; + char *tmp_ext; + + tmp_drive = (char *)strchr(path,':'); + if ( tmp_drive != (char *)NULL ) { + strncpy(drive,tmp_drive-1,1); + *(drive+1) = 0; + } + else { + *drive = 0; + tmp_drive = (char *)path; + } + + tmp_dir = (char *)strrchr(path,'\\'); + if( tmp_dir != NULL && tmp_dir != tmp_drive + 1 ) { + strncpy(dir,tmp_drive+1,tmp_dir - tmp_drive); + *(dir + (tmp_dir - tmp_drive)) = 0; + } + else + *dir =0; + + tmp_ext = ( char *)strrchr(path,'.'); + if ( tmp_ext != NULL ) { + strcpy(ext,tmp_ext); + } + else + *ext = 0; + if ( tmp_dir != NULL ) { + strncpy(fname,tmp_dir+1,tmp_ext - tmp_dir - 1); + *(fname + (tmp_ext - tmp_dir -1)) = 0; + } + else + strncpy(fname,path,tmp_ext - path); + +} + diff --git a/reactos/lib/crtdll/stdlib/strtod.c b/reactos/lib/crtdll/stdlib/strtod.c new file mode 100644 index 00000000000..832cb2efc12 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtod.c @@ -0,0 +1,97 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + + +double +strtod(const char *s, char **sret) +{ + long double r; /* result */ + int e; /* exponent */ + long double d; /* scale */ + int sign; /* +- 1.0 */ + int esign; + int i; + int flags=0; + + r = 0.0; + sign = 1; + e = 0; + esign = 1; + + while ((*s == ' ') || (*s == '\t')) + s++; + + if (*s == '+') + s++; + else if (*s == '-') + { + sign = -1; + s++; + } + + while ((*s >= '0') && (*s <= '9')) + { + flags |= 1; + r *= 10.0; + r += *s - '0'; + s++; + } + + if (*s == '.') + { + d = 0.1L; + s++; + while ((*s >= '0') && (*s <= '9')) + { + flags |= 2; + r += d * (*s - '0'); + s++; + d *= 0.1L; + } + } + + if (flags == 0) + { + if (sret) + *sret = (char *)s; + return 0; + } + + if ((*s == 'e') || (*s == 'E')) + { + s++; + if (*s == '+') + s++; + else if (*s == '-') + { + s++; + esign = -1; + } + if ((*s < '0') || (*s > '9')) + { + if (sret) + *sret = (char *)s; + return r; + } + + while ((*s >= '0') && (*s <= '9')) + { + e *= 10; + e += *s - '0'; + s++; + } + } + + if (esign < 0) + for (i = 1; i <= e; i++) + r *= 0.1L; + else + for (i = 1; i <= e; i++) + r *= 10.0; + + if (sret) + *sret = (char *)s; + return r * sign; +} diff --git a/reactos/lib/crtdll/stdlib/strtol.c b/reactos/lib/crtdll/stdlib/strtol.c new file mode 100644 index 00000000000..362f9bcce2e --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtol.c @@ -0,0 +1,91 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include + + +long +strtol(const char *nptr, char **endptr, int base) +{ + const char *s = nptr; + unsigned long acc; + int c; + unsigned long cutoff; + int neg = 0, any, cutlim; + + /* + * Skip white space and pick up leading +/- sign if any. + * If base is 0, allow 0x for hex and 0 for octal, else + * assume decimal; if base is already 16, allow 0x. + */ + do { + c = *s++; + } while (isspace(c)); + if (c == '-') + { + neg = 1; + c = *s++; + } + else if (c == '+') + c = *s++; + if ((base == 0 || base == 16) && + c == '0' && (*s == 'x' || *s == 'X')) + { + c = s[1]; + s += 2; + base = 16; + } + if (base == 0) + base = c == '0' ? 8 : 10; + + /* + * Compute the cutoff value between legal numbers and illegal + * numbers. That is the largest legal value, divided by the + * base. An input number that is greater than this value, if + * followed by a legal input character, is too big. One that + * is equal to this value may be valid or not; the limit + * between valid and invalid numbers is then based on the last + * digit. For instance, if the range for longs is + * [-2147483648..2147483647] and the input base is 10, + * cutoff will be set to 214748364 and cutlim to either + * 7 (neg==0) or 8 (neg==1), meaning that if we have accumulated + * a value > 214748364, or equal but the next digit is > 7 (or 8), + * the number is too big, and we will return a range error. + * + * Set any if any `digits' consumed; make it negative to indicate + * overflow. + */ + cutoff = neg ? -(unsigned long)LONG_MIN : LONG_MAX; + cutlim = cutoff % (unsigned long)base; + cutoff /= (unsigned long)base; + for (acc = 0, any = 0;; c = *s++) + { + if (isdigit(c)) + c -= '0'; + else if (isalpha(c)) + c -= isupper(c) ? 'A' - 10 : 'a' - 10; + else + break; + if (c >= base) + break; + if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim)) + any = -1; + else + { + any = 1; + acc *= base; + acc += c; + } + } + if (any < 0) + { + acc = neg ? LONG_MIN : LONG_MAX; + errno = ERANGE; + } + else if (neg) + acc = -acc; + if (endptr != 0) + *endptr = any ? (char *)s - 1 : (char *)nptr; + return acc; +} diff --git a/reactos/lib/crtdll/stdlib/strtold.c b/reactos/lib/crtdll/stdlib/strtold.c new file mode 100644 index 00000000000..cbcce231d51 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtold.c @@ -0,0 +1,124 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +//#include + +static double powten[] = +{ + 1e1L, 1e2L, 1e4L, 1e8L, 1e16L, 1e32L, 1e64L, 1e128L, 1e256L + //1e512L, 1e512L*1e512L, 1e2048L, 1e4096L +}; + +double +_strtold(const char *s, char **sret) +{ +#if 0 + double r; /* result */ + int e, ne; /* exponent */ + int sign; /* +- 1.0 */ + int esign; + int flags=0; + int l2powm1; + + r = 0.0L; + sign = 1; + e = ne = 0; + esign = 1; + + while(*s && isspace(*s)) + s++; + + if (*s == '+') + s++; + else if (*s == '-') + { + sign = -1; + s++; + } + + while ((*s >= '0') && (*s <= '9')) + { + flags |= 1; + r *= 10.0L; + r += *s - '0'; + s++; + } + + if (*s == '.') + { + s++; + while ((*s >= '0') && (*s <= '9')) + { + flags |= 2; + r *= 10.0L; + r += *s - '0'; + s++; + ne++; + } + } + if (flags == 0) + { + if (sret) + *sret = (char *)s; + return 0.0L; + } + + if ((*s == 'e') || (*s == 'E')) + { + s++; + if (*s == '+') + s++; + else if (*s == '-') + { + s++; + esign = -1; + } + while ((*s >= '0') && (*s <= '9')) + { + e *= 10; + e += *s - '0'; + s++; + } + } + if (esign < 0) + { + esign = -esign; + e = -e; + } + e = e - ne; + if (e < -4096) + { + /* possibly subnormal number, 10^e would overflow */ + r *= 1.0e-2048L; + e += 2048; + } + if (e < 0) + { + e = -e; + esign = -esign; + } + if (e >= 8192) + e = 8191; + if (e) + { + double d = 1.0L; + l2powm1 = 0; + while (e) + { + if (e & 1) + d *= powten[l2powm1]; + e >>= 1; + l2powm1++; + } + if (esign > 0) + r *= d; + else + r /= d; + } + if (sret) + *sret = (char *)s; + return r * sign; + +#endif + return 0; +} diff --git a/reactos/lib/crtdll/stdlib/strtoll.c b/reactos/lib/crtdll/stdlib/strtoll.c new file mode 100644 index 00000000000..26b4944acf3 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtoll.c @@ -0,0 +1,84 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include +//#include + +/* constants used in Solaris */ +#define LLONG_MIN -9223372036854775807L-1L +#define LLONG_MAX 9223372036854775807L +#define ULLONG_MAX 18446744073709551615UL + +long +strtoll(const char *nptr, char **endptr, int base) +{ + const char *s = nptr; + unsigned long acc; + int c; + unsigned long cutoff; + int neg = 0, any, cutlim; + + /* + * See strtol for comments as to the logic used. + */ + do { + c = *s++; + } while (isspace(c)); + if (c == '-') + { + neg = 1; + c = *s++; + } + else if (c == '+') + c = *s++; + if ((base == 0 || base == 16) && + c == '0' && (*s == 'x' || *s == 'X')) + { + c = s[1]; + s += 2; + base = 16; + } + if (base == 0) + base = c == '0' ? 8 : 10; + +/* to prevent overflow, we take max-1 and add 1 after division */ + cutoff = neg ? -(LLONG_MIN+1) : LLONG_MAX-1; + cutlim = cutoff % base; + cutoff /= base; + if (++cutlim == base) + { + cutlim = 0; + cutoff++; + } + for (acc = 0, any = 0;; c = *s++) + { + if (isdigit(c)) + c -= '0'; + else if (isalpha(c)) + c -= isupper(c) ? 'A' - 10 : 'a' - 10; + else + break; + if (c >= base) + break; + if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim)) + any = -1; + else + { + any = 1; + acc *= base; + acc += c; + } + } + if (any < 0) + { + acc = neg ? LLONG_MIN : LLONG_MAX; + errno = ERANGE; + } + else if (neg) + acc *= -1; + if (endptr != 0) + *endptr = any ? (char *)s - 1 : (char *)nptr; + return acc; +} diff --git a/reactos/lib/crtdll/stdlib/strtoul.c b/reactos/lib/crtdll/stdlib/strtoul.c new file mode 100644 index 00000000000..d62bd5366b0 --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtoul.c @@ -0,0 +1,75 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include +#include + +/* + * Convert a string to an unsigned long integer. + * + * Ignores `locale' stuff. Assumes that the upper and lower case + * alphabets and digits are each contiguous. + */ +unsigned long +strtoul(const char *nptr, char **endptr, int base) +{ + const char *s = nptr; + unsigned long acc; + int c; + unsigned long cutoff; + int neg = 0, any, cutlim; + + /* + * See strtol for comments as to the logic used. + */ + do { + c = *s++; + } while (isspace(c)); + if (c == '-') + { + neg = 1; + c = *s++; + } + else if (c == '+') + c = *s++; + if ((base == 0 || base == 16) && + c == '0' && (*s == 'x' || *s == 'X')) + { + c = s[1]; + s += 2; + base = 16; + } + if (base == 0) + base = c == '0' ? 8 : 10; + cutoff = (unsigned long)ULONG_MAX / (unsigned long)base; + cutlim = (unsigned long)ULONG_MAX % (unsigned long)base; + for (acc = 0, any = 0;; c = *s++) + { + if (isdigit(c)) + c -= '0'; + else if (isalpha(c)) + c -= isupper(c) ? 'A' - 10 : 'a' - 10; + else + break; + if (c >= base) + break; + if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim)) + any = -1; + else { + any = 1; + acc *= base; + acc += c; + } + } + if (any < 0) + { + acc = ULONG_MAX; + errno = ERANGE; + } + else if (neg) + acc = -acc; + if (endptr != 0) + *endptr = any ? unconst(s, char *) - 1 : unconst(nptr, char *); + return acc; +} diff --git a/reactos/lib/crtdll/stdlib/strtoull.c b/reactos/lib/crtdll/stdlib/strtoull.c new file mode 100644 index 00000000000..020d539c04d --- /dev/null +++ b/reactos/lib/crtdll/stdlib/strtoull.c @@ -0,0 +1,76 @@ +/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include +//#include + +/* + * Convert a string to an unsigned long integer. + * + * Ignores `locale' stuff. Assumes that the upper and lower case + * alphabets and digits are each contiguous. + */ +unsigned long +strtoull(const char *nptr, char **endptr, int base) +{ + const char *s = nptr; + unsigned long acc; + int c; + unsigned long cutoff; + int neg = 0, any, cutlim; + + /* + * See strtol for comments as to the logic used. + */ + do { + c = *s++; + } while (isspace(c)); + if (c == '-') + { + neg = 1; + c = *s++; + } + else if (c == '+') + c = *s++; + if ((base == 0 || base == 16) && + c == '0' && (*s == 'x' || *s == 'X')) + { + c = s[1]; + s += 2; + base = 16; + } + if (base == 0) + base = c == '0' ? 8 : 10; + cutoff = (unsigned long)ULONG_MAX / base; + cutlim = (unsigned long)ULONG_MAX % base; + for (acc = 0, any = 0;; c = *s++) + { + if (isdigit(c)) + c -= '0'; + else if (isalpha(c)) + c -= isupper(c) ? 'A' - 10 : 'a' - 10; + else + break; + if (c >= base) + break; + if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim)) + any = -1; + else { + any = 1; + acc *= base; + acc += c; + } + } + if (any < 0) + { + acc = ULONG_MAX; + errno = ERANGE; + } + else if (neg) + acc = -acc; + if (endptr != 0) + *endptr = any ? (char *)s - 1 : (char *)nptr; + return acc; +} diff --git a/reactos/lib/crtdll/string/memchr.c b/reactos/lib/crtdll/string/memchr.c index 174680a3372..cd8b19cbd6d 100644 --- a/reactos/lib/crtdll/string/memchr.c +++ b/reactos/lib/crtdll/string/memchr.c @@ -1,6 +1,7 @@ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + + #include -#include void * memchr(const void *s, int c, size_t n) @@ -10,7 +11,7 @@ memchr(const void *s, int c, size_t n) const char *p = s; do { if (*p++ == c) - return unconst(p-1, void *); + return (void *)(p-1); } while (--n != 0); } return 0; diff --git a/reactos/lib/crtdll/string/memcpy.c b/reactos/lib/crtdll/string/memcpy.c new file mode 100644 index 00000000000..0e117013f2b --- /dev/null +++ b/reactos/lib/crtdll/string/memcpy.c @@ -0,0 +1,19 @@ +typedef unsigned int size_t; + +void * +memcpy (char *to, char *from, size_t count); + +/* This is the most reliable way to avoid incompatibilities + in available built-in functions on various systems. */ +void * +memcpy (char *to, char *from, size_t count) +{ + register char *f = from; + register char *t = to; + register int i = count; + + while (i-- > 0) + *t++ = *f++; + + return to; +} diff --git a/reactos/lib/crtdll/string/memmove.c b/reactos/lib/crtdll/string/memmove.c new file mode 100644 index 00000000000..eaad6e2200a --- /dev/null +++ b/reactos/lib/crtdll/string/memmove.c @@ -0,0 +1,20 @@ +#include + + +void * memmove(void *dest,const void *src,size_t count) +{ + int *int_dest = dest; + int *int_src = src; + + while(count > 0 ) + { + *int_dest = *int_src; + int_dest++; + int_src++; + count--; + } + + return dest; + + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/string/memset.c b/reactos/lib/crtdll/string/memset.c new file mode 100644 index 00000000000..faeb33d82bb --- /dev/null +++ b/reactos/lib/crtdll/string/memset.c @@ -0,0 +1,11 @@ +typedef int size_t; + +void * memset(void *src,int val,size_t count) +{ + int *int_src = src; + while(count>0) { + *int_src = val; + count--; + } + return src; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/string/str_old.c b/reactos/lib/crtdll/string/str_old.c new file mode 100644 index 00000000000..bc5ec329cae --- /dev/null +++ b/reactos/lib/crtdll/string/str_old.c @@ -0,0 +1,48 @@ +/* + * string_old.c + * + * Oldnames from ANSI header string.h + * + * Some wrapper functions for those old name functions whose appropriate + * equivalents are not simply underscore prefixed. + * + * Contributors: + * Created by Colin Peters + * + * THIS SOFTWARE IS NOT COPYRIGHTED + * + * This source code is offered for use in the public domain. You may + * use, modify or distribute it freely. + * + * This code is distributed in the hope that it will be useful but + * WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY + * DISCLAMED. This includes but is not limited to warrenties of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * + * $Revision: 1.1 $ + * $Author: rex $ + * $Date: 1999/01/16 02:11:44 $ + * + */ + +#include +#include + +int +strcasecmp (const char* sz1, const char* sz2) +{ + return stricmp (sz1, sz2); +} + +int +strncasecmp (const char* sz1, const char* sz2, size_t sizeMaxCompare) +{ + return strnicmp (sz1, sz2, sizeMaxCompare); +} + +int +wcscmpi (const wchar_t* ws1, const wchar_t* ws2) +{ + return wcsicmp (ws1, ws2); +} + diff --git a/reactos/lib/crtdll/string/strchr.c b/reactos/lib/crtdll/string/strchr.c index d308d358bdd..448940371b4 100644 --- a/reactos/lib/crtdll/string/strchr.c +++ b/reactos/lib/crtdll/string/strchr.c @@ -1,20 +1,21 @@ /* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ -#include -#include -char * -strchr(const char *s, int c) + + +char *strchr(const char *s, int c); + +char *strchr(const char *s, int c) { char cc = c; while (*s) { if (*s == cc) - return unconst(s, char *); + return (char *)s; s++; } if (cc == 0) - return unconst(s, char *); + return (char *)s; return 0; } diff --git a/reactos/lib/crtdll/string/strcpy.c b/reactos/lib/crtdll/string/strcpy.c index 72d92cfa506..4813be8e477 100644 --- a/reactos/lib/crtdll/string/strcpy.c +++ b/reactos/lib/crtdll/string/strcpy.c @@ -1,5 +1,6 @@ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ -#include +char * +strcpy(char *to, const char *from); char * strcpy(char *to, const char *from) diff --git a/reactos/lib/crtdll/string/strdup.c b/reactos/lib/crtdll/string/strdup.c index c59cd32c39a..70180f42d52 100644 --- a/reactos/lib/crtdll/string/strdup.c +++ b/reactos/lib/crtdll/string/strdup.c @@ -1,6 +1,6 @@ /* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ #include -//#include +#include char * strdup(const char *_s) diff --git a/reactos/lib/crtdll/string/strerror.c b/reactos/lib/crtdll/string/strerror.c new file mode 100644 index 00000000000..bd28973826a --- /dev/null +++ b/reactos/lib/crtdll/string/strerror.c @@ -0,0 +1,102 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include +#include +#include +#include +//#include + + +char __syserr00[] = "No Error"; +char __syserr01[] = "Input to function out of range (EDOM)"; +char __syserr02[] = "Output of function out of range (ERANGE)"; +char __syserr03[] = "Argument list too long (E2BIG)"; +char __syserr04[] = "Permission denied (EACCES)"; +char __syserr05[] = "Resource temporarily unavailable (EAGAIN)"; +char __syserr06[] = "Bad file descriptor (EBADF)"; +char __syserr07[] = "Resource busy (EBUSY)"; +char __syserr08[] = "No child processes (ECHILD)"; +char __syserr09[] = "Resource deadlock avoided (EDEADLK)"; +char __syserr10[] = "File exists (EEXIST)"; +char __syserr11[] = "Bad address (EFAULT)"; +char __syserr12[] = "File too large (EFBIG)"; +char __syserr13[] = "Interrupted system call (EINTR)"; +char __syserr14[] = "Invalid argument (EINVAL)"; +char __syserr15[] = "Input or output error (EIO)"; +char __syserr16[] = "Is a directory (EISDIR)"; +char __syserr17[] = "Too many open files (EMFILE)"; +char __syserr18[] = "Too many links (EMLINK)"; +char __syserr19[] = "File name too long (ENAMETOOLONG)"; +char __syserr20[] = "Too many open files in system (ENFILE)"; +char __syserr21[] = "No such device (ENODEV)"; +char __syserr22[] = "No such file or directory (ENOENT)"; +char __syserr23[] = "Unable to execute file (ENOEXEC)"; +char __syserr24[] = "No locks available (ENOLCK)"; +char __syserr25[] = "Not enough memory (ENOMEM)"; +char __syserr26[] = "No space left on drive (ENOSPC)"; +char __syserr27[] = "Function not implemented (ENOSYS)"; +char __syserr28[] = "Not a directory (ENOTDIR)"; +char __syserr29[] = "Directory not empty (ENOTEMPTY)"; +char __syserr30[] = "Inappropriate I/O control operation (ENOTTY)"; +char __syserr31[] = "No such device or address (ENXIO)"; +char __syserr32[] = "Operation not permitted (EPERM)"; +char __syserr33[] = "Broken pipe (EPIPE)"; +char __syserr34[] = "Read-only file system (EROFS)"; +char __syserr35[] = "Invalid seek (ESPIPE)"; +char __syserr36[] = "No such process (ESRCH)"; +char __syserr37[] = "Improper link (EXDEV)"; +char __syserr38[] = "No more files (ENMFILE)"; + +const char *__sys_errlist[] = { +__syserr00, __syserr01, __syserr02, __syserr03, __syserr04, +__syserr05, __syserr06, __syserr07, __syserr08, __syserr09, +__syserr10, __syserr11, __syserr12, __syserr13, __syserr14, +__syserr15, __syserr16, __syserr17, __syserr18, __syserr19, +__syserr20, __syserr21, __syserr22, __syserr23, __syserr24, +__syserr25, __syserr26, __syserr27, __syserr28, __syserr29, +__syserr30, __syserr31, __syserr32, __syserr33, __syserr34, +__syserr35, __syserr36, __syserr37, __syserr38 +}; + +int __sys_nerr = sizeof(__sys_errlist) / sizeof(__sys_errlist[0]); + +char * +strerror(int errnum) +{ + static char ebuf[40]; /* 64-bit number + slop */ + char *cp; + int v=1000000, lz=0; + + if (errnum >= 0 && errnum < __sys_nerr) + return((char *)__sys_errlist[errnum]); + + strcpy(ebuf, "Unknown error: "); + cp = ebuf + 15; + if (errnum < 0) + { + *cp++ = '-'; + errnum = -errnum; + } + while (v) + { + int d = errnum / v; + if (d || lz || (v == 1)) + { + *cp++ = d+'0'; + lz = 1; + } + errnum %= v; + v /= 10; + } + + return ebuf; +} + +#undef errno +extern int errno; +char *_strerror(const char *s) +{ + if ( s == NULL ) + return strerror(errno); + + return strerror(atoi(s)); +} diff --git a/reactos/lib/crtdll/string/stricmp.c b/reactos/lib/crtdll/string/stricmp.c new file mode 100644 index 00000000000..377414e972f --- /dev/null +++ b/reactos/lib/crtdll/string/stricmp.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +stricmp(const char *s1, const char *s2) +{ + while (toupper(*s1) == toupper(*s2)) + { + if (*s1 == 0) + return 0; + s1++; + s2++; + } + return toupper(*(unsigned const char *)s1) - toupper(*(unsigned const char *)(s2)); +} diff --git a/reactos/lib/crtdll/string/strlwr.c b/reactos/lib/crtdll/string/strlwr.c new file mode 100644 index 00000000000..2bacd51c0fe --- /dev/null +++ b/reactos/lib/crtdll/string/strlwr.c @@ -0,0 +1,23 @@ +/* + * The C RunTime DLL + * + * Implements C run-time functionality as known from UNIX. + * + * Copyright 1996,1998 Marcus Meissner + * Copyright 1996 Jukka Iivonen + * Copyright 1997 Uwe Bonnes + */ + +#include +#include + +char * strlwr(char *x) +{ + char *y=x; + + while (*y) { + *y=tolower(*y); + y++; + } + return x; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/string/strncmp.c b/reactos/lib/crtdll/string/strncmp.c index c651e4c9495..f90eb5b2e44 100644 --- a/reactos/lib/crtdll/string/strncmp.c +++ b/reactos/lib/crtdll/string/strncmp.c @@ -1,6 +1,7 @@ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ #include + int strncmp(const char *s1, const char *s2, size_t n) { diff --git a/reactos/lib/crtdll/string/strnicmp.c b/reactos/lib/crtdll/string/strnicmp.c new file mode 100644 index 00000000000..3469c98963c --- /dev/null +++ b/reactos/lib/crtdll/string/strnicmp.c @@ -0,0 +1,18 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#include + +int +strnicmp(const char *s1, const char *s2, size_t n) +{ + + if (n == 0) + return 0; + do { + if (toupper(*s1) != toupper(*s2++)) + return toupper(*(unsigned const char *)s1) - toupper(*(unsigned const char *)--s2); + if (*s1++ == 0) + break; + } while (--n != 0); + return 0; +} diff --git a/reactos/lib/crtdll/string/strnlen.c b/reactos/lib/crtdll/string/strnlen.c new file mode 100644 index 00000000000..3027497f79a --- /dev/null +++ b/reactos/lib/crtdll/string/strnlen.c @@ -0,0 +1,14 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#include + +size_t +strnlen(const char *str, int count) +{ + const char *s; + + if (str == 0) + return 0; + for (s = str; *s && count; ++s, count--); + return s-str; +} + diff --git a/reactos/lib/crtdll/string/strpbrk.c b/reactos/lib/crtdll/string/strpbrk.c index 42e3473c4b1..5f642c4c1bf 100644 --- a/reactos/lib/crtdll/string/strpbrk.c +++ b/reactos/lib/crtdll/string/strpbrk.c @@ -1,6 +1,6 @@ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ #include -#include + char * strpbrk(const char *s1, const char *s2) @@ -12,7 +12,7 @@ strpbrk(const char *s1, const char *s2) { for (scanp = s2; (sc = *scanp++) != 0;) if (sc == c) - return unconst(s1 - 1, char *); + return (char *)(s1 - 1); } return 0; } diff --git a/reactos/lib/crtdll/string/strrchr.c b/reactos/lib/crtdll/string/strrchr.c index c822b2360b5..e6f3399494f 100644 --- a/reactos/lib/crtdll/string/strrchr.c +++ b/reactos/lib/crtdll/string/strrchr.c @@ -1,7 +1,7 @@ /* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ #include -#include +//#include char * strrchr(const char *s, int c) @@ -16,6 +16,6 @@ strrchr(const char *s, int c) } if (cc == 0) sp = s; - return unconst(sp, char *); + return (char *)sp; } diff --git a/reactos/lib/crtdll/string/strstr.c b/reactos/lib/crtdll/string/strstr.c index 0b20d2d91e3..7a102a1827f 100644 --- a/reactos/lib/crtdll/string/strstr.c +++ b/reactos/lib/crtdll/string/strstr.c @@ -1,6 +1,6 @@ /* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ #include -#include +//#include char * strstr(const char *s, const char *find) @@ -19,5 +19,5 @@ strstr(const char *s, const char *find) } while (strncmp(s, find, len) != 0); s--; } - return unconst(s, char *); + return (char *)s; } diff --git a/reactos/lib/crtdll/string/strtoul.c b/reactos/lib/crtdll/string/strtoul.c new file mode 100644 index 00000000000..21285770251 --- /dev/null +++ b/reactos/lib/crtdll/string/strtoul.c @@ -0,0 +1,27 @@ +#include +#include + +unsigned long 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; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/string/strupr.c b/reactos/lib/crtdll/string/strupr.c new file mode 100644 index 00000000000..f0bf755ea0b --- /dev/null +++ b/reactos/lib/crtdll/string/strupr.c @@ -0,0 +1,24 @@ +/* + * The C RunTime DLL + * + * Implements C run-time functionality as known from UNIX. + * + * Copyright 1996,1998 Marcus Meissner + * Copyright 1996 Jukka Iivonen + * Copyright 1997 Uwe Bonnes + */ + + +#include +#include + +char *strupr(char *x) +{ + char *y=x; + + while (*y) { + *y=toupper(*y); + y++; + } + return x; +} diff --git a/reactos/lib/crtdll/string/strxfrm.c b/reactos/lib/crtdll/string/strxfrm.c index ea9533e6391..389b6f5c575 100644 --- a/reactos/lib/crtdll/string/strxfrm.c +++ b/reactos/lib/crtdll/string/strxfrm.c @@ -2,10 +2,7 @@ #include size_t -strxfrm(dst, src, n) - char *dst; - const char *src; - size_t n; +strxfrm(char *dst,const char *src, size_t n) { size_t r = 0; int c; diff --git a/reactos/lib/crtdll/sys_stat/fstat.c b/reactos/lib/crtdll/sys_stat/fstat.c new file mode 100644 index 00000000000..436b6e8ee21 --- /dev/null +++ b/reactos/lib/crtdll/sys_stat/fstat.c @@ -0,0 +1,32 @@ +#include +#include +#include +#include +#include +#include + +void UnixTimeToFileTime( time_t unix_time, FILETIME *filetime, DWORD remainder ); +time_t FileTimeToUnixTime( const FILETIME *filetime, DWORD *remainder ); + +int +fstat(int handle, struct stat *statbuf) +{ + + BY_HANDLE_FILE_INFORMATION FileInformation; + + if (!statbuf) + { + + return -1; + } + + if ( !GetFileInformationByHandle(filehnd(handle),&FileInformation) ) + return -1; + statbuf->st_ctime = FileTimeToUnixTime( &FileInformation.ftCreationTime,NULL); + statbuf->st_atime = FileTimeToUnixTime( &FileInformation.ftLastAccessTime,NULL); + statbuf->st_mtime = FileTimeToUnixTime( &FileInformation.ftLastWriteTime,NULL); + + statbuf->st_dev = handle; + statbuf->st_size = FileInformation.nFileSizeLow; + return 0; +} diff --git a/reactos/lib/crtdll/sys_stat/stat.c b/reactos/lib/crtdll/sys_stat/stat.c new file mode 100644 index 00000000000..5de9b4f1876 --- /dev/null +++ b/reactos/lib/crtdll/sys_stat/stat.c @@ -0,0 +1,22 @@ +#include +#include +#include +#include + +#undef stat +int stat( const char *path, struct stat *buffer ) +{ + return _stat(path,buffer); +} + +int _stat( const char *path, struct stat *buffer ) +{ + int handle = _open(path,_O_RDONLY); + int ret; + + ret = fstat(handle,buffer); + _close(handle); + + return ret; + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/time/ctime.c b/reactos/lib/crtdll/time/ctime.c new file mode 100644 index 00000000000..b16b38fe783 --- /dev/null +++ b/reactos/lib/crtdll/time/ctime.c @@ -0,0 +1,1433 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +/* This file has been modified by DJ Delorie. These modifications are +** Copyright (C) 1995 DJ Delorie, 24 Kirsten Ave, Rochester NH, +** 03867-2954, USA. +*/ + +/* + * Copyright (c) 1987, 1989 Regents of the University of California. + * All rights reserved. + * + * This code is derived from software contributed to Berkeley by + * Arthur David Olson of the National Cancer Institute. + * + * Redistribution and use in source and binary forms are permitted provided + * that: (1) source distributions retain this entire copyright notice and + * comment, and (2) distributions including binaries display the following + * acknowledgement: ``This product includes software developed by the + * University of California, Berkeley and its contributors'' in the + * documentation or other materials provided with the distribution and in + * all advertising materials mentioning features or use of this software. + * Neither the name of the University nor the names of its contributors may + * be used to endorse or promote products derived from this software without + * specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + */ + +#if defined(LIBC_SCCS) && !defined(lint) +static char sccsid[] = "@(#)ctime.c 5.23 (Berkeley) 6/22/90"; +#endif /* LIBC_SCCS and not lint */ + +/* +** Leap second handling from Bradley White (bww@k.gp.cs.cmu.edu). +** POSIX-style TZ environment variable handling from Guy Harris +** (guy@auspex.com). +*/ + + +#ifndef _TM_DEFINED +struct tm { + int tm_sec; + int tm_min; + int tm_hour; + int tm_mday; + int tm_mon; + int tm_year; + int tm_wday; + int tm_yday; + int tm_isdst; + char *tm_zone; + int tm_gmtoff; +}; +#define _TM_DEFINED +#endif + +//#include +#include +#include +#include +#include +#include +#include + +#include +//#include +#include "tzfile.h" + +//#include + +#include + +#include "posixrul.h" + +#define P(s) s +#define alloc_size_t size_t +#define qsort_size_t size_t +#define fread_size_t size_t +#define fwrite_size_t size_t + +#define ACCESS_MODE O_RDONLY|O_BINARY +#define OPEN_MODE O_RDONLY|O_BINARY + +/* +** Someone might make incorrect use of a time zone abbreviation: +** 1. They might reference tzname[0] before calling tzset (explicitly +** or implicitly). +** 2. They might reference tzname[1] before calling tzset (explicitly +** or implicitly). +** 3. They might reference tzname[1] after setting to a time zone +** in which Daylight Saving Time is never observed. +** 4. They might reference tzname[0] after setting to a time zone +** in which Standard Time is never observed. +** 5. They might reference tm.TM_ZONE after calling offtime. +** What's best to do in the above cases is open to debate; +** for now, we just set things up so that in any of the five cases +** WILDABBR is used. Another possibility: initialize tzname[0] to the +** string "tzname[0] used before set", and similarly for the other cases. +** And another: initialize tzname[0] to "ERA", with an explanation in the +** manual page of what this "time zone abbreviation" means (doing this so +** that tzname[0] has the "normal" length of three characters). +*/ +static char WILDABBR[] = " "; + +#ifndef TRUE +#define TRUE 1 +#define FALSE 0 +#endif /* !defined TRUE */ + +static const char GMT[] = "GMT"; + +struct ttinfo { /* time type information */ + long tt_gmtoff; /* GMT offset in seconds */ + int tt_isdst; /* used to set tm_isdst */ + int tt_abbrind; /* abbreviation list index */ + int tt_ttisstd; /* TRUE if transition is std time */ +}; + +struct lsinfo { /* leap second information */ + time_t ls_trans; /* transition time */ + long ls_corr; /* correction to apply */ +}; + +struct state { + int leapcnt; + int timecnt; + int typecnt; + int charcnt; + time_t ats[TZ_MAX_TIMES]; + unsigned char types[TZ_MAX_TIMES]; + struct ttinfo ttis[TZ_MAX_TYPES]; + char chars[(TZ_MAX_CHARS + 1 > sizeof GMT) ? TZ_MAX_CHARS + 1 : sizeof GMT]; + struct lsinfo lsis[TZ_MAX_LEAPS]; +}; + +struct rule { + int r_type; /* type of rule--see below */ + int r_day; /* day number of rule */ + int r_week; /* week number of rule */ + int r_mon; /* month number of rule */ + long r_time; /* transition time of rule */ +}; + +#define JULIAN_DAY 0 /* Jn - Julian day */ +#define DAY_OF_YEAR 1 /* n - day of year */ +#define MONTH_NTH_DAY_OF_WEEK 2 /* Mm.n.d - month, week, day of week */ + +/* +** Prototypes for static functions. +*/ + +static long detzcode P((const char * codep)); +static const char * getzname P((const char * strp)); +static const char * getnum P((const char * strp, int * nump, int min, + int max)); +static const char * getsecs P((const char * strp, long * secsp)); +static const char * getoffset P((const char * strp, long * offsetp)); +static const char * getrule P((const char * strp, struct rule * rulep)); +static void gmtload P((struct state * sp)); +static void gmtsub P((const time_t * timep, long offset, + struct tm * tmp)); +static void localsub P((const time_t * timep, long offset, + struct tm * tmp)); +static void normalize P((int * tensptr, int * unitsptr, int base)); +static void settzname P((void)); +static time_t time1 P((struct tm * tmp, void (* funcp)(const time_t * const, const long, struct tm * const), + long offset)); +static time_t time2 P((struct tm *tmp, void (* funcp)(const time_t * const, const long, struct tm * const), + long offset, int * okayp)); +static void timesub P((const time_t * timep, long offset, + const struct state * sp, struct tm * tmp)); +static int tmcomp P((const struct tm * atmp, + const struct tm * btmp)); +static time_t transtime P((time_t janfirst, int year, + const struct rule * rulep, long offset)); +static int tzload P((const char * name, struct state * sp)); +static int tzparse P((const char * name, struct state * sp, + int lastditch)); +static void tzsetwall(void); + +#ifdef ALL_STATE +static struct state *lclptr; +static struct state *gmtptr; +#endif /* defined ALL_STATE */ + +#ifndef ALL_STATE +static struct state lclmem; +static struct state gmtmem; +#define lclptr (&lclmem) +#define gmtptr (&gmtmem) +#endif /* State Farm */ + +static int lcl_is_set; +static int gmt_is_set; + +char * tzname[2] = { + WILDABBR, + WILDABBR +}; + +static long +detzcode(const char * const codep) +{ + long result; + int i; + + result = 0; + for (i = 0; i < 4; ++i) + result = (result << 8) | (codep[i] & 0xff); + return result; +} + +static void +settzname(void) +{ + const struct state * const sp = lclptr; + int i; + + tzname[0] = WILDABBR; + tzname[1] = WILDABBR; +#ifdef ALL_STATE + if (sp == NULL) + { + tzname[0] = tzname[1] = GMT; + return; + } +#endif /* defined ALL_STATE */ + for (i = 0; i < sp->typecnt; ++i) + { + register const struct ttinfo * const ttisp = &sp->ttis[i]; + + tzname[ttisp->tt_isdst] = + (char *)&sp->chars[ttisp->tt_abbrind]; +#if 0 + if (ttisp->tt_isdst) + _daylight = 1; + if (i == 0 || !ttisp->tt_isdst) + _timezone = -(ttisp->tt_gmtoff); + if (i == 0 || ttisp->tt_isdst) + _altzone = -(ttisp->tt_gmtoff); +#endif + } + /* + ** And to get the latest zone names into tzname. . . + */ + for (i = 0; i < sp->timecnt; ++i) + { + const struct ttinfo * const ttisp = &sp->ttis[sp->types[i]]; + + tzname[ttisp->tt_isdst] = (char *)&sp->chars[ttisp->tt_abbrind]; + } +} + +static char * +tzdir(void) +{ + static char dir[80]={0}, *cp; + if (dir[0] == 0) + { + if ((cp = getenv("TZDIR"))) + { + strcpy(dir, cp); + } + else if ((cp = getenv("DJDIR"))) + { + strcpy(dir, cp); + strcat(dir, "/zoneinfo"); + } + else + strcpy(dir, "./"); + } + return dir; +} + +static int +tzload(const char *name, struct state * const sp) +{ + const char * p; + int i; + int fid; + char fullname[FILENAME_MAX + 1]; + const struct tzhead * tzhp; + char buf[sizeof *sp + sizeof *tzhp]; + int ttisstdcnt; + + if (name == NULL && (name = TZDEFAULT) == NULL) + return -1; + + if (name[0] == ':') + ++name; + if (name[0] != '/') + { + if ((p = tzdir()) == NULL) + return -1; + if ((strlen(p) + strlen(name) + 1) >= sizeof fullname) + return -1; + strcpy(fullname, p); + strcat(fullname, "/"); + strcat(fullname, name); + name = fullname; + } + + if ((fid = open(name, OPEN_MODE)) == -1) + { + const char *base = strrchr(name, '/'); + if (base) + base++; + else + base = name; + if (strcmp(base, "posixrules")) + return -1; + + /* We've got a built-in copy of posixrules just in case */ + memcpy(buf, _posixrules_data, sizeof(_posixrules_data)); + i = sizeof(_posixrules_data); + } + else + { + i = read(fid, buf, sizeof buf); + if (close(fid) != 0 || i < sizeof *tzhp) + return -1; + } + + tzhp = (struct tzhead *) buf; + ttisstdcnt = (int) detzcode(tzhp->tzh_ttisstdcnt); + sp->leapcnt = (int) detzcode(tzhp->tzh_leapcnt); + sp->timecnt = (int) detzcode(tzhp->tzh_timecnt); + sp->typecnt = (int) detzcode(tzhp->tzh_typecnt); + sp->charcnt = (int) detzcode(tzhp->tzh_charcnt); + if (sp->leapcnt < 0 || sp->leapcnt > TZ_MAX_LEAPS || + sp->typecnt <= 0 || sp->typecnt > TZ_MAX_TYPES || + sp->timecnt < 0 || sp->timecnt > TZ_MAX_TIMES || + sp->charcnt < 0 || sp->charcnt > TZ_MAX_CHARS || + (ttisstdcnt != sp->typecnt && ttisstdcnt != 0)) + return -1; + if (i < sizeof *tzhp + + sp->timecnt * (4 + sizeof (char)) + + sp->typecnt * (4 + 2 * sizeof (char)) + + sp->charcnt * sizeof (char) + + sp->leapcnt * 2 * 4 + + ttisstdcnt * sizeof (char)) + return -1; + p = buf + sizeof *tzhp; + for (i = 0; i < sp->timecnt; ++i) + { + sp->ats[i] = detzcode(p); + p += 4; + } + for (i = 0; i < sp->timecnt; ++i) + { + sp->types[i] = (unsigned char) *p++; + if (sp->types[i] >= sp->typecnt) + return -1; + } + for (i = 0; i < sp->typecnt; ++i) + { + struct ttinfo * ttisp; + + ttisp = &sp->ttis[i]; + ttisp->tt_gmtoff = detzcode(p); + p += 4; + ttisp->tt_isdst = (unsigned char) *p++; + if (ttisp->tt_isdst != 0 && ttisp->tt_isdst != 1) + return -1; + ttisp->tt_abbrind = (unsigned char) *p++; + if (ttisp->tt_abbrind < 0 || + ttisp->tt_abbrind > sp->charcnt) + return -1; + } + for (i = 0; i < sp->charcnt; ++i) + sp->chars[i] = *p++; + sp->chars[i] = '\0'; /* ensure '\0' at end */ + for (i = 0; i < sp->leapcnt; ++i) + { + struct lsinfo * lsisp; + + lsisp = &sp->lsis[i]; + lsisp->ls_trans = detzcode(p); + p += 4; + lsisp->ls_corr = detzcode(p); + p += 4; + } + for (i = 0; i < sp->typecnt; ++i) + { + struct ttinfo * ttisp; + + ttisp = &sp->ttis[i]; + if (ttisstdcnt == 0) + ttisp->tt_ttisstd = FALSE; + else + { + ttisp->tt_ttisstd = *p++; + if (ttisp->tt_ttisstd != TRUE && + ttisp->tt_ttisstd != FALSE) + return -1; + } + } + return 0; +} + +static const int mon_lengths[2][MONSPERYEAR] = { +{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }, +{ 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 } +}; + +static const int year_lengths[2] = { +DAYSPERNYEAR, DAYSPERLYEAR +}; + +/* +** Given a pointer into a time zone string, scan until a character that is not +** a valid character in a zone name is found. Return a pointer to that +** character. +*/ + +static const char * +getzname(const char *strp) +{ + char c; + + while ((c = *strp) != '\0' && !isdigit(c) && c != ',' && c != '-' && + c != '+') + ++strp; + return strp; +} + +/* +** Given a pointer into a time zone string, extract a number from that string. +** Check that the number is within a specified range; if it is not, return +** NULL. +** Otherwise, return a pointer to the first character not part of the number. +*/ + +static const char * +getnum(const char *strp, int * const nump, const int min, const int max) +{ + char c; + int num; + + if (strp == NULL || !isdigit(*strp)) + return NULL; + num = 0; + while ((c = *strp) != '\0' && isdigit(c)) + { + num = num * 10 + (c - '0'); + if (num > max) + return NULL; + ++strp; + } + if (num < min) + return NULL; + *nump = num; + return strp; +} + +/* +** Given a pointer into a time zone string, extract a number of seconds, +** in hh[:mm[:ss]] form, from the string. +** If any error occurs, return NULL. +** Otherwise, return a pointer to the first character not part of the number +** of seconds. +*/ + +static const char * +getsecs(const char *strp, long * const secsp) +{ + int num; + + strp = getnum(strp, &num, 0, HOURSPERDAY); + if (strp == NULL) + return NULL; + *secsp = num * SECSPERHOUR; + if (*strp == ':') + { + ++strp; + strp = getnum(strp, &num, 0, MINSPERHOUR - 1); + if (strp == NULL) + return NULL; + *secsp += num * SECSPERMIN; + if (*strp == ':') + { + ++strp; + strp = getnum(strp, &num, 0, SECSPERMIN - 1); + if (strp == NULL) + return NULL; + *secsp += num; + } + } + return strp; +} + +/* +** Given a pointer into a time zone string, extract an offset, in +** [+-]hh[:mm[:ss]] form, from the string. +** If any error occurs, return NULL. +** Otherwise, return a pointer to the first character not part of the time. +*/ + +static const char * +getoffset(const char *strp, long * const offsetp) +{ + int neg; + + if (*strp == '-') + { + neg = 1; + ++strp; + } + else if (isdigit(*strp) || *strp++ == '+') + neg = 0; + else + return NULL; /* illegal offset */ + strp = getsecs(strp, offsetp); + if (strp == NULL) + return NULL; /* illegal time */ + if (neg) + *offsetp = -*offsetp; + return strp; +} + +/* +** Given a pointer into a time zone string, extract a rule in the form +** date[/time]. See POSIX section 8 for the format of "date" and "time". +** If a valid rule is not found, return NULL. +** Otherwise, return a pointer to the first character not part of the rule. +*/ + +static const char * +getrule(const char *strp, struct rule * const rulep) +{ + if (*strp == 'J') + { + /* + ** Julian day. + */ + rulep->r_type = JULIAN_DAY; + ++strp; + strp = getnum(strp, &rulep->r_day, 1, DAYSPERNYEAR); + } + else if (*strp == 'M') + { + /* + ** Month, week, day. + */ + rulep->r_type = MONTH_NTH_DAY_OF_WEEK; + ++strp; + strp = getnum(strp, &rulep->r_mon, 1, MONSPERYEAR); + if (strp == NULL) + return NULL; + if (*strp++ != '.') + return NULL; + strp = getnum(strp, &rulep->r_week, 1, 5); + if (strp == NULL) + return NULL; + if (*strp++ != '.') + return NULL; + strp = getnum(strp, &rulep->r_day, 0, DAYSPERWEEK - 1); + } + else if (isdigit(*strp)) + { + /* + ** Day of year. + */ + rulep->r_type = DAY_OF_YEAR; + strp = getnum(strp, &rulep->r_day, 0, DAYSPERLYEAR - 1); + } + else + return NULL; /* invalid format */ + if (strp == NULL) + return NULL; + if (*strp == '/') + { + /* + ** Time specified. + */ + ++strp; + strp = getsecs(strp, &rulep->r_time); + } + else + rulep->r_time = 2 * SECSPERHOUR; /* default = 2:00:00 */ + return strp; +} + +/* +** Given the Epoch-relative time of January 1, 00:00:00 GMT, in a year, the +** year, a rule, and the offset from GMT at the time that rule takes effect, +** calculate the Epoch-relative time that rule takes effect. +*/ + +static time_t +transtime(const time_t janfirst, const int year, const struct rule * const rulep, const long offset) +{ + int leapyear; + time_t value=0; + int i; + int d, m1, yy0, yy1, yy2, dow; + + leapyear = isleap(year); + switch (rulep->r_type) + { + + case JULIAN_DAY: + /* + ** Jn - Julian day, 1 == January 1, 60 == March 1 even in leap + ** years. + ** In non-leap years, or if the day number is 59 or less, just + ** add SECSPERDAY times the day number-1 to the time of + ** January 1, midnight, to get the day. + */ + value = janfirst + (rulep->r_day - 1) * SECSPERDAY; + if (leapyear && rulep->r_day >= 60) + value += SECSPERDAY; + break; + + case DAY_OF_YEAR: + /* + ** n - day of year. + ** Just add SECSPERDAY times the day number to the time of + ** January 1, midnight, to get the day. + */ + value = janfirst + rulep->r_day * SECSPERDAY; + break; + + case MONTH_NTH_DAY_OF_WEEK: + /* + ** Mm.n.d - nth "dth day" of month m. + */ + value = janfirst; + for (i = 0; i < rulep->r_mon - 1; ++i) + value += mon_lengths[leapyear][i] * SECSPERDAY; + + /* + ** Use Zeller's Congruence to get day-of-week of first day of + ** month. + */ + m1 = (rulep->r_mon + 9) % 12 + 1; + yy0 = (rulep->r_mon <= 2) ? (year - 1) : year; + yy1 = yy0 / 100; + yy2 = yy0 % 100; + dow = ((26 * m1 - 2) / 10 + + 1 + yy2 + yy2 / 4 + yy1 / 4 - 2 * yy1) % 7; + if (dow < 0) + dow += DAYSPERWEEK; + + /* + ** "dow" is the day-of-week of the first day of the month. Get + ** the day-of-month (zero-origin) of the first "dow" day of the + ** month. + */ + d = rulep->r_day - dow; + if (d < 0) + d += DAYSPERWEEK; + for (i = 1; i < rulep->r_week; ++i) + { + if (d + DAYSPERWEEK >= + mon_lengths[leapyear][rulep->r_mon - 1]) + break; + d += DAYSPERWEEK; + } + + /* + ** "d" is the day-of-month (zero-origin) of the day we want. + */ + value += d * SECSPERDAY; + break; + } + + /* + ** "value" is the Epoch-relative time of 00:00:00 GMT on the day in + ** question. To get the Epoch-relative time of the specified local + ** time on that day, add the transition time and the current offset + ** from GMT. + */ + return value + rulep->r_time + offset; +} + +/* +** Given a POSIX section 8-style TZ string, fill in the rule tables as +** appropriate. +*/ + +static int +tzparse(const char *name, struct state * const sp, const int lastditch) +{ + const char * stdname; + const char * dstname=0; + int stdlen; + int dstlen; + long stdoffset; + long dstoffset; + time_t * atp; + unsigned char * typep; + char * cp; + int load_result; + + stdname = name; + if (lastditch) + { + stdlen = strlen(name); /* length of standard zone name */ + name += stdlen; + if (stdlen >= sizeof sp->chars) + stdlen = (sizeof sp->chars) - 1; + } + else + { + name = getzname(name); + stdlen = name - stdname; + if (stdlen < 3) + return -1; + } + if (*name == '\0') + return -1; + else + { + name = getoffset(name, &stdoffset); + if (name == NULL) + return -1; + } + load_result = tzload(TZDEFRULES, sp); + if (load_result != 0) + sp->leapcnt = 0; /* so, we're off a little */ + if (*name != '\0') + { + dstname = name; + name = getzname(name); + dstlen = name - dstname; /* length of DST zone name */ + if (dstlen < 3) + return -1; + if (*name != '\0' && *name != ',' && *name != ';') + { + name = getoffset(name, &dstoffset); + if (name == NULL) + return -1; + } + else + dstoffset = stdoffset - SECSPERHOUR; + if (*name == ',' || *name == ';') + { + struct rule start; + struct rule end; + int year; + time_t janfirst; + time_t starttime; + time_t endtime; + + ++name; + if ((name = getrule(name, &start)) == NULL) + return -1; + if (*name++ != ',') + return -1; + if ((name = getrule(name, &end)) == NULL) + return -1; + if (*name != '\0') + return -1; + sp->typecnt = 2; /* standard time and DST */ + /* + ** Two transitions per year, from EPOCH_YEAR to 2037. + */ + sp->timecnt = 2 * (2037 - EPOCH_YEAR + 1); + if (sp->timecnt > TZ_MAX_TIMES) + return -1; + sp->ttis[0].tt_gmtoff = -dstoffset; + sp->ttis[0].tt_isdst = 1; + sp->ttis[0].tt_abbrind = stdlen + 1; + sp->ttis[1].tt_gmtoff = -stdoffset; + sp->ttis[1].tt_isdst = 0; + sp->ttis[1].tt_abbrind = 0; + atp = sp->ats; + typep = sp->types; + janfirst = 0; + for (year = EPOCH_YEAR; year <= 2037; ++year) + { + starttime = transtime(janfirst, year, &start, + stdoffset); + endtime = transtime(janfirst, year, &end, + dstoffset); + if (starttime > endtime) + { + *atp++ = endtime; + *typep++ = 1; /* DST ends */ + *atp++ = starttime; + *typep++ = 0; /* DST begins */ + } + else + { + *atp++ = starttime; + *typep++ = 0; /* DST begins */ + *atp++ = endtime; + *typep++ = 1; /* DST ends */ + } + janfirst += + year_lengths[isleap(year)] * SECSPERDAY; + } + } + else + { + int sawstd; + int sawdst; + long stdfix; + long dstfix; + long oldfix; + int isdst; + int i; + + if (*name != '\0') + return -1; + if (load_result != 0) + return -1; + /* + ** Compute the difference between the real and + ** prototype standard and summer time offsets + ** from GMT, and put the real standard and summer + ** time offsets into the rules in place of the + ** prototype offsets. + */ + sawstd = FALSE; + sawdst = FALSE; + stdfix = 0; + dstfix = 0; + for (i = 0; i < sp->typecnt; ++i) + { + if (sp->ttis[i].tt_isdst) + { + oldfix = dstfix; + dstfix = + sp->ttis[i].tt_gmtoff + dstoffset; + if (sawdst && (oldfix != dstfix)) + return -1; + sp->ttis[i].tt_gmtoff = -dstoffset; + sp->ttis[i].tt_abbrind = stdlen + 1; + sawdst = TRUE; + } + else + { + oldfix = stdfix; + stdfix = + sp->ttis[i].tt_gmtoff + stdoffset; + if (sawstd && (oldfix != stdfix)) + return -1; + sp->ttis[i].tt_gmtoff = -stdoffset; + sp->ttis[i].tt_abbrind = 0; + sawstd = TRUE; + } + } + /* + ** Make sure we have both standard and summer time. + */ + if (!sawdst || !sawstd) + return -1; + /* + ** Now correct the transition times by shifting + ** them by the difference between the real and + ** prototype offsets. Note that this difference + ** can be different in standard and summer time; + ** the prototype probably has a 1-hour difference + ** between standard and summer time, but a different + ** difference can be specified in TZ. + */ + isdst = FALSE; /* we start in standard time */ + for (i = 0; i < sp->timecnt; ++i) + { + const struct ttinfo * ttisp; + + /* + ** If summer time is in effect, and the + ** transition time was not specified as + ** standard time, add the summer time + ** offset to the transition time; + ** otherwise, add the standard time offset + ** to the transition time. + */ + ttisp = &sp->ttis[sp->types[i]]; + sp->ats[i] += + (isdst && !ttisp->tt_ttisstd) ? + dstfix : stdfix; + isdst = ttisp->tt_isdst; + } + } + } + else + { + dstlen = 0; + sp->typecnt = 1; /* only standard time */ + sp->timecnt = 0; + sp->ttis[0].tt_gmtoff = -stdoffset; + sp->ttis[0].tt_isdst = 0; + sp->ttis[0].tt_abbrind = 0; + } + sp->charcnt = stdlen + 1; + if (dstlen != 0) + sp->charcnt += dstlen + 1; + if (sp->charcnt > sizeof sp->chars) + return -1; + cp = sp->chars; + (void) strncpy(cp, stdname, stdlen); + cp += stdlen; + *cp++ = '\0'; + if (dstlen != 0) + { + (void) strncpy(cp, dstname, dstlen); + *(cp + dstlen) = '\0'; + } + return 0; +} + +static void +gmtload(struct state * const sp) +{ + if (tzload(GMT, sp) != 0) + (void) tzparse(GMT, sp, TRUE); +} + +void +tzset(void) +{ + const char * name; + + name = getenv("TZ"); + if (name == NULL) + { + tzsetwall(); + return; + } + lcl_is_set = TRUE; +#ifdef ALL_STATE + if (lclptr == NULL) + { + lclptr = (struct state *) malloc(sizeof *lclptr); + if (lclptr == NULL) + { + settzname(); /* all we can do */ + return; + } + } +#endif /* defined ALL_STATE */ + if (*name == '\0') + { + /* + ** User wants it fast rather than right. + */ + lclptr->leapcnt = 0; /* so, we're off a little */ + lclptr->timecnt = 0; + lclptr->ttis[0].tt_gmtoff = 0; + lclptr->ttis[0].tt_abbrind = 0; + (void) strcpy(lclptr->chars, GMT); + } + else if (tzload(name, lclptr) != 0) + if (name[0] == ':' || tzparse(name, lclptr, FALSE) != 0) + gmtload(lclptr); + settzname(); +} + +void +tzsetwall(void) +{ + lcl_is_set = TRUE; +#ifdef ALL_STATE + if (lclptr == NULL) + { + lclptr = (struct state *) malloc(sizeof *lclptr); + if (lclptr == NULL) + { + settzname(); /* all we can do */ + return; + } + } +#endif /* defined ALL_STATE */ + if (tzload((char *) NULL, lclptr) != 0) + gmtload(lclptr); + settzname(); +} + +/* +** The easy way to behave "as if no library function calls" localtime +** is to not call it--so we drop its guts into "localsub", which can be +** freely called. (And no, the PANS doesn't require the above behavior-- +** but it *is* desirable.) +** +** The unused offset argument is for the benefit of mktime variants. +*/ + +/*ARGSUSED*/ +static void +localsub(const time_t * const timep, const long offset, struct tm * const tmp) +{ + const struct state * sp; + const struct ttinfo * ttisp; + int i; + const time_t t = *timep; + + if (!lcl_is_set) + tzset(); + sp = lclptr; +#ifdef ALL_STATE + if (sp == NULL) + { + gmtsub(timep, offset, tmp); + return; + } +#endif /* defined ALL_STATE */ + if (sp->timecnt == 0 || t < sp->ats[0]) + { + i = 0; + while (sp->ttis[i].tt_isdst) + if (++i >= sp->typecnt) + { + i = 0; + break; + } + } + else + { + for (i = 1; i < sp->timecnt; ++i) + if (t < sp->ats[i]) + break; + i = sp->types[i - 1]; + } + ttisp = &sp->ttis[i]; + /* + ** To get (wrong) behavior that's compatible with System V Release 2.0 + ** you'd replace the statement below with + ** t += ttisp->tt_gmtoff; + ** timesub(&t, 0L, sp, tmp); + */ + timesub(&t, ttisp->tt_gmtoff, sp, tmp); + tmp->tm_isdst = ttisp->tt_isdst; + tzname[tmp->tm_isdst] = (char *)&sp->chars[ttisp->tt_abbrind]; + tmp->tm_zone = (char *)&sp->chars[ttisp->tt_abbrind]; +} + +struct tm * +localtime(const time_t * const timep) +{ + static struct tm tm; + + localsub(timep, 0L, &tm); + return &tm; +} + +/* +** gmtsub is to gmtime as localsub is to localtime. +*/ + +static void +gmtsub(const time_t * const timep, const long offset, struct tm * const tmp) +{ + if (!gmt_is_set) + { + gmt_is_set = TRUE; +#ifdef ALL_STATE + gmtptr = (struct state *) malloc(sizeof *gmtptr); + if (gmtptr != NULL) +#endif /* defined ALL_STATE */ + gmtload(gmtptr); + } + timesub(timep, offset, gmtptr, tmp); + /* + ** Could get fancy here and deliver something such as + ** "GMT+xxxx" or "GMT-xxxx" if offset is non-zero, + ** but this is no time for a treasure hunt. + */ + if (offset != 0) + tmp->tm_zone = WILDABBR; + else + { +#ifdef ALL_STATE + if (gmtptr == NULL) + tmp->TM_ZONE = GMT; + else + tmp->TM_ZONE = gmtptr->chars; +#endif /* defined ALL_STATE */ +#ifndef ALL_STATE + tmp->tm_zone = gmtptr->chars; +#endif /* State Farm */ + } +} + +struct tm * +gmtime(const time_t * const timep) +{ + static struct tm tm; + + gmtsub(timep, 0L, &tm); + return &tm; +} + +static void +timesub(const time_t * const timep, const long offset, const struct state * const sp, struct tm * const tmp) +{ + const struct lsinfo * lp; + long days; + long rem; + int y; + int yleap; + const int * ip; + long corr; + int hit; + int i; + + corr = 0; + hit = FALSE; +#ifdef ALL_STATE + i = (sp == NULL) ? 0 : sp->leapcnt; +#endif /* defined ALL_STATE */ +#ifndef ALL_STATE + i = sp->leapcnt; +#endif /* State Farm */ + while (--i >= 0) + { + lp = &sp->lsis[i]; + if (*timep >= lp->ls_trans) + { + if (*timep == lp->ls_trans) + hit = ((i == 0 && lp->ls_corr > 0) || + lp->ls_corr > sp->lsis[i - 1].ls_corr); + corr = lp->ls_corr; + break; + } + } + days = *timep / SECSPERDAY; + rem = *timep % SECSPERDAY; +#ifdef mc68k + if (*timep == 0x80000000) + { + /* + ** A 3B1 muffs the division on the most negative number. + */ + days = -24855; + rem = -11648; + } +#endif /* mc68k */ + rem += (offset - corr); + while (rem < 0) + { + rem += SECSPERDAY; + --days; + } + while (rem >= SECSPERDAY) + { + rem -= SECSPERDAY; + ++days; + } + tmp->tm_hour = (int) (rem / SECSPERHOUR); + rem = rem % SECSPERHOUR; + tmp->tm_min = (int) (rem / SECSPERMIN); + tmp->tm_sec = (int) (rem % SECSPERMIN); + if (hit) + /* + ** A positive leap second requires a special + ** representation. This uses "... ??:59:60". + */ + ++(tmp->tm_sec); + tmp->tm_wday = (int) ((EPOCH_WDAY + days) % DAYSPERWEEK); + if (tmp->tm_wday < 0) + tmp->tm_wday += DAYSPERWEEK; + y = EPOCH_YEAR; + if (days >= 0) + for ( ; ; ) + { + yleap = isleap(y); + if (days < (long) year_lengths[yleap]) + break; + ++y; + days = days - (long) year_lengths[yleap]; + } + else + do { + --y; + yleap = isleap(y); + days = days + (long) year_lengths[yleap]; + } while (days < 0); + tmp->tm_year = y - TM_YEAR_BASE; + tmp->tm_yday = (int) days; + ip = mon_lengths[yleap]; + for (tmp->tm_mon = 0; days >= (long) ip[tmp->tm_mon]; ++(tmp->tm_mon)) + days = days - (long) ip[tmp->tm_mon]; + tmp->tm_mday = (int) (days + 1); + tmp->tm_isdst = 0; + tmp->tm_gmtoff = offset; +} + +/* +** A la X3J11 +*/ + +char * +asctime(const struct tm *timeptr) +{ + static const char wday_name[DAYSPERWEEK][3] = { + "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" + }; + static const char mon_name[MONSPERYEAR][3] = { + "Jan", "Feb", "Mar", "Apr", "May", "Jun", + "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" + }; + static char result[26]; + + (void) sprintf(result, "%.3s %.3s%3d %02d:%02d:%02d %d\n", + wday_name[timeptr->tm_wday], + mon_name[timeptr->tm_mon], + timeptr->tm_mday, timeptr->tm_hour, + timeptr->tm_min, timeptr->tm_sec, + TM_YEAR_BASE + timeptr->tm_year); + return result; +} + +char * +ctime(const time_t * const timep) +{ + return asctime(localtime(timep)); +} + +/* +** Adapted from code provided by Robert Elz, who writes: +** The "best" way to do mktime I think is based on an idea of Bob +** Kridle's (so its said...) from a long time ago. (mtxinu!kridle now). +** It does a binary search of the time_t space. Since time_t's are +** just 32 bits, its a max of 32 iterations (even at 64 bits it +** would still be very reasonable). +*/ + +#ifndef WRONG +#define WRONG (-1) +#endif /* !defined WRONG */ + +static void +normalize(int * const tensptr, int * const unitsptr, const int base) +{ + if (*unitsptr >= base) + { + *tensptr += *unitsptr / base; + *unitsptr %= base; + } + else if (*unitsptr < 0) + { + --*tensptr; + *unitsptr += base; + if (*unitsptr < 0) + { + *tensptr -= 1 + (-*unitsptr) / base; + *unitsptr = base - (-*unitsptr) % base; + } + } +} + +static int +tmcomp(const struct tm * const atmp, const struct tm * const btmp) +{ + int result; + + if ((result = (atmp->tm_year - btmp->tm_year)) == 0 && + (result = (atmp->tm_mon - btmp->tm_mon)) == 0 && + (result = (atmp->tm_mday - btmp->tm_mday)) == 0 && + (result = (atmp->tm_hour - btmp->tm_hour)) == 0 && + (result = (atmp->tm_min - btmp->tm_min)) == 0) + result = atmp->tm_sec - btmp->tm_sec; + return result; +} + +static time_t +time2(struct tm *tmp, void (*const funcp)(const time_t *const,const long,struct tm *), const long offset, int * const okayp) +{ + const struct state * sp; + int dir; + int bits; + int i, j ; + int saved_seconds; + time_t newt; + time_t t; + struct tm yourtm, mytm; + + *okayp = FALSE; + yourtm = *tmp; + if (yourtm.tm_sec >= SECSPERMIN + 2 || yourtm.tm_sec < 0) + normalize(&yourtm.tm_min, &yourtm.tm_sec, SECSPERMIN); + normalize(&yourtm.tm_hour, &yourtm.tm_min, MINSPERHOUR); + normalize(&yourtm.tm_mday, &yourtm.tm_hour, HOURSPERDAY); + normalize(&yourtm.tm_year, &yourtm.tm_mon, MONSPERYEAR); + while (yourtm.tm_mday <= 0) + { + --yourtm.tm_year; + yourtm.tm_mday += + year_lengths[isleap(yourtm.tm_year + TM_YEAR_BASE)]; + } + for ( ; ; ) + { + i = mon_lengths[isleap(yourtm.tm_year + + TM_YEAR_BASE)][yourtm.tm_mon]; + if (yourtm.tm_mday <= i) + break; + yourtm.tm_mday -= i; + if (++yourtm.tm_mon >= MONSPERYEAR) + { + yourtm.tm_mon = 0; + ++yourtm.tm_year; + } + } + saved_seconds = yourtm.tm_sec; + yourtm.tm_sec = 0; + /* + ** Calculate the number of magnitude bits in a time_t + ** (this works regardless of whether time_t is + ** signed or unsigned, though lint complains if unsigned). + */ + for (bits = 0, t = 1; t > 0; ++bits, t <<= 1) + ; + /* + ** If time_t is signed, then 0 is the median value, + ** if time_t is unsigned, then 1 << bits is median. + */ + t = (time_t) 1 << bits; + for ( ; ; ) + { + (*funcp)(&t, offset, &mytm); + dir = tmcomp(&mytm, &yourtm); + if (dir != 0) + { + if (bits-- < 0) + return WRONG; + if (bits < 0) + --t; + else if (dir > 0) + t -= (time_t) 1 << bits; + else t += (time_t) 1 << bits; + continue; + } + if (yourtm.tm_isdst < 0 || mytm.tm_isdst == yourtm.tm_isdst) + break; + /* + ** Right time, wrong type. + ** Hunt for right time, right type. + ** It's okay to guess wrong since the guess + ** gets checked. + */ + sp = (const struct state *) + ((funcp == localsub) ? lclptr : gmtptr); +#ifdef ALL_STATE + if (sp == NULL) + return WRONG; +#endif /* defined ALL_STATE */ + for (i = 0; i < sp->typecnt; ++i) + { + if (sp->ttis[i].tt_isdst != yourtm.tm_isdst) + continue; + for (j = 0; j < sp->typecnt; ++j) + { + if (sp->ttis[j].tt_isdst == yourtm.tm_isdst) + continue; + newt = t + sp->ttis[j].tt_gmtoff - + sp->ttis[i].tt_gmtoff; + (*funcp)(&newt, offset, &mytm); + if (tmcomp(&mytm, &yourtm) != 0) + continue; + if (mytm.tm_isdst != yourtm.tm_isdst) + continue; + /* + ** We have a match. + */ + t = newt; + goto label; + } + } + return WRONG; + } + label: + t += saved_seconds; + (*funcp)(&t, offset, tmp); + *okayp = TRUE; + return t; +} + +static time_t +time1(struct tm * const tmp, void (*const funcp)(const time_t * const, const long, struct tm *), const long offset) +{ + time_t t; + const struct state * sp; + int samei, otheri; + int okay; + + if (tmp->tm_isdst > 1) + tmp->tm_isdst = 1; + t = time2(tmp, funcp, offset, &okay); + if (okay || tmp->tm_isdst < 0) + return t; + /* + ** We're supposed to assume that somebody took a time of one type + ** and did some math on it that yielded a "struct tm" that's bad. + ** We try to divine the type they started from and adjust to the + ** type they need. + */ + sp = (const struct state *) ((funcp == localsub) ? lclptr : gmtptr); +#ifdef ALL_STATE + if (sp == NULL) + return WRONG; +#endif /* defined ALL_STATE */ + for (samei = 0; samei < sp->typecnt; ++samei) + { + if (sp->ttis[samei].tt_isdst != tmp->tm_isdst) + continue; + for (otheri = 0; otheri < sp->typecnt; ++otheri) + { + if (sp->ttis[otheri].tt_isdst == tmp->tm_isdst) + continue; + tmp->tm_sec += sp->ttis[otheri].tt_gmtoff - + sp->ttis[samei].tt_gmtoff; + tmp->tm_isdst = !tmp->tm_isdst; + t = time2(tmp, funcp, offset, &okay); + if (okay) + return t; + tmp->tm_sec -= sp->ttis[otheri].tt_gmtoff - + sp->ttis[samei].tt_gmtoff; + tmp->tm_isdst = !tmp->tm_isdst; + } + } + return WRONG; +} + +time_t +mktime(struct tm * tmp) +{ + return time1(tmp, localsub, 0L); +} + + +time_t +time(time_t *t) +{ + SYSTEMTIME SystemTime; + GetLocalTime(&SystemTime); + + +} + diff --git a/reactos/lib/crtdll/time/difftime.c b/reactos/lib/crtdll/time/difftime.c new file mode 100644 index 00000000000..7f1846078d7 --- /dev/null +++ b/reactos/lib/crtdll/time/difftime.c @@ -0,0 +1,8 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include + +double +difftime(time_t time1, time_t time0) +{ + return time1-time0; +} diff --git a/reactos/lib/crtdll/time/posixrul.h b/reactos/lib/crtdll/time/posixrul.h new file mode 100644 index 00000000000..48c5ceeab0d --- /dev/null +++ b/reactos/lib/crtdll/time/posixrul.h @@ -0,0 +1,49 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +/* generated with bin2h from DJGPP/zoneinfo/posixrules */ + +unsigned char _posixrules_data[] = { +0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0, +0,1,16,0,0,0,2,0,0,0,8,0,151,254,240,1,135,225,224,2,119,224,240,3,112,254,96,4,96,253,112,5,80, +224,96,6,64,223,112,7,48,194,96,7,141,25,112,9,16,164,96,9,173,148,240,10,240,134,96,11,224,133,112,12,217,162, +224,13,192,103,112,14,185,132,224,15,169,131,240,16,153,102,224,17,137,101,240,18,121,72,224,19,105,71,240,20,89,42,224, +21,73,41,240,22,57,12,224,23,41,11,240,24,34,41,96,25,8,237,240,26,2,11,96,26,242,10,112,27,225,237,96,28, +209,236,112,29,193,207,96,30,177,206,112,31,161,177,96,32,118,0,240,33,129,147,96,34,85,226,240,35,106,175,224,36,53, +196,240,37,74,145,224,38,21,166,240,39,42,115,224,39,254,195,112,41,10,85,224,41,222,165,112,42,234,55,224,43,190,135, +112,44,211,84,96,45,158,105,112,46,179,54,96,47,126,75,112,48,147,24,96,49,103,103,240,50,114,250,96,51,71,73,240, +52,82,220,96,53,39,43,240,54,50,190,96,55,7,13,240,56,27,218,224,56,230,239,240,57,251,188,224,58,198,209,240,59, +219,158,224,60,175,238,112,61,187,128,224,62,143,208,112,63,155,98,224,64,111,178,112,65,132,127,96,66,79,148,112,67,100, +97,96,68,47,118,112,69,68,67,96,70,15,88,112,71,36,37,96,71,248,116,240,73,4,7,96,73,216,86,240,74,227,233, +96,75,184,56,240,76,205,5,224,77,152,26,240,78,172,231,224,79,119,252,240,80,140,201,224,81,97,25,112,82,108,171,224, +83,64,251,112,84,76,141,224,85,32,221,112,86,44,111,224,87,0,191,112,88,21,140,96,88,224,161,112,89,245,110,96,90, +192,131,112,91,213,80,96,92,169,159,240,93,181,50,96,94,137,129,240,95,149,20,96,96,105,99,240,97,126,48,224,98,73, +69,240,99,94,18,224,100,41,39,240,101,61,244,224,102,18,68,112,103,29,214,224,103,242,38,112,104,253,184,224,105,210,8, +112,106,221,154,224,107,177,234,112,108,198,183,96,109,145,204,112,110,166,153,96,111,113,174,112,112,134,123,96,113,90,202,240, +114,102,93,96,115,58,172,240,116,70,63,96,117,26,142,240,118,47,91,224,118,250,112,240,120,15,61,224,120,218,82,240,121, +239,31,224,122,186,52,240,123,207,1,224,124,163,81,112,125,174,227,224,126,131,51,112,127,142,197,224,128,99,21,112,129,119, +226,96,130,66,247,112,131,87,196,96,132,34,217,112,133,55,166,96,134,11,245,240,135,23,136,96,135,235,215,240,136,247,106, +96,137,203,185,240,138,215,76,96,139,171,155,240,140,192,104,224,141,139,125,240,142,160,74,224,143,107,95,240,144,128,44,224, +145,84,124,112,146,96,14,224,147,52,94,112,148,63,240,224,149,20,64,112,150,41,13,96,150,244,34,112,152,8,239,96,152, +212,4,112,153,232,209,96,154,189,32,240,155,200,179,96,156,157,2,240,157,168,149,96,158,124,228,240,159,136,119,96,160,92, +198,240,161,113,147,224,162,60,168,240,163,81,117,224,164,28,138,240,165,49,87,224,166,5,167,112,167,17,57,224,167,229,137, +112,168,241,27,224,169,197,107,112,170,218,56,96,171,165,77,112,172,186,26,96,173,133,47,112,174,153,252,96,175,101,17,112, +176,121,222,96,177,78,45,240,178,89,192,96,179,46,15,240,180,57,162,96,181,13,241,240,182,34,190,224,182,237,211,240,184, +2,160,224,184,205,181,240,185,226,130,224,186,182,210,112,187,194,100,224,188,150,180,112,189,162,70,224,190,118,150,112,191,130, +40,224,192,86,120,112,193,107,69,96,194,54,90,112,195,75,39,96,196,22,60,112,197,43,9,96,197,255,88,240,199,10,235, +96,199,223,58,240,200,234,205,96,201,191,28,240,202,211,233,224,203,158,254,240,204,179,203,224,205,126,224,240,206,147,173,224, +207,103,253,112,208,115,143,224,209,71,223,112,210,83,113,224,211,39,193,112,212,51,83,224,213,7,163,112,214,28,112,96,214, +231,133,112,215,252,82,96,216,199,103,112,217,220,52,96,218,176,131,240,219,188,22,96,220,144,101,240,221,155,248,96,222,112, +71,240,223,133,20,224,224,80,41,240,225,100,246,224,226,48,11,240,227,68,216,224,228,15,237,240,229,36,186,224,229,249,10, +112,231,4,156,224,231,216,236,112,232,228,126,224,233,184,206,112,234,205,155,96,235,152,176,112,236,173,125,96,237,120,146,112, +238,141,95,96,239,97,174,240,240,109,65,96,241,65,144,240,242,77,35,96,243,33,114,240,244,45,5,96,245,1,84,240,246, +22,33,224,246,225,54,240,247,246,3,224,248,193,24,240,249,213,229,224,250,160,250,240,251,181,199,224,252,138,23,112,253,149, +169,224,254,105,249,112,255,117,139,224,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0, +1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1, +0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0, +1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1, +0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0, +1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1, +0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0, +1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1, +0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,0,1,255,255,199,192,1,0,255,255,185,176,0,4,69,68,84, +0,69,83,84,0,0,0 +}; diff --git a/reactos/lib/crtdll/time/strftime.c b/reactos/lib/crtdll/time/strftime.c new file mode 100644 index 00000000000..32c6973950a --- /dev/null +++ b/reactos/lib/crtdll/time/strftime.c @@ -0,0 +1,243 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ +#include +#ifndef _TM_DEFINED +struct tm { + int tm_sec; + int tm_min; + int tm_hour; + int tm_mday; + int tm_mon; + int tm_year; + int tm_wday; + int tm_yday; + int tm_isdst; + char *tm_zone; + int tm_gmtoff; +}; +#define _TM_DEFINED +#endif + +#include + +#define TM_YEAR_BASE 1900 + +static const char *afmt[] = { + "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat", +}; +static const char *Afmt[] = { + "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", + "Saturday", +}; +static const char *bfmt[] = { + "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", + "Oct", "Nov", "Dec", +}; +static const char *Bfmt[] = { + "January", "February", "March", "April", "May", "June", "July", + "August", "September", "October", "November", "December", +}; + +static size_t gsize; +static char *pt; + +static int +_add(const char *str) +{ + for (;; ++pt, --gsize) + { + if (!gsize) + return 0; + if (!(*pt = *str++)) + return 1; + } +} + +static int +_conv(int n, int digits, char pad) +{ + static char buf[10]; + char *p; + + for (p = buf + sizeof(buf) - 2; n > 0 && p > buf; n /= 10, --digits) + *p-- = n % 10 + '0'; + while (p > buf && digits-- > 0) + *p-- = pad; + return _add(++p); +} + +static size_t +_fmt(const char *format, const struct tm *t) +{ + for (; *format; ++format) + { + if (*format == '%') + switch(*++format) + { + case '\0': + --format; + break; + case 'A': + if (t->tm_wday < 0 || t->tm_wday > 6) + return 0; + if (!_add(Afmt[t->tm_wday])) + return 0; + continue; + case 'a': + if (t->tm_wday < 0 || t->tm_wday > 6) + return 0; + if (!_add(afmt[t->tm_wday])) + return 0; + continue; + case 'B': + if (t->tm_mon < 0 || t->tm_mon > 11) + return 0; + if (!_add(Bfmt[t->tm_mon])) + return 0; + continue; + case 'b': + case 'h': + if (t->tm_mon < 0 || t->tm_mon > 11) + return 0; + if (!_add(bfmt[t->tm_mon])) + return 0; + continue; + case 'C': + if (!_fmt("%a %b %e %H:%M:%S %Y", t)) + return 0; + continue; + case 'c': + if (!_fmt("%m/%d/%y %H:%M:%S", t)) + return 0; + continue; + case 'e': + if (!_conv(t->tm_mday, 2, ' ')) + return 0; + continue; + case 'D': + if (!_fmt("%m/%d/%y", t)) + return 0; + continue; + case 'd': + if (!_conv(t->tm_mday, 2, '0')) + return 0; + continue; + case 'H': + if (!_conv(t->tm_hour, 2, '0')) + return 0; + continue; + case 'I': + if (!_conv(t->tm_hour % 12 ? + t->tm_hour % 12 : 12, 2, '0')) + return 0; + continue; + case 'j': + if (!_conv(t->tm_yday + 1, 3, '0')) + return 0; + continue; + case 'k': + if (!_conv(t->tm_hour, 2, ' ')) + return 0; + continue; + case 'l': + if (!_conv(t->tm_hour % 12 ? + t->tm_hour % 12 : 12, 2, ' ')) + return 0; + continue; + case 'M': + if (!_conv(t->tm_min, 2, '0')) + return 0; + continue; + case 'm': + if (!_conv(t->tm_mon + 1, 2, '0')) + return 0; + continue; + case 'n': + if (!_add("\n")) + return 0; + continue; + case 'p': + if (!_add(t->tm_hour >= 12 ? "PM" : "AM")) + return 0; + continue; + case 'R': + if (!_fmt("%H:%M", t)) + return 0; + continue; + case 'r': + if (!_fmt("%I:%M:%S %p", t)) + return 0; + continue; + case 'S': + if (!_conv(t->tm_sec, 2, '0')) + return 0; + continue; + case 'T': + case 'X': + if (!_fmt("%H:%M:%S", t)) + return 0; + continue; + case 't': + if (!_add("\t")) + return 0; + continue; + case 'U': + if (!_conv((t->tm_yday + 7 - t->tm_wday) / 7, + 2, '0')) + return 0; + continue; + case 'W': + if (!_conv((t->tm_yday + 7 - + (t->tm_wday ? (t->tm_wday - 1) : 6)) + / 7, 2, '0')) + return 0; + continue; + case 'w': + if (!_conv(t->tm_wday, 1, '0')) + return 0; + continue; + case 'x': + if (!_fmt("%m/%d/%y", t)) + return 0; + continue; + case 'y': + if (!_conv((t->tm_year + TM_YEAR_BASE) + % 100, 2, '0')) + return 0; + continue; + case 'Y': + if (!_conv(t->tm_year + TM_YEAR_BASE, 4, '0')) + return 0; + continue; + case 'Z': + if (!t->tm_zone || !_add(t->tm_zone)) + return 0; + continue; + case '%': + /* + * X311J/88-090 (4.12.3.5): if conversion char is + * undefined, behavior is undefined. Print out the + * character itself as printf(3) does. + */ + default: + break; + } + if (!gsize--) + return 0; + *pt++ = *format; + } + return gsize; +} + +size_t +strftime(char *s, size_t maxsize, const char *format, const struct tm *t) +{ + pt = s; + if ((gsize = maxsize) < 1) + return 0; + if (_fmt(format, t)) + { + *pt = '\0'; + return maxsize - gsize; + } + return 0; +} diff --git a/reactos/lib/crtdll/time/time.c b/reactos/lib/crtdll/time/time.c new file mode 100644 index 00000000000..4ff00485a74 --- /dev/null +++ b/reactos/lib/crtdll/time/time.c @@ -0,0 +1,30 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef _TM_DEFINED +struct tm { + int tm_sec; + int tm_min; + int tm_hour; + int tm_mday; + int tm_mon; + int tm_year; + int tm_wday; + int tm_yday; + int tm_isdst; + char *tm_zone; + int tm_gmtoff; +}; +#define _TM_DEFINED +#endif + +#include +#include + + +time_t +time(time_t *t) +{ + SYSTEMTIME SystemTime; + GetLocalTime(&SystemTime); + + +} diff --git a/reactos/lib/crtdll/time/tzfile.h b/reactos/lib/crtdll/time/tzfile.h new file mode 100644 index 00000000000..3999029adb9 --- /dev/null +++ b/reactos/lib/crtdll/time/tzfile.h @@ -0,0 +1,160 @@ +/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */ +#ifndef __dj_include_tzfile_h__ +#define __dj_include_tzfile_h__ + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef __dj_ENFORCE_ANSI_FREESTANDING + +#ifndef __STRICT_ANSI__ + +#ifndef _POSIX_SOURCE + +/* + * Copyright (c) 1988 Regents of the University of California. + * All rights reserved. + * + * This code is derived from software contributed to Berkeley by + * Arthur David Olson of the National Cancer Institute. + * + * Redistribution and use in source and binary forms are permitted provided + * that: (1) source distributions retain this entire copyright notice and + * comment, and (2) distributions including binaries display the following + * acknowledgement: ``This product includes software developed by the + * University of California, Berkeley and its contributors'' in the + * documentation or other materials provided with the distribution and in + * all advertising materials mentioning features or use of this software. + * Neither the name of the University nor the names of its contributors may + * be used to endorse or promote products derived from this software without + * specific prior written permission. + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. + * + * @(#)tzfile.h 5.9 (Berkeley) 6/11/90 + */ + +/* +** Information about time zone files. +*/ + + /* Time zone object file directory */ +#define TZDIR "/usr/share/zoneinfo" +#define TZDEFAULT "/etc/localtime" +#define TZDEFRULES "posixrules" + +/* +** Each file begins with. . . +*/ + +struct tzhead { + char tzh_reserved[24]; /* reserved for future use */ + char tzh_ttisstdcnt[4]; /* coded number of trans. time flags */ + char tzh_leapcnt[4]; /* coded number of leap seconds */ + char tzh_timecnt[4]; /* coded number of transition times */ + char tzh_typecnt[4]; /* coded number of local time types */ + char tzh_charcnt[4]; /* coded number of abbr. chars */ +}; + +/* +** . . .followed by. . . +** +** tzh_timecnt (char [4])s coded transition times a la time(2) +** tzh_timecnt (unsigned char)s types of local time starting at above +** tzh_typecnt repetitions of +** one (char [4]) coded GMT offset in seconds +** one (unsigned char) used to set tm_isdst +** one (unsigned char) that's an abbreviation list index +** tzh_charcnt (char)s '\0'-terminated zone abbreviations +** tzh_leapcnt repetitions of +** one (char [4]) coded leap second transition times +** one (char [4]) total correction after above +** tzh_ttisstdcnt (char)s indexed by type; if TRUE, transition +** time is standard time, if FALSE, +** transition time is wall clock time +** if absent, transition times are +** assumed to be wall clock time +*/ + +/* +** In the current implementation, "tzset()" refuses to deal with files that +** exceed any of the limits below. +*/ + +/* +** The TZ_MAX_TIMES value below is enough to handle a bit more than a +** year's worth of solar time (corrected daily to the nearest second) or +** 138 years of Pacific Presidential Election time +** (where there are three time zone transitions every fourth year). +*/ +#define TZ_MAX_TIMES 370 + +#define NOSOLAR /* 4BSD doesn't currently handle solar time */ + +#ifndef NOSOLAR +#define TZ_MAX_TYPES 256 /* Limited by what (unsigned char)'s can hold */ +#else +#define TZ_MAX_TYPES 10 /* Maximum number of local time types */ +#endif + +#define TZ_MAX_CHARS 50 /* Maximum number of abbreviation characters */ + +#define TZ_MAX_LEAPS 50 /* Maximum number of leap second corrections */ + +#define SECSPERMIN 60 +#define MINSPERHOUR 60 +#define HOURSPERDAY 24 +#define DAYSPERWEEK 7 +#define DAYSPERNYEAR 365 +#define DAYSPERLYEAR 366 +#define SECSPERHOUR (SECSPERMIN * MINSPERHOUR) +#define SECSPERDAY ((long) SECSPERHOUR * HOURSPERDAY) +#define MONSPERYEAR 12 + +#define TM_SUNDAY 0 +#define TM_MONDAY 1 +#define TM_TUESDAY 2 +#define TM_WEDNESDAY 3 +#define TM_THURSDAY 4 +#define TM_FRIDAY 5 +#define TM_SATURDAY 6 + +#define TM_JANUARY 0 +#define TM_FEBRUARY 1 +#define TM_MARCH 2 +#define TM_APRIL 3 +#define TM_MAY 4 +#define TM_JUNE 5 +#define TM_JULY 6 +#define TM_AUGUST 7 +#define TM_SEPTEMBER 8 +#define TM_OCTOBER 9 +#define TM_NOVEMBER 10 +#define TM_DECEMBER 11 + +#define TM_YEAR_BASE 1900 + +#define EPOCH_YEAR 1970 +#define EPOCH_WDAY TM_THURSDAY + +/* +** Accurate only for the past couple of centuries; +** that will probably do. +*/ + +#define isleap(y) ((((y) % 4) == 0 && ((y) % 100) != 0) || ((y) % 400) == 0) + +#endif /* !_POSIX_SOURCE */ +#endif /* !__STRICT_ANSI__ */ +#endif /* !__dj_ENFORCE_ANSI_FREESTANDING */ + +#ifndef __dj_ENFORCE_FUNCTION_CALLS +#endif /* !__dj_ENFORCE_FUNCTION_CALLS */ + +#ifdef __cplusplus +} +#endif + +#endif /* __dj_include_tzfile_h__ */ diff --git a/reactos/lib/crtdll/wchar/wcscat.c b/reactos/lib/crtdll/wchar/wcscat.c new file mode 100644 index 00000000000..fcc36038a99 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcscat.c @@ -0,0 +1,19 @@ + + +#include + +wchar_t * wcscat(wchar_t * dest,const wchar_t * src) +{ + + int i,j; + j=0; + for (i=0; dest[i]!=0; i++); + while (src[j] != 0) + { + dest[i+j] = src[j]; + j++; + } + dest[i+j] = 0; + return dest; +} + diff --git a/reactos/lib/crtdll/wchar/wcschr.c b/reactos/lib/crtdll/wchar/wcschr.c new file mode 100644 index 00000000000..1fb1540856b --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcschr.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +wchar_t* wcschr(const wchar_t* str, wchar_t ch) +{ + while ((*str)!=0) + { + if ((*str)==ch) + { + return((wchar_t *)str); + } + str++; + } + return(NULL); +} diff --git a/reactos/lib/crtdll/wchar/wcscmp.c b/reactos/lib/crtdll/wchar/wcscmp.c new file mode 100644 index 00000000000..2fc95c9d3a3 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcscmp.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +int wcscmp(const wchar_t* cs,const wchar_t * ct) +{ + while (*cs == *ct) + { + if (*cs == 0) + return 0; + cs++; + ct++; + } + return *cs - *ct; + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcscoll.c b/reactos/lib/crtdll/wchar/wcscoll.c new file mode 100644 index 00000000000..a41fd451790 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcscoll.c @@ -0,0 +1,17 @@ +/* + * The C RunTime DLL + * + * Implements C run-time functionality as known from UNIX. + * + * Copyright 1996,1998 Marcus Meissner + * Copyright 1996 Jukka Iivonen + * Copyright 1997 Uwe Bonnes + */ + +#include + +size_t wcscoll(wchar_t *a1,wchar_t *a2) +{ + /* FIXME: handle collates */ + return wcscmp(a1,a2); +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcscpy.c b/reactos/lib/crtdll/wchar/wcscpy.c new file mode 100644 index 00000000000..d17d96b700f --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcscpy.c @@ -0,0 +1,11 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +wchar_t * wcscpy(wchar_t * str1,const wchar_t * str2) +{ + wchar_t *save = str1; + + for (; (*str1 = *str2); ++str2, ++str1); + return save; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcscspn.c b/reactos/lib/crtdll/wchar/wcscspn.c new file mode 100644 index 00000000000..d1f2ff19b32 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcscspn.c @@ -0,0 +1,20 @@ +#include + +size_t wcscspn(const wchar_t *str,const wchar_t *reject) +{ + wchar_t *s; + wchar_t *t; + s=(wchar_t *)str; + do { + t=(wchar_t *)reject; + while (*t) { + if (*t==*s) + break; + t++; + } + if (*t) + break; + s++; + } while (*s); + return s-str; /* nr of wchars */ +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcsdup.c b/reactos/lib/crtdll/wchar/wcsdup.c new file mode 100644 index 00000000000..ee21a9b49f2 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsdup.c @@ -0,0 +1,15 @@ +#include + + +wchar_t *wcsdup(const wchar_t *ptr) +{ + wchar_t *dup; + dup = malloc((wcslen(ptr) + 1)*sizeof(wchar_t)); + if( dup == NULL ) + return NULL; + wcscpy(dup,ptr); + return dup; +} + + + diff --git a/reactos/lib/crtdll/wchar/wcsicmp.c b/reactos/lib/crtdll/wchar/wcsicmp.c new file mode 100644 index 00000000000..db14731e26c --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsicmp.c @@ -0,0 +1,16 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +int wcsicmp(const wchar_t* cs,const wchar_t * ct) +{ + while (towlower(*cs) == towlower(*ct)) + { + if (*cs == 0) + return 0; + cs++; + ct++; + } + return towlower(*cs) - towlower(*ct); + +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcslen.c b/reactos/lib/crtdll/wchar/wcslen.c new file mode 100644 index 00000000000..31e81fa7806 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcslen.c @@ -0,0 +1,19 @@ +/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */ + +#include + +size_t wstrlen(const wchar_t *s) +{ + return wcslen(s); +} + + +size_t wcslen(const wchar_t * s) +{ + const wchar_t *save; + + if (s == 0) + return 0; + for (save = s; *save; ++save); + return save-s; +} diff --git a/reactos/lib/crtdll/wchar/wcslwr.c b/reactos/lib/crtdll/wchar/wcslwr.c new file mode 100644 index 00000000000..a7b3b7e3c6b --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcslwr.c @@ -0,0 +1,22 @@ +/* + * The C RunTime DLL + * + * Implements C run-time functionality as known from UNIX. + * + * Copyright 1996,1998 Marcus Meissner + * Copyright 1996 Jukka Iivonen + * Copyright 1997 Uwe Bonnes + */ + +#include + +wchar_t * wcslwr(wchar_t *x) +{ + wchar_t *y=x; + + while (*y) { + *y=towlower(*y); + y++; + } + return x; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcsncat.c b/reactos/lib/crtdll/wchar/wcsncat.c new file mode 100644 index 00000000000..c4bfc7d4843 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsncat.c @@ -0,0 +1,20 @@ +#include + +wchar_t * wcsncat(wchar_t * dest,const wchar_t * src,size_t count) +{ + int i,j; + if ( count != 0 ) { + + for (j=0;dest[j]!=0;j++); + + for (i=0;i + +int wcsncmp(const wchar_t * cs,const wchar_t * ct,size_t count) +{ + while ((*cs) == (*ct) && count > 0) + { + if (*cs == 0) + return 0; + cs++; + ct++; + count--; + } + return (*cs) - (*ct); + +} + diff --git a/reactos/lib/crtdll/wchar/wcsncpy.c b/reactos/lib/crtdll/wchar/wcsncpy.c new file mode 100644 index 00000000000..7c8a1a1e28d --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsncpy.c @@ -0,0 +1,21 @@ +#include + +wchar_t * wcsncpy(wchar_t * dest,const wchar_t *src,size_t count) +{ + int i; + + for (i=0;i + +int wcsnicmp(const wchar_t * cs,const wchar_t * ct,size_t count) +{ + wchar_t *save = cs; + while (towlower(*cs) == towlower(*ct) && (int)(cs - save) < count) + { + if (*cs == 0) + return 0; + cs++; + ct++; + } + return towlower(*cs) - towlower(*ct); + +} diff --git a/reactos/lib/crtdll/wchar/wcsnlen.c b/reactos/lib/crtdll/wchar/wcsnlen.c new file mode 100644 index 00000000000..b91b9d11e46 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsnlen.c @@ -0,0 +1,10 @@ +size_t wcsnlen(const wchar_t * s, size_t count) +{ + + unsigned int len=0; + + while(s[len]!=0 && len < count) { + len++; + }; + return len; +} diff --git a/reactos/lib/crtdll/wchar/wcsrchr.c b/reactos/lib/crtdll/wchar/wcsrchr.c new file mode 100644 index 00000000000..52a091128a5 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsrchr.c @@ -0,0 +1,14 @@ +wchar_t* wcsrchr(const wchar_t* str, wchar_t ch) +{ + + wchar_t *sp=(wchar_t *)0; + while (*str != 0) + { + if (*str == ch) + sp = (wchar_t *)str; + str++; + } + if (ch == 0) + sp = (wchar_t *)str; + return sp; +} \ No newline at end of file diff --git a/reactos/lib/crtdll/wchar/wcsrev.c b/reactos/lib/crtdll/wchar/wcsrev.c new file mode 100644 index 00000000000..78e42771513 --- /dev/null +++ b/reactos/lib/crtdll/wchar/wcsrev.c @@ -0,0 +1,16 @@ +wchar_t * wcsrev(wchar_t *s) +{ + wchar_t *e; + wchar_t a; + e=s; + while (*e) + e++; + while (s #include #include #include -#include +#include #include -#define NDEBUG -#include - -/* FUNCTIONS ****************************************************************/ - HANDLE STDCALL CreateFileA(LPCSTR lpFileName, DWORD dwDesiredAccess, DWORD dwShareMode, @@ -35,7 +30,7 @@ HANDLE STDCALL CreateFileA(LPCSTR lpFileName, WCHAR FileNameW[MAX_PATH]; ULONG i = 0; - DPRINT("CreateFileA\n"); + // OutputDebugStringA("CreateFileA\n"); while ((*lpFileName)!=0 && i < MAX_PATH) { @@ -54,6 +49,108 @@ HANDLE STDCALL CreateFileA(LPCSTR lpFileName, } +HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, + DWORD dwDesiredAccess, + DWORD dwShareMode, + LPSECURITY_ATTRIBUTES lpSecurityAttributes, + DWORD dwCreationDisposition, + DWORD dwFlagsAndAttributes, + HANDLE hTemplateFile) +{ + HANDLE FileHandle; + NTSTATUS Status; + + OBJECT_ATTRIBUTES ObjectAttributes; + IO_STATUS_BLOCK IoStatusBlock; + UNICODE_STRING FileNameString; + ULONG Flags = 0; + WCHAR PathNameW[MAX_PATH]; + WCHAR FileNameW[MAX_PATH]; + WCHAR *FilePart; + UINT Len = 0; + + if (!(dwFlagsAndAttributes & FILE_FLAG_OVERLAPPED)) + { + Flags |= FILE_SYNCHRONOUS_IO_ALERT; + } + +// dprintf("CreateFile %S\n",lpFileName); + + if ( lpFileName[0] == L'\\' || lpFileName[1] == L':') { + wcscpy(PathNameW,lpFileName); + } + else if ( ( ( dwCreationDisposition & OPEN_EXISTING ) == OPEN_EXISTING ) || ( ( dwCreationDisposition & TRUNCATE_EXISTING ) == TRUNCATE_EXISTING ) ) { + dprintf("Before SearchPath\n"); + Len = SearchPathW(NULL,lpFileName,NULL,MAX_PATH,PathNameW,&FilePart); + if ( Len == 0 ) + return NULL; + } + else { + Len = GetCurrentDirectoryW(MAX_PATH,PathNameW); + if ( Len == 0 ) + return NULL; + if ( PathNameW[Len-1] != L'\\' ) { + PathNameW[Len] = L'\\'; + PathNameW[Len+1] = 0; + } + wcscat(PathNameW,lpFileName); + } + + if ( PathNameW[1] == L':' ) { + FileNameW[0] = '\\'; + FileNameW[1] = '?'; + FileNameW[2] = '?'; + FileNameW[3] = '\\'; + FileNameW[4] = 0; + wcscat(FileNameW,PathNameW); + } + else + wcscpy(FileNameW,PathNameW); + + + + FileNameString.Length = wcslen( FileNameW)*sizeof(WCHAR); + + if ( FileNameString.Length == 0 ) + return NULL; + + if ( FileNameString.Length > MAX_PATH*sizeof(WCHAR) ) + return NULL; + + FileNameString.Buffer = (WCHAR *)FileNameW; + FileNameString.MaximumLength = FileNameString.Length + sizeof(WCHAR); + + ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); + ObjectAttributes.RootDirectory = NULL; + ObjectAttributes.ObjectName = &FileNameString; + ObjectAttributes.Attributes = OBJ_CASE_INSENSITIVE; + ObjectAttributes.SecurityDescriptor = NULL; + ObjectAttributes.SecurityQualityOfService = NULL; + +// dprintf("File Name %S\n",FileNameW); + + Status = ZwCreateFile(&FileHandle, + dwDesiredAccess, + &ObjectAttributes, + &IoStatusBlock, + NULL, + dwFlagsAndAttributes, + dwShareMode, + dwCreationDisposition, + Flags, + NULL, + 0); + + dprintf("After create file"); + if (!NT_SUCCESS(Status)) + { + SetLastError(RtlNtStatusToDosError(Status)); + return NULL; + } + return(FileHandle); +} + +#if 0 HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, DWORD dwDesiredAccess, DWORD dwShareMode, @@ -74,7 +171,7 @@ HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, UINT Len = 0; WCHAR CurrentDir[MAX_PATH]; - DPRINT("CreateFileW\n"); + OutputDebugStringA("CreateFileW\n"); if (!(dwFlagsAndAttributes & FILE_FLAG_OVERLAPPED)) { @@ -88,16 +185,16 @@ HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, PathNameW[3] = '\\'; PathNameW[4] = 0; - DPRINT("Name %w\n",PathNameW); + dprintf("Name %w\n",PathNameW); if (lpFileName[0] != L'\\' && lpFileName[1] != L':') { Len = GetCurrentDirectoryW(MAX_PATH,CurrentDir); - DPRINT("CurrentDir %w\n",CurrentDir); + dprintf("CurrentDir %w\n",CurrentDir); lstrcatW(PathNameW,CurrentDir); - DPRINT("Name %w\n",PathNameW); + dprintf("Name %w\n",PathNameW); } lstrcatW(PathNameW,lpFileName); - DPRINT("Name %w\n",PathNameW); + dprintf("Name %w\n",PathNameW); FileNameString.Length = lstrlenW( PathNameW)*sizeof(WCHAR); @@ -108,7 +205,7 @@ HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, return NULL; FileNameString.Buffer = (WCHAR *)PathNameW; - FileNameString.MaximumLength = FileNameString.Length; + FileNameString.MaximumLength = FileNameString.Length+sizeof(WCHAR); ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); ObjectAttributes.RootDirectory = NULL; @@ -131,3 +228,4 @@ HANDLE STDCALL CreateFileW(LPCWSTR lpFileName, return(FileHandle); } +#endif \ No newline at end of file diff --git a/reactos/lib/kernel32/file/curdir.c b/reactos/lib/kernel32/file/curdir.c index 7f59a1cae39..0b65d5b4d4f 100644 --- a/reactos/lib/kernel32/file/curdir.c +++ b/reactos/lib/kernel32/file/curdir.c @@ -3,6 +3,7 @@ * PROJECT: ReactOS system libraries * FILE: lib/kernel32/file/curdir.c * PURPOSE: Current directory functions + * PROGRAMMER: David Welch (welch@mcmail.com) * UPDATE HISTORY: * Created 30/09/98 */ @@ -12,17 +13,14 @@ #include -#define NDEBUG -#include - /* GLOBALS *******************************************************************/ -static unsigned short CurrentDirectoryW[MAX_PATH] = {0,}; +WCHAR CurrentDirectoryW[MAX_PATH] = {0,}; -static unsigned short SystemDirectoryW[MAX_PATH]; +WCHAR SystemDirectoryW[MAX_PATH]; -static unsigned short WindowsDirectoryW[MAX_PATH]; +WCHAR WindowsDirectoryW[MAX_PATH]; /* FUNCTIONS *****************************************************************/ @@ -48,7 +46,7 @@ DWORD STDCALL GetCurrentDirectoryW(DWORD nBufferLength, LPWSTR lpBuffer) { UINT uSize; - DPRINT("CurrentDirectoryW %w\n",CurrentDirectoryW); + dprintf("CurrentDirectoryW %w\n",CurrentDirectoryW); if ( lpBuffer == NULL ) return 0; @@ -56,7 +54,7 @@ DWORD STDCALL GetCurrentDirectoryW(DWORD nBufferLength, LPWSTR lpBuffer) if ( nBufferLength > uSize ) lstrcpynW(lpBuffer,CurrentDirectoryW,uSize); - DPRINT("GetCurrentDirectoryW() = %w\n",lpBuffer); + dprintf("GetCurrentDirectoryW() = %w\n",lpBuffer); return uSize; } @@ -65,7 +63,7 @@ BOOL STDCALL SetCurrentDirectoryA(LPCSTR lpPathName) { UINT i; - DPRINT("SetCurrentDirectoryA(lpPathName %s)\n",lpPathName); + dprintf("SetCurrentDirectoryA(lpPathName %s)\n",lpPathName); if ( lpPathName == NULL ) return FALSE; @@ -79,13 +77,17 @@ BOOL STDCALL SetCurrentDirectoryA(LPCSTR lpPathName) } CurrentDirectoryW[i] = 0; - DPRINT("CurrentDirectoryW = '%w'\n",CurrentDirectoryW); + dprintf("CurrentDirectoryW = '%w'\n",CurrentDirectoryW); return(TRUE); } -WINBOOL STDCALL SetCurrentDirectoryW(LPCWSTR lpPathName) +WINBOOL +STDCALL +SetCurrentDirectoryW( + LPCWSTR lpPathName + ) { if ( lpPathName == NULL ) return FALSE; diff --git a/reactos/lib/kernel32/file/dir.c b/reactos/lib/kernel32/file/dir.c index 65c489462c4..ecd506d78ba 100644 --- a/reactos/lib/kernel32/file/dir.c +++ b/reactos/lib/kernel32/file/dir.c @@ -37,16 +37,13 @@ CreateDirectoryExA( WCHAR NewDirectoryW[MAX_PATH]; ULONG i; i = 0; - if(lpTemplateDirectory) - { - while ((*lpTemplateDirectory)!=0 && i < MAX_PATH) + while ((*lpTemplateDirectory)!=0 && i < MAX_PATH) { TemplateDirectoryW[i] = *lpTemplateDirectory; lpTemplateDirectory++; i++; } - TemplateDirectoryW[i] = 0; - } + TemplateDirectoryW[i] = 0; i = 0; while ((*lpNewDirectory)!=0 && i < MAX_PATH) @@ -83,28 +80,15 @@ CreateDirectoryExW( HANDLE DirectoryHandle; OBJECT_ATTRIBUTES ObjectAttributes; UNICODE_STRING DirectoryNameString; - WCHAR PathNameW[MAX_PATH],CurrentDir[MAX_PATH]; if ( lpTemplateDirectory != NULL ) { // get object attributes from template directory } - PathNameW[0] = '\\'; - PathNameW[1] = '?'; - PathNameW[2] = '?'; - PathNameW[3] = '\\'; - PathNameW[4] = 0; - - if (lpNewDirectory[0] != L'\\' && lpNewDirectory[1] != L':') - { - GetCurrentDirectoryW(MAX_PATH,CurrentDir); - lstrcatW(PathNameW,CurrentDir); - } - lstrcatW(PathNameW,lpNewDirectory); - DirectoryNameString.Length = lstrlenW(PathNameW)*sizeof(WCHAR); - DirectoryNameString.Buffer = (WCHAR *)PathNameW; - DirectoryNameString.MaximumLength = DirectoryNameString.Length; + DirectoryNameString.Length = lstrlenW(lpNewDirectory)*sizeof(WCHAR); + DirectoryNameString.Buffer = (WCHAR *)lpNewDirectory; + DirectoryNameString.MaximumLength = DirectoryNameString.Length+sizeof(WCHAR); ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); ObjectAttributes.RootDirectory = NULL; @@ -114,17 +98,11 @@ CreateDirectoryExW( ObjectAttributes.SecurityQualityOfService = NULL; - errCode = NtCreateFile(&DirectoryHandle, - FILE_LIST_DIRECTORY, - &ObjectAttributes, - NULL, - NULL, - FILE_ATTRIBUTE_NORMAL, - 0, - FILE_CREATE, - FILE_DIRECTORY_FILE, - NULL, - 0); + errCode = NtCreateDirectoryObject( + &DirectoryHandle, + GENERIC_ALL, + &ObjectAttributes + ); if (!NT_SUCCESS(errCode) ) { SetLastError(RtlNtStatusToDosError(errCode)); return FALSE; @@ -166,7 +144,7 @@ RemoveDirectoryW( PathNameString.Length = lstrlenW(lpPathName)*sizeof(WCHAR); PathNameString.Buffer = (WCHAR *)lpPathName; - PathNameString.MaximumLength = PathNameString.Length; + PathNameString.MaximumLength = PathNameString.Length+sizeof(WCHAR); ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); ObjectAttributes.RootDirectory = NULL; @@ -197,6 +175,7 @@ GetFullPathNameA( } +#define IS_END_OF_NAME(ch) (!(ch) || ((ch) == L'/') || ((ch) == L'\\')) DWORD @@ -208,8 +187,81 @@ GetFullPathNameW( LPWSTR *lpFilePart ) { + + WCHAR buffer[MAX_PATH]; + WCHAR *p; + + if (!lpFileName || !lpBuffer) return 0; + + p = buffer; + + if (IS_END_OF_NAME(*lpFileName) && (*lpFileName)) /* Absolute path */ + { + while (*lpFileName == L'\\') + lpFileName++; + } + else /* Relative path or empty path */ + { + if ( GetCurrentDirectoryW(MAX_PATH,p) == 0 ) + wcscpy( p, L"C:"); + if (*p) + p += wcslen(p); + } + if (!*lpFileName) /* empty path */ + *p++ = '\\'; + *p = '\0'; + + while (*lpFileName) + { + if (*lpFileName == '.') + { + if (IS_END_OF_NAME(lpFileName[1])) + { + lpFileName++; + while (*lpFileName == L'\\' ) lpFileName++; + continue; + } + else if ((lpFileName[1] == L'.') && IS_END_OF_NAME(lpFileName[2])) + { + lpFileName += 2; + while ((*lpFileName == '\\') ) lpFileName++; + while ((p > buffer + 2) && (*p != '\\')) p--; + *p = '\0'; /* Remove trailing separator */ + continue; + } + } + if (p >= buffer + sizeof(buffer) - 1) + { + //DOS_ERROR( ER_PathNotFound, EC_NotFound, SA_Abort, EL_Disk); + return 0; + } + *p++ = '\\'; + while (!IS_END_OF_NAME(*lpFileName) && (p < buffer + sizeof(buffer) -1)) + *p++ = *lpFileName++; + *p = '\0'; + while ((*lpFileName == '\\') ) lpFileName++; + } + + if (!buffer[2]) + { + buffer[2] = '\\'; + buffer[3] = '\0'; + } + + + wcsncpy( lpBuffer, buffer, nBufferLength); + + //TRACE(dosfs, "returning %s\n", buffer ); + return wcslen(buffer); } + + + + + + + DWORD STDCALL GetShortPathNameA( @@ -253,6 +305,49 @@ SearchPathA( LPSTR *lpFilePart ) { + WCHAR PathW[MAX_PATH]; + WCHAR FileNameW[MAX_PATH]; + WCHAR ExtensionW[MAX_PATH]; + + WCHAR BufferW[MAX_PATH]; + WCHAR *FilePartW; + + ULONG i; + DWORD RetValue; + + i = 0; + while ((*lpPath)!=0 && i < MAX_PATH) + { + PathW[i] = *lpPath; + lpPath++; + i++; + } + PathW[i] = 0; + + i = 0; + while ((*lpFileName)!=0 && i < MAX_PATH) + { + FileNameW[i] = *lpFileName; + lpFileName++; + i++; + } + FileNameW[i] = 0; + + i = 0; + while ((*lpExtension)!=0 && i < MAX_PATH) + { + ExtensionW[i] = *lpExtension; + lpExtension++; + i++; + } + ExtensionW[i] = 0; + + RetValue = SearchPathW(PathW,FileNameW,ExtensionW,nBufferLength,BufferW,&FilePartW); + for(i=0;i 0 ) { @@ -350,40 +439,38 @@ SearchPathW( if ( lpExtension != NULL ) { if ( lpFileName[i-4] != L'.' ) { - memcpy(FileAndExtensionW,lpFileName,(i+1)*sizeof(WCHAR)); - lstrcatW(FileAndExtensionW,lpExtension); + wcscpy(FileAndExtensionW,lpFileName); + wcscat(FileAndExtensionW,lpExtension); } else - memcpy(FileAndExtensionW,lpFileName,(i+1)*sizeof(WCHAR)); + wcscpy(FileAndExtensionW,lpFileName); } else - memcpy(FileAndExtensionW,lpFileName,(i+1)*sizeof(WCHAR)); + wcscpy(FileAndExtensionW,lpFileName); - if ( lpPath[0] == L'\\' ) - lstrcatW(lpBuffer,lpPath); - else { - lstrcatW(lpBuffer,L"\\??\\"); - lstrcatW(lpBuffer,lpPath); - } + + lstrcatW(BufferW,L"\\??\\"); + lstrcatW(BufferW,lpPath); + //printf("%S\n",FileAndExtensionW); - i = lstrlenW(lpBuffer); - if ( lpBuffer[i-1] != L'\\' ) { - lpBuffer[i] = L'\\'; - lpBuffer[i+1] = 0; + i = wcslen(BufferW); + if ( BufferW[i-1] != L'\\' ) { + BufferW[i] = L'\\'; + BufferW[i+1] = 0; } if ( lpFilePart != NULL ) - *lpFilePart = &lpBuffer[lstrlenW(lpBuffer)+1]; - lstrcatW(lpBuffer,FileAndExtensionW); + *lpFilePart = &BufferW[wcslen(BufferW)+1]; + wcscat(BufferW,FileAndExtensionW); //printf("%S\n",lpBuffer); - PathString.Buffer = lpBuffer; + PathString.Buffer = BufferW; PathString.Length = lstrlenW(PathString.Buffer)*sizeof(WCHAR); - PathString.MaximumLength = PathString.Length; + PathString.MaximumLength = PathString.Length + sizeof(WCHAR); @@ -409,10 +496,15 @@ SearchPathW( if ( !NT_SUCCESS(errCode) ) { return 0; } - + else { + NtClose(FileHandle); + wcscpy(lpBuffer,&BufferW[4]); + lpFilePart = wcsrchr(lpBuffer,'\\')+1; + } } return lstrlenW(lpBuffer); } + diff --git a/reactos/lib/kernel32/file/file.c b/reactos/lib/kernel32/file/file.c index 52941dc9d9a..b9b814e1fd2 100644 --- a/reactos/lib/kernel32/file/file.c +++ b/reactos/lib/kernel32/file/file.c @@ -16,7 +16,7 @@ #include #include #include -#include +#include #include #define LPPROGRESS_ROUTINE void* @@ -88,31 +88,26 @@ WINBOOL STDCALL WriteFile(HANDLE hFile, LPOVERLAPPED lpOverLapped) { - PLARGE_INTEGER Offset; - LARGE_INTEGER ByteOffset; + LARGE_INTEGER Offset; HANDLE hEvent = NULL; NTSTATUS errCode; - PIO_STATUS_BLOCK IoStatusBlock; - IO_STATUS_BLOCK IIosb; - if ( lpOverLapped != NULL ) + + WCHAR Buffer[1000]; + + //printk("%.*s",nNumberOfBytesToWrite,lpBuffer); + + if (lpOverLapped != NULL ) { - SET_LARGE_INTEGER_LOW_PART(ByteOffset, lpOverLapped->Offset); - SET_LARGE_INTEGER_HIGH_PART(ByteOffset, lpOverLapped->OffsetHigh); - Offset = &ByteOffset; + SET_LARGE_INTEGER_LOW_PART(Offset, lpOverLapped->Offset); + SET_LARGE_INTEGER_HIGH_PART(Offset, lpOverLapped->OffsetHigh); lpOverLapped->Internal = STATUS_PENDING; - hEvent = lpOverLapped->hEvent; - IoStatusBlock = (PIO_STATUS_BLOCK)lpOverLapped; - } - else - { - IoStatusBlock = &IIosb; - Offset = NULL; + hEvent= lpOverLapped->hEvent; } errCode = NtWriteFile(hFile,hEvent,NULL,NULL, (PIO_STATUS_BLOCK)lpOverLapped, (PVOID)lpBuffer, nNumberOfBytesToWrite, - Offset, + &Offset, NULL); if (!NT_SUCCESS(errCode)) { @@ -137,7 +132,7 @@ WINBOOL STDCALL ReadFile(HANDLE hFile, PIO_STATUS_BLOCK IoStatusBlock; IO_STATUS_BLOCK IIosb; - + if ( lpOverLapped != NULL ) { SET_LARGE_INTEGER_LOW_PART(ByteOffset, lpOverLapped->Offset); @@ -167,6 +162,8 @@ WINBOOL STDCALL ReadFile(HANDLE hFile, SetLastError(RtlNtStatusToDosError(errCode)); return FALSE; } + + return TRUE; } @@ -675,7 +672,7 @@ OpenFile( FileNameString.Length = lstrlenW(PathNameW)*sizeof(WCHAR); FileNameString.Buffer = PathNameW; - FileNameString.MaximumLength = FileNameString.Length; + FileNameString.MaximumLength = FileNameString.Length+sizeof(WCHAR); @@ -857,27 +854,30 @@ DeleteFileW( NTSTATUS errCode; WCHAR PathNameW[MAX_PATH]; UINT Len; - - Len = GetCurrentDirectoryW(MAX_PATH,PathNameW); - if ( Len == 0 ) - return FALSE; - if ( PathNameW[Len-1] != L'\\' ) { - PathNameW[Len] = L'\\'; - PathNameW[Len+1] = 0; + if ( lpFileName[1] != ':' ) { + Len = GetCurrentDirectoryW(MAX_PATH,PathNameW); + if ( Len == 0 ) + return FALSE; + if ( PathNameW[Len-1] != L'\\' ) { + PathNameW[Len] = L'\\'; + PathNameW[Len+1] = 0; + } } + else + PathNameW[0] = 0; lstrcatW(PathNameW,lpFileName); FileNameString.Length = lstrlenW( PathNameW)*sizeof(WCHAR); if ( FileNameString.Length == 0 ) return FALSE; - if ( FileNameString.Length > MAX_PATH ) + if ( FileNameString.Length > MAX_PATH*sizeof(WCHAR) ) return FALSE; FileNameString.Buffer = (WCHAR *)PathNameW; - FileNameString.MaximumLength = FileNameString.Length; + FileNameString.MaximumLength = FileNameString.Length+sizeof(WCHAR); @@ -1200,6 +1200,69 @@ GetFileAttributesW( } +WINBOOL +STDCALL +SetFileAttributesA( + LPCSTR lpFileName, + DWORD dwFileAttributes + ) +{ + ULONG i; + WCHAR FileNameW[MAX_PATH]; + i = 0; + while ((*lpFileName)!=0 && i < MAX_PATH) + { + FileNameW[i] = *lpFileName; + lpFileName++; + i++; + } + FileNameW[i] = 0; + return SetFileAttributesW(FileNameW, dwFileAttributes); +} + + +WINBOOL +STDCALL +SetFileAttributesW( + LPCWSTR lpFileName, + DWORD dwFileAttributes + ) +{ + IO_STATUS_BLOCK IoStatusBlock; + FILE_BASIC_INFORMATION FileBasic; + HANDLE hFile; + NTSTATUS errCode; + + + hFile = CreateFileW( + lpFileName, + GENERIC_READ, + FILE_SHARE_READ, + NULL, + OPEN_EXISTING, + FILE_ATTRIBUTE_NORMAL, + NULL + ); + + + errCode = NtQueryInformationFile(hFile,&IoStatusBlock,&FileBasic, sizeof(FILE_BASIC_INFORMATION),FileBasicInformation); + if ( !NT_SUCCESS(errCode) ) { + CloseHandle(hFile); + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + FileBasic.FileAttributes = dwFileAttributes; + errCode = NtSetInformationFile(hFile,&IoStatusBlock,&FileBasic, sizeof(FILE_BASIC_INFORMATION),FileBasicInformation); + if ( !NT_SUCCESS(errCode) ) { + CloseHandle(hFile); + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + CloseHandle(hFile); + return TRUE; + +} + DWORD @@ -1207,9 +1270,10 @@ GetCurrentTime(VOID) { NTSTATUS errCode; FILETIME CurrentTime; - errCode = NtQuerySystemTime ( - (TIME *)&CurrentTime - ); +memset(&CurrentTime,sizeof(FILETIME),0); +// errCode = NtQuerySystemTime ( +// (TIME *)&CurrentTime +// ); return CurrentTime.dwLowDateTime; } @@ -1230,10 +1294,10 @@ GetTempFileNameA( if (uUnique == 0) uUnique = GetCurrentTime(); - - wsprintfA(lpTempFileName,"%s\\%c%.3s%4.4x%s", + /* + sprintf(lpTempFileName,"%s\\%c%.3s%4.4x%s", lpPathName,'~',lpPrefixString,uUnique,".tmp"); - + */ if (unique) return uUnique; @@ -1241,8 +1305,8 @@ GetTempFileNameA( CREATE_NEW, FILE_ATTRIBUTE_TEMPORARY, 0)) == INVALID_HANDLE_VALUE) { - wsprintfA(lpTempFileName,"%s\\%c%.3s%4.4x%s", - lpPathName,'~',lpPrefixString,++uUnique,".tmp"); + // wsprintfA(lpTempFileName,"%s\\%c%.3s%4.4x%s", +// lpPathName,'~',lpPrefixString,++uUnique,".tmp"); } CloseHandle((HANDLE)hFile); @@ -1268,8 +1332,8 @@ GetTempFileNameW( if (uUnique == 0) uUnique = GetCurrentTime(); - wsprintfW(lpTempFileName,L"%s\\%c%.3s%4.4x%s", - lpPathName,'~',lpPrefixString,uUnique,L".tmp"); + // swprintf(lpTempFileName,L"%s\\%c%.3s%4.4x%s", +// lpPathName,'~',lpPrefixString,uUnique,L".tmp"); if (unique) return uUnique; @@ -1278,8 +1342,8 @@ GetTempFileNameW( CREATE_NEW, FILE_ATTRIBUTE_TEMPORARY, 0)) == INVALID_HANDLE_VALUE) { - wsprintfW(lpTempFileName,L"%s\\%c%.3s%4.4x%s", - lpPathName,'~',lpPrefixString,++uUnique,L".tmp"); +// wsprintfW(lpTempFileName,L"%s\\%c%.3s%4.4x%s", +// lpPathName,'~',lpPrefixString,++uUnique,L".tmp"); } CloseHandle((HANDLE)hFile); @@ -1341,3 +1405,14 @@ SetFileTime( return TRUE; } + +WINBOOL +STDCALL +SetEndOfFile( + HANDLE hFile + ) +{ + int x = -1; + DWORD Num; + return WriteFile(hFile,&x,1,&Num,NULL); +} diff --git a/reactos/lib/kernel32/file/find.c b/reactos/lib/kernel32/file/find.c index 026f0d3a41e..cd3a78b3dd4 100644 --- a/reactos/lib/kernel32/file/find.c +++ b/reactos/lib/kernel32/file/find.c @@ -1,258 +1,463 @@ -/* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS system libraries - * FILE: lib/kernel32/file/find.c - * PURPOSE: Find functions - * PROGRAMMER: Ariadne ( ariadne@xs4all.nl) - * UPDATE HISTORY: - * Created 01/11/98 - */ - -/* INCLUDES *****************************************************************/ - -#include -#include -#include - -#define NDEBUG -#include - -/* TYPES ********************************************************************/ - -typedef struct _KERNEL32_FIND_FILE_DATA -{ - HANDLE DirectoryHandle; - FILE_DIRECTORY_INFORMATION FileInfo; - WCHAR FileNameExtra[MAX_PATH]; - UNICODE_STRING PatternStr; -} KERNEL32_FIND_FILE_DATA, *PKERNEL32_FIND_FILE_DATA; - -typedef struct _WIN32_FIND_DATA_UNICODE { - DWORD dwFileAttributes; - FILETIME ftCreationTime; - FILETIME ftLastAccessTime; - FILETIME ftLastWriteTime; - DWORD nFileSizeHigh; - DWORD nFileSizeLow; - DWORD dwReserved0; - DWORD dwReserved1; - WCHAR cFileName[ MAX_PATH ]; - WCHAR cAlternateFileName[ 14 ]; -} WIN32_FIND_DATA_UNICODE, *PWIN32_FIND_DATA_UNICODE; - -typedef struct _WIN32_FIND_DATA_ASCII { - DWORD dwFileAttributes; - FILETIME ftCreationTime; - FILETIME ftLastAccessTime; - FILETIME ftLastWriteTime; - DWORD nFileSizeHigh; - DWORD nFileSizeLow; - DWORD dwReserved0; - DWORD dwReserved1; - CHAR cFileName[ MAX_PATH ]; - CHAR cAlternateFileName[ 14 ]; -} WIN32_FIND_DATA_ASCII, *PWIN32_FIND_DATA_ASCII; - - -/* FUNCTIONS *****************************************************************/ - -WINBOOL STDCALL InternalFindNextFile(HANDLE hFindFile, - LPWIN32_FIND_DATA lpFindFileData) -{ - IO_STATUS_BLOCK IoStatusBlock; - NTSTATUS Status; - PKERNEL32_FIND_FILE_DATA IData; - - IData = (PKERNEL32_FIND_FILE_DATA)hFindFile; - - Status = NtQueryDirectoryFile(IData->DirectoryHandle, - NULL, - NULL, - NULL, - &IoStatusBlock, - (PVOID)&IData->FileInfo, - sizeof(IData->FileInfo) + - sizeof(IData->FileNameExtra), - FileDirectoryInformation, - TRUE, - &(IData->PatternStr), - FALSE); - DPRINT("Found %w\n",IData->FileInfo.FileName); - lpFindFileData->dwFileAttributes = IData->FileInfo.FileAttributes; - if (Status != STATUS_SUCCESS) - { - return(FALSE); - } - return(TRUE); -} - -HANDLE STDCALL InternalFindFirstFile(LPCWSTR lpFileName, - LPWIN32_FIND_DATA lpFindFileData) -{ - WCHAR CurrentDirectory[MAX_PATH]; - WCHAR Pattern[MAX_PATH]; - WCHAR Directory[MAX_PATH]; - PWSTR End; - PKERNEL32_FIND_FILE_DATA IData; - OBJECT_ATTRIBUTES ObjectAttributes; - UNICODE_STRING DirectoryNameStr; - IO_STATUS_BLOCK IoStatusBlock; - - DPRINT("FindFirstFileW(lpFileName %w, lpFindFileData %x)\n", - lpFileName, lpFindFileData); - - GetCurrentDirectoryW(MAX_PATH, CurrentDirectory); - Directory[0] = '\\'; - Directory[1] = '?'; - Directory[2] = '?'; - Directory[3] = '\\'; - Directory[4] = 0; - DPRINT("Directory %w\n",Directory); - wcscat(Directory, CurrentDirectory); - DPRINT("Directory %w\n",Directory); - wcscat(Directory, lpFileName); - DPRINT("Directory %w\n",Directory); - End = wcsrchr(Directory, '\\'); - *End = 0; - - wcscpy(Pattern, End+1); - - DPRINT("Directory %w Pattern %w\n",Directory,Pattern); - - IData = HeapAlloc(GetProcessHeap(), - HEAP_ZERO_MEMORY, - sizeof(KERNEL32_FIND_FILE_DATA)); - - RtlInitUnicodeString(&DirectoryNameStr, Directory); - InitializeObjectAttributes(&ObjectAttributes, - &DirectoryNameStr, - 0, - NULL, - NULL); - - if (ZwOpenFile(&IData->DirectoryHandle, - FILE_LIST_DIRECTORY, - &ObjectAttributes, - &IoStatusBlock, - 0, - OPEN_EXISTING)!=STATUS_SUCCESS) - { - return(NULL); - } - - RtlInitUnicodeString(&(IData->PatternStr), Pattern); - - NtQueryDirectoryFile(IData->DirectoryHandle, - NULL, - NULL, - NULL, - &IoStatusBlock, - (PVOID)&IData->FileInfo, - sizeof(IData->FileInfo) + - sizeof(IData->FileNameExtra), - FileDirectoryInformation, - TRUE, - &(IData->PatternStr), - FALSE); - DPRINT("Found %w\n",IData->FileInfo.FileName); - - lpFindFileData->dwFileAttributes = IData->FileInfo.FileAttributes; - return(IData); -} - -HANDLE FindFirstFileA(LPCTSTR lpFileName, LPWIN32_FIND_DATA lpFindFileData) -{ - WCHAR lpFileNameW[MAX_PATH]; - ULONG i; - PKERNEL32_FIND_FILE_DATA IData; - PWIN32_FIND_DATA_ASCII Ret; - - i = 0; - while (lpFileName[i]!=0) - { - lpFileNameW[i] = lpFileName[i]; - i++; - } - lpFileNameW[i] = 0; - - IData = InternalFindFirstFile(lpFileNameW,lpFindFileData); - Ret = (PWIN32_FIND_DATA_ASCII)lpFindFileData; - - for (i=0; iFileInfo.FileNameLength; i++) - { - Ret->cFileName[i] = IData->FileInfo.FileName[i]; - } - Ret->cFileName[i] = 0; - - return(IData); -} - -WINBOOL FindNextFileA(HANDLE hFindFile, LPWIN32_FIND_DATA lpFindFileData) -{ - PWIN32_FIND_DATA_ASCII Ret; - PKERNEL32_FIND_FILE_DATA IData; - ULONG i; - - IData = (PKERNEL32_FIND_FILE_DATA)hFindFile; - if (!InternalFindNextFile(hFindFile, lpFindFileData)) - { - return(FALSE); - } - - Ret = (PWIN32_FIND_DATA_ASCII)lpFindFileData; - - for (i=0; iFileInfo.FileNameLength; i++) - { - Ret->cFileName[i] = IData->FileInfo.FileName[i]; - } - Ret->cFileName[i] = 0; - - return(TRUE); -} - -BOOL FindClose(HANDLE hFindFile) -{ - PKERNEL32_FIND_FILE_DATA IData; - - IData = (PKERNEL32_FIND_FILE_DATA)hFindFile; - NtClose(IData->DirectoryHandle); - HeapFree(GetProcessHeap(), 0, IData); - return(TRUE); -} - -HANDLE STDCALL FindFirstFileW(LPCWSTR lpFileName, - LPWIN32_FIND_DATA lpFindFileData) -{ - PWIN32_FIND_DATA_UNICODE Ret; - PKERNEL32_FIND_FILE_DATA IData; - - IData = InternalFindFirstFile(lpFileName,lpFindFileData); - Ret = (PWIN32_FIND_DATA_UNICODE)lpFindFileData; - - memcpy(Ret->cFileName, IData->FileInfo.FileName, - IData->FileInfo.FileNameLength); - memset(Ret->cAlternateFileName, 0, 14); - - return(IData); -} - -WINBOOL STDCALL FindNextFileW(HANDLE hFindFile, - LPWIN32_FIND_DATA lpFindFileData) -{ - PWIN32_FIND_DATA_UNICODE Ret; - PKERNEL32_FIND_FILE_DATA IData; - - IData = (PKERNEL32_FIND_FILE_DATA)hFindFile; - if (!InternalFindNextFile(hFindFile, lpFindFileData)) - { - return(FALSE); - } - - Ret = (PWIN32_FIND_DATA_UNICODE)lpFindFileData; - - memcpy(Ret->cFileName, IData->FileInfo.FileName, - IData->FileInfo.FileNameLength); - memset(Ret->cAlternateFileName, 0, 14); - - return(TRUE); -} +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/kernel32/file/find.c + * PURPOSE: Find functions + * PROGRAMMER: Ariadne ( ariadne@xs4all.nl) + * UPDATE HISTORY: + * Created 01/11/98 + */ +#include +#include +#include +#include + + + + + + + + +typedef struct _FIND_FILE_INFO +{ + ULONG Offset; + WCHAR PathName[MAX_PATH]; + WCHAR FileName[MAX_PATH]; + FILE_DIRECTORY_INFORMATION *FileDirectory; +} FIND_FILE_INFO; + +typedef struct _NOTIFY_INFO +{ + HANDLE Event; + HANDLE FileHandle; + DWORD dwNotifyFilter; + WINBOOL bWatchSubtree; +} NOTIFY_INFO; + + + + +typedef struct _WIN32_FIND_DATAW { + DWORD dwFileAttributes; + FILETIME ftCreationTime; + FILETIME ftLastAccessTime; + FILETIME ftLastWriteTime; + DWORD nFileSizeHigh; + DWORD nFileSizeLow; + DWORD dwReserved0; + DWORD dwReserved1; + WCHAR cFileName[ MAX_PATH ]; + WCHAR cAlternateFileName[ 14 ]; +} WIN32_FIND_DATAW, *LPWIN32_FIND_DATAW, *PWIN32_FIND_DATAW; + + +WINBOOL +STDCALL +FindClose( + HANDLE hFind + ) +{ + + if ( hFind == NULL) + return FALSE; + if ( hFind == (HANDLE)-1) + return FALSE; + + HeapFree(GetProcessHeap(),0,((FIND_FILE_INFO *)hFind)->FileDirectory); + HeapFree(GetProcessHeap(),0,hFind); + return TRUE; +} + + + +HANDLE +STDCALL +FindFirstFileA( + LPCSTR lpFileName, + LPWIN32_FIND_DATA lpFindFileData + ) +{ + WIN32_FIND_DATAW FindFileDataW; + WCHAR FileNameW[MAX_PATH]; + ULONG i; + HANDLE hFind; + + i = 0; + while ((*lpFileName)!=0 && i < MAX_PATH) + { + FileNameW[i] = *lpFileName; + lpFileName++; + i++; + } + FileNameW[i] = 0; + hFind = FindFirstFileW(FileNameW,(WIN32_FIND_DATA *)&FindFileDataW); + + lpFindFileData->dwFileAttributes = FindFileDataW.dwFileAttributes; + memcpy(&lpFindFileData->ftCreationTime,&FindFileDataW.ftCreationTime,sizeof(FILETIME)); + memcpy(&lpFindFileData->ftLastAccessTime,&FindFileDataW.ftLastAccessTime,sizeof(FILETIME)); + memcpy(&lpFindFileData->ftLastWriteTime,&FindFileDataW.ftLastWriteTime,sizeof(FILETIME)); + lpFindFileData->nFileSizeHigh = FindFileDataW.nFileSizeHigh; + lpFindFileData->nFileSizeLow = FindFileDataW.nFileSizeLow; + lpFindFileData->dwReserved0= FindFileDataW.dwReserved0; + lpFindFileData->dwReserved1= FindFileDataW.dwReserved1; + i = 0; + while ((lpFindFileData->cFileName[i])!=0 && i < MAX_PATH) + { + lpFindFileData->cFileName[i] = (char)FindFileDataW.cFileName[i]; + i++; + } + lpFindFileData->cFileName[i] = 0; + + i = 0; + while ((lpFindFileData->cAlternateFileName[i])!=0 && i < 14) + { + lpFindFileData->cAlternateFileName[i] = (char)FindFileDataW.cAlternateFileName[i]; + i++; + } + lpFindFileData->cAlternateFileName[i] = 0; + + + return hFind; +} + +HANDLE +STDCALL +FindFirstFileW( + LPCWSTR lpFileName, + LPWIN32_FIND_DATA lpFindFileData + ) +{ + NTSTATUS errCode; + IO_STATUS_BLOCK IoStatusBlock; + HANDLE FileHandle = NULL; + FIND_FILE_INFO *hFind; + WCHAR *FilePart; + UNICODE_STRING FileNameString, PathNameString; + OBJECT_ATTRIBUTES ObjectAttributes; + + + ACCESS_MASK DesiredAccess=FILE_READ_DATA; + + ULONG FileAttributes=FILE_ATTRIBUTE_DIRECTORY; + ULONG ShareAccess=FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE; + ULONG CreateDisposition=FILE_OPEN; + ULONG CreateOptions=FILE_DIRECTORY_FILE; + + + hFind = HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,sizeof(FIND_FILE_INFO)); + + hFind->FileDirectory = HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,8192); + + + + /* Try to find a path and a filename in the passed filename */ + + lstrcpyW(hFind->PathName, lpFileName); + FilePart = wcsrchr(hFind->PathName, '\\'); + + if (FilePart == NULL){ + GetCurrentDirectoryW(MAX_PATH, hFind->PathName); + lstrcpyW(hFind->FileName, lpFileName); + } + else { + lstrcpyW(hFind->FileName, &FilePart[1]); + } + + hFind->Offset = 0; + + + PathNameString.Length = lstrlenW(hFind->PathName)*sizeof(WCHAR); + PathNameString.Buffer = hFind->PathName; + PathNameString.MaximumLength = FileNameString.Length+sizeof(WCHAR); + + + FileNameString.Length = lstrlenW(hFind->FileName)*sizeof(WCHAR); + FileNameString.Buffer = hFind->FileName; + FileNameString.MaximumLength = FileNameString.Length+sizeof(WCHAR); + + + ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); + ObjectAttributes.RootDirectory = NULL; + ObjectAttributes.ObjectName = &PathNameString; + ObjectAttributes.Attributes = OBJ_CASE_INSENSITIVE| OBJ_INHERIT; + ObjectAttributes.SecurityDescriptor = NULL; + ObjectAttributes.SecurityQualityOfService = NULL; + + + + + + + errCode = NtCreateFile( + &FileHandle, + DesiredAccess, + &ObjectAttributes, + &IoStatusBlock, + NULL, + FileAttributes, + ShareAccess, + CreateDisposition, + CreateOptions, + NULL, + 0); // + + if ( !NT_SUCCESS(errCode) ) { + + return NULL; + } + + errCode = NtQueryDirectoryFile( + FileHandle, + NULL, + NULL, + NULL, + &IoStatusBlock, + hFind->FileDirectory, + 8192, + FileDirectoryInformation, + FALSE, + &FileNameString, + FALSE + ); + if ( !NT_SUCCESS(errCode) ) { + // printf("%x\n",errCode); + return NULL; + } + + + + + if ( FindNextFileW(hFind,lpFindFileData) ) + return hFind; + else { + FindClose(hFind); + return NULL; + } + return NULL; +} + +WINBOOL +STDCALL +FindNextFileA( + HANDLE hFind, + LPWIN32_FIND_DATA lpFindFileData + ) +{ + WIN32_FIND_DATAW FindFileDataW; + ULONG i; + + + hFind = FindNextFileW(hFind,(WIN32_FIND_DATA *)&FindFileDataW); + + lpFindFileData->dwFileAttributes = FindFileDataW.dwFileAttributes; + memcpy(&lpFindFileData->ftCreationTime,&FindFileDataW.ftCreationTime,sizeof(FILETIME)); + memcpy(&lpFindFileData->ftLastAccessTime,&FindFileDataW.ftLastAccessTime,sizeof(FILETIME)); + memcpy(&lpFindFileData->ftLastWriteTime,&FindFileDataW.ftLastWriteTime,sizeof(FILETIME)); + lpFindFileData->nFileSizeHigh = FindFileDataW.nFileSizeHigh; + lpFindFileData->nFileSizeLow = FindFileDataW.nFileSizeLow; + lpFindFileData->dwReserved0= FindFileDataW.dwReserved0; + lpFindFileData->dwReserved1= FindFileDataW.dwReserved1; + i = 0; + while ((lpFindFileData->cFileName[i])!=0 && i < MAX_PATH) + { + lpFindFileData->cFileName[i] = (char)FindFileDataW.cFileName[i]; + i++; + } + lpFindFileData->cFileName[i] = 0; + + i = 0; + while ((lpFindFileData->cAlternateFileName[i])!=0 && i < 14) + { + lpFindFileData->cAlternateFileName[i] = (char)FindFileDataW.cAlternateFileName[i]; + i++; + } + lpFindFileData->cAlternateFileName[i] = 0; + + + return hFind; +} + +WINBOOL +STDCALL +FindNextFileW( + HANDLE hFind, + LPWIN32_FIND_DATA lpFindFileData + ) +{ + + + LPWIN32_FIND_DATAW lpFindFileDataW = (LPWIN32_FIND_DATAW)lpFindFileData; + + FIND_FILE_INFO *FindPtr = hFind; + FILE_DIRECTORY_INFORMATION *FileDirectory=NULL; + + if ( FindPtr == NULL ) + return FALSE; + if ( FileDirectory->NextEntryOffset == 0 ) + return FALSE; + + /* Try to find a file */ + FileDirectory = FindPtr->Offset + FindPtr->FileDirectory; + + + + + FindPtr->Offset += FileDirectory->NextEntryOffset; + + /* We found one! */ + if (FindPtr->PathName[0] != L'\0') + { + wcscpy(lpFindFileDataW->cFileName, FindPtr->PathName); + wcscat(lpFindFileDataW->cFileName, L"\\"); + wcscat(lpFindFileDataW->cFileName, FileDirectory->FileName); + } + else + wcscpy(lpFindFileDataW->cFileName, FileDirectory->FileName); + + + + wcscpy(lpFindFileDataW->cAlternateFileName, L""); + lpFindFileData->dwReserved0 = 0; + lpFindFileData->dwReserved1 = 0; + return TRUE; + +} + + + + + + +HANDLE +STDCALL +FindFirstChangeNotificationA( + LPCSTR lpPathName, + WINBOOL bWatchSubtree, + DWORD dwNotifyFilter + ) +{ + ULONG i; + + WCHAR PathNameW[MAX_PATH]; + + + + + i = 0; + while ((*lpPathName)!=0 && i < MAX_PATH) + { + PathNameW[i] = *lpPathName; + lpPathName++; + i++; + } + PathNameW[i] = 0; + return FindFirstChangeNotificationW(PathNameW, bWatchSubtree, dwNotifyFilter ); + +} + +HANDLE +STDCALL +FindFirstChangeNotificationW( + LPCWSTR lpPathName, + WINBOOL bWatchSubtree, + DWORD dwNotifyFilter + ) +{ + NTSTATUS errCode; + + + IO_STATUS_BLOCK IoStatusBlock; + NOTIFY_INFO *NotifyHandle; + WCHAR Buffer[100]; + ULONG BufferSize = 100; + + NotifyHandle = HeapAlloc(GetProcessHeap(),0,sizeof(NOTIFY_INFO)); + + NotifyHandle->Event = CreateEventW(NULL,FALSE,FALSE,NULL); + NotifyHandle->FileHandle = CreateFileW(lpPathName,GENERIC_READ,FILE_SHARE_READ | FILE_SHARE_WRITE,NULL,OPEN_EXISTING, + FILE_ATTRIBUTE_NORMAL, NULL); + + NotifyHandle->dwNotifyFilter = dwNotifyFilter; + NotifyHandle->bWatchSubtree = bWatchSubtree; + + errCode = NtNotifyChangeDirectoryFile( + NotifyHandle->FileHandle, + NotifyHandle->Event, + NULL, + NULL, + &IoStatusBlock, + Buffer, + BufferSize, + NotifyHandle->dwNotifyFilter, + NotifyHandle->bWatchSubtree + ); + return NotifyHandle; +} + +WINBOOL +STDCALL +FindNextChangeNotification( + HANDLE hChangeHandle + ) +{ + NTSTATUS errCode; + + + IO_STATUS_BLOCK IoStatusBlock; + NOTIFY_INFO *NotifyHandle = hChangeHandle; + + WCHAR Buffer[100]; + ULONG BufferSize = 100; + EVENT_BASIC_INFORMATION EventBasic; + ULONG ReturnLength; + + + + NtQueryEvent(NotifyHandle->Event,EventBasicInformation,&EventBasic,sizeof(EVENT_BASIC_INFORMATION),&ReturnLength); + + if ( EventBasic.Signaled == TRUE ) { + ResetEvent(NotifyHandle->Event); + return TRUE; + } + + errCode = NtNotifyChangeDirectoryFile( + NotifyHandle->FileHandle, + NotifyHandle->Event, + NULL, + NULL, + &IoStatusBlock, + Buffer, + BufferSize, + NotifyHandle->dwNotifyFilter, + (BOOLEAN)NotifyHandle->bWatchSubtree + ); + + return FALSE; +} + +WINBOOL +STDCALL +FindCloseChangeNotification( + HANDLE hChangeHandle + ) +{ + HeapFree(GetProcessHeap(),0,hChangeHandle); + return TRUE; + +} + + + + + + + + + + + + + + + diff --git a/reactos/lib/kernel32/file/volume.c b/reactos/lib/kernel32/file/volume.c index 5996c17fbd7..39920fe5825 100644 --- a/reactos/lib/kernel32/file/volume.c +++ b/reactos/lib/kernel32/file/volume.c @@ -271,3 +271,43 @@ GetVolumeInformationW( } +WINBOOL +STDCALL +SetVolumeLabelA( + LPCSTR lpRootPathName, + LPCSTR lpVolumeName + ) +{ + WCHAR RootPathNameW[MAX_PATH]; + WCHAR VolumeNameW[MAX_PATH]; + UINT i; + + i = 0; + while ((*lpRootPathName)!=0 && i < MAX_PATH) + { + RootPathNameW[i] = *lpRootPathName; + lpRootPathName++; + i++; + } + RootPathNameW[i] = 0; + + i = 0; + while ((*lpVolumeName)!=0 && i < MAX_PATH) + { + VolumeNameW[i] = *lpVolumeName; + lpVolumeName++; + i++; + } + VolumeNameW[i] = 0; + return SetVolumeLabelW(RootPathNameW,VolumeNameW); +} + +WINBOOL +STDCALL +SetVolumeLabelW( + LPCWSTR lpRootPathName, + LPCWSTR lpVolumeName + ) +{ + return FALSE; +} diff --git a/reactos/lib/kernel32/makefile b/reactos/lib/kernel32/makefile index 531b12fd6b6..52a9f2240e9 100644 --- a/reactos/lib/kernel32/makefile +++ b/reactos/lib/kernel32/makefile @@ -2,17 +2,18 @@ all: kernel32.a SYNCH_OBJECTS = synch/critical.o synch/event.o synch/wait.o -MISC_OBJECTS = misc/error.o misc/atom.o misc/handle.o misc/env.o misc/dllmain.o +MISC_OBJECTS = misc/error.o misc/atom.o misc/handle.o misc/env.o misc/dllmain.o \ + misc/console.o FILE_OBJECTS = file/file.o file/curdir.o file/lfile.o file/dir.o \ file/iocompl.o file/volume.o file/deviceio.o file/dosdev.o \ - file/create.o file/find.o file/cnotify.o + file/create.o file/find.o MEM_OBJECTS = mem/virtual.o mem/heap.o mem/utils.o THREAD_OBJECTS = thread/thread.o -PROCESS_OBJECTS = process/proc.o process/cmdline.o +PROCESS_OBJECTS = process/proc.o STRING_OBJECTS = string/lstring.o @@ -21,15 +22,13 @@ INTERNAL_OBJECTS = internal/dprintf.o internal/init.o EXCEPT_OBJECTS = except/except.o - - OBJECTS = $(MISC_OBJECTS) $(FILE_OBJECTS) $(THREAD_OBJECTS) \ $(PROCESS_OBJECTS) $(STRING_OBJECTS) $(MEM_OBJECTS) \ $(INTERNAL_OBJECTS) $(SYNCH_OBJECTS) $(EXCEPT_OBJECTS) kernel32.a: $(OBJECTS) - $(AR) rcs kernel32.a $(OBJECTS) + $(AR) vrcs kernel32.a $(OBJECTS) dummy: diff --git a/reactos/lib/kernel32/mem/heap.c b/reactos/lib/kernel32/mem/heap.c index 36a3b62e109..c48c4cc42da 100644 --- a/reactos/lib/kernel32/mem/heap.c +++ b/reactos/lib/kernel32/mem/heap.c @@ -26,16 +26,13 @@ * Put the type definitions of the heap in a seperate header. Boudewijn Dekker */ -/* INCLUDES *****************************************************************/ - -#define NDEBUG -#include - #include +#include #include #include -/* GLOBALS ******************************************************************/ +#include + static HEAP_BUCKET __HeapDefaultBuckets[]= { @@ -49,9 +46,7 @@ static HEAP_BUCKET __HeapDefaultBuckets[]= { NULL, 256, 15, 4088 }, }; -PHEAP __ProcessHeap = NULL; - -/* FUNCTIONS ****************************************************************/ +PHEAP __ProcessHeap; static BOOL __HeapCommit(PHEAP pheap, LPVOID start, LPVOID end); static BOOL __HeapDecommit(PHEAP pheap, LPVOID start, LPVOID end); @@ -68,6 +63,8 @@ static BOOL __HeapFreeFragment(PHEAP pheap, ULONG flags, LPVOID ptr); static PHEAP __HeapPrepare(LPVOID base, ULONG minsize, ULONG maxsize, ULONG flags); + + /********************************************************************* * __HeapCommit * * * @@ -75,8 +72,8 @@ static PHEAP __HeapPrepare(LPVOID base, ULONG minsize, ULONG maxsize, *********************************************************************/ static BOOL __HeapCommit(PHEAP pheap, LPVOID start, LPVOID end) { - DPRINT("__HeapCommit( 0x%lX, 0x%lX, 0x%lX)\n", - (ULONG) pheap, (ULONG) start, (ULONG) end); + dprintf("__HeapCommit( 0x%lX, 0x%lX, 0x%lX)\n", + (ULONG) pheap, (ULONG) start, (ULONG) end); if(end >= pheap->LastBlock) pheap->LastBlock=end; @@ -94,7 +91,7 @@ static BOOL __HeapCommit(PHEAP pheap, LPVOID start, LPVOID end) *********************************************************************/ static BOOL __HeapDecommit(PHEAP pheap, LPVOID start, LPVOID end) { - DPRINT("__HeapDecommit( 0x%lX, 0x%lX, 0x%lX)\n", + dprintf("__HeapDecommit( 0x%lX, 0x%lX, 0x%lX)\n", (ULONG) pheap, (ULONG) start, (ULONG) end); #ifdef NOT __VirtualDump(); @@ -120,7 +117,7 @@ static LPVOID __HeapAlloc(PHEAP pheap, ULONG flags, ULONG size, ULONG tag) ULONG freesize; ULONG allocsize; - DPRINT("__HeapAlloc(pheap %x, flags %x, size %d, tag %x)\n", + dprintf("__HeapAlloc(pheap %x, flags %x, size %d, tag %x)\n", pheap,flags,size,tag); pfree=&(pheap->Start); @@ -242,7 +239,7 @@ static LPVOID __HeapReAlloc(PHEAP pheap, ULONG flags, LPVOID pold, DWORD size) */ if(size==0) { - DPRINT("__HeapReAlloc: freeing memory\n"); + dprintf("__HeapReAlloc: freeing memory\n"); __HeapFree(pheap, flags, pold); return NULL; } @@ -258,7 +255,7 @@ static LPVOID __HeapReAlloc(PHEAP pheap, ULONG flags, LPVOID pold, DWORD size) #endif else if(newsize < allocsize ) { - DPRINT("__HeapReAlloc: shrinking memory\n"); + dprintf("__HeapReAlloc: shrinking memory\n"); /* free remaining region of memory */ prealloc->Size=size | HEAP_NORMAL_TAG; pnext=HEAP_NEXT(prealloc); @@ -274,7 +271,7 @@ static LPVOID __HeapReAlloc(PHEAP pheap, ULONG flags, LPVOID pold, DWORD size) } else if(newsize == allocsize ) { - DPRINT("__HeapReAlloc: no changes\n"); + dprintf("__HeapReAlloc: no changes\n"); /* nothing to do */ prealloc->Size= size | HEAP_NORMAL_TAG; return pold; @@ -287,7 +284,7 @@ static LPVOID __HeapReAlloc(PHEAP pheap, ULONG flags, LPVOID pold, DWORD size) if(((LPVOID) pnext< pheap->End)&& HEAP_ISFREE(pnext) && (HEAP_SIZE(pnext) + HEAP_ADMIN_SIZE >=newsize-allocsize)) { - DPRINT("__HeapReAlloc: joining memory\n"); + dprintf("__HeapReAlloc: joining memory\n"); oldsize=HEAP_SIZE(prealloc); prealloc->Size=size | HEAP_NORMAL_TAG; @@ -311,7 +308,7 @@ static LPVOID __HeapReAlloc(PHEAP pheap, ULONG flags, LPVOID pold, DWORD size) { if((flags&HEAP_REALLOC_IN_PLACE_ONLY)==0) { - DPRINT("__HeapReAlloc: allocating new memory\n"); + dprintf("__HeapReAlloc: allocating new memory\n"); /* alloc a new piece of memory */ oldsize=HEAP_SIZE(prealloc); pmem=__HeapAlloc(pheap, flags, size, HEAP_NORMAL_TAG); @@ -539,7 +536,7 @@ static BOOL __HeapFreeFragment(PHEAP pheap, ULONG flags, LPVOID pfree ) PHEAP_BUCKET pbucket; PHEAP_SUBALLOC psub; PHEAP_FRAGMENT pfrag=(PHEAP_FRAGMENT) - ((LPVOID)pfree-HEAP_FRAG_ADMIN_SIZE); + ((DWORD)pfree - HEAP_FRAG_ADMIN_SIZE); INT nalloc; /* sanity checks */ @@ -585,6 +582,7 @@ static BOOL __HeapFreeFragment(PHEAP pheap, ULONG flags, LPVOID pfree ) pfrag->FreeNext=NULL; } } + return TRUE; } @@ -597,7 +595,7 @@ PHEAP __HeapPrepare(LPVOID base, ULONG minsize, ULONG maxsize, ULONG flags) { PHEAP pheap=(PHEAP) base; - DPRINT("__HeapPrepare(base %x, minsize %d, maxsize %d, flags %x)\n", + dprintf("__HeapPrepare(base %x, minsize %d, maxsize %d, flags %x)\n", base,minsize,maxsize,flags); pheap->Magic=MAGIC_HEAP; @@ -630,10 +628,9 @@ PHEAP __HeapPrepare(LPVOID base, ULONG minsize, ULONG maxsize, ULONG flags) VOID WINAPI __HeapInit(LPVOID base, ULONG minsize, ULONG maxsize) { - base = VirtualAlloc(base,maxsize,MEM_RESERVE,PAGE_READWRITE); - VirtualAlloc(base,PAGESIZE,MEM_COMMIT,PAGE_READWRITE); - - __HeapPrepare(base, minsize, maxsize, 0); + __ProcessHeap = VirtualAlloc(base, maxsize, MEM_RESERVE, PAGE_READWRITE); + VirtualAlloc(__ProcessHeap, PAGESIZE, MEM_COMMIT, PAGE_READWRITE); + __HeapPrepare(__ProcessHeap, minsize, maxsize, 0); } @@ -674,10 +671,11 @@ BOOL WINAPI HeapDestroy(HANDLE hheap) *********************************************************************/ LPVOID STDCALL HeapAlloc(HANDLE hheap, DWORD flags, DWORD size) { + PHEAP pheap=hheap; LPVOID retval; - DPRINT("HeapAlloc( 0x%lX, 0x%lX, 0x%lX )\n", + aprintf("HeapAlloc( 0x%lX, 0x%lX, 0x%lX )\n", (ULONG) hheap, flags, (ULONG) size ); #ifdef NOT HeapValidate(hheap, 0, 0); @@ -693,9 +691,10 @@ LPVOID STDCALL HeapAlloc(HANDLE hheap, DWORD flags, DWORD size) if( (flags | pheap->Flags) & HEAP_NO_SERIALIZE ) LeaveCriticalSection(&(pheap->Synchronize)); - DPRINT("HeapAlloc returns 0x%lX\n", (ULONG) retval); + aprintf("HeapAlloc returns 0x%lX\n", (ULONG) retval); return retval; + } /********************************************************************* @@ -703,11 +702,12 @@ LPVOID STDCALL HeapAlloc(HANDLE hheap, DWORD flags, DWORD size) *********************************************************************/ LPVOID STDCALL HeapReAlloc(HANDLE hheap, DWORD flags, LPVOID ptr, DWORD size) { + PHEAP pheap=hheap; PHEAP_BLOCK pfree=((PHEAP_BLOCK)ptr-1); LPVOID retval; - DPRINT("HeapReAlloc( 0x%lX, 0x%lX, 0x%lX, 0x%lX )\n", + aprintf("HeapReAlloc( 0x%lX, 0x%lX, 0x%lX, 0x%lX )\n", (ULONG) hheap, flags, (ULONG) ptr, size ); #ifdef NOT HeapValidate(hheap, 0, 0); @@ -726,6 +726,8 @@ LPVOID STDCALL HeapReAlloc(HANDLE hheap, DWORD flags, LPVOID ptr, DWORD size) LeaveCriticalSection(&(pheap->Synchronize)); return retval; + + } /********************************************************************* @@ -733,11 +735,12 @@ LPVOID STDCALL HeapReAlloc(HANDLE hheap, DWORD flags, LPVOID ptr, DWORD size) *********************************************************************/ WINBOOL STDCALL HeapFree(HANDLE hheap, DWORD flags, LPVOID ptr) { + PHEAP pheap=hheap; - PHEAP_BLOCK pfree=(PHEAP_BLOCK)((LPVOID)ptr-HEAP_ADMIN_SIZE); + PHEAP_BLOCK pfree=(PHEAP_BLOCK)((DWORD)ptr-HEAP_ADMIN_SIZE); BOOL retval; - DPRINT("HeapFree( 0x%lX, 0x%lX, 0x%lX )\n", + aprintf("HeapFree( 0x%lX, 0x%lX, 0x%lX )\n", (ULONG) hheap, flags, (ULONG) ptr ); #ifdef NOT HeapValidate(hheap, 0, 0); @@ -746,16 +749,23 @@ WINBOOL STDCALL HeapFree(HANDLE hheap, DWORD flags, LPVOID ptr) EnterCriticalSection(&(pheap->Synchronize)); if(HEAP_ISNORMAL(pfree)) - retval=__HeapFree(pheap, flags, ptr); + { + retval=__HeapFree(pheap, flags, ptr); + } else if(HEAP_ISFRAG(pfree)) - retval=__HeapFreeFragment(pheap, flags, ptr); + { + retval=__HeapFreeFragment(pheap, flags, ptr); + } else - retval=__ErrorReturnFalse(ERROR_INVALID_PARAMETER); + { + retval=__ErrorReturnFalse(ERROR_INVALID_PARAMETER); + } if( (flags| pheap->Flags) & HEAP_NO_SERIALIZE ) LeaveCriticalSection(&(pheap->Synchronize)); return retval; + } /********************************************************************* @@ -763,7 +773,7 @@ WINBOOL STDCALL HeapFree(HANDLE hheap, DWORD flags, LPVOID ptr) *********************************************************************/ HANDLE WINAPI GetProcessHeap(VOID) { - DPRINT("GetProcessHeap()\n"); + aprintf("GetProcessHeap()\n"); return (HANDLE) __ProcessHeap; } @@ -778,7 +788,7 @@ DWORD WINAPI GetProcessHeaps(DWORD maxheaps, PHANDLE phandles ) DWORD retval; PHEAP pheap; - DPRINT("GetProcessHeaps( %u, 0x%lX )\n", maxheaps, (ULONG) phandles ); + aprintf("GetProcessHeaps( %u, 0x%lX )\n", maxheaps, (ULONG) phandles ); pheap= __ProcessHeap; retval=0; @@ -808,7 +818,7 @@ BOOL WINAPI HeapLock(HANDLE hheap) { PHEAP pheap=hheap; - DPRINT("HeapLock( 0x%lX )\n", (ULONG) hheap ); + aprintf("HeapLock( 0x%lX )\n", (ULONG) hheap ); EnterCriticalSection(&(pheap->Synchronize)); return TRUE; @@ -822,7 +832,7 @@ BOOL WINAPI HeapUnlock(HANDLE hheap) { PHEAP pheap=hheap; - DPRINT("HeapUnlock( 0x%lX )\n", (ULONG) hheap ); + aprintf("HeapUnlock( 0x%lX )\n", (ULONG) hheap ); LeaveCriticalSection(&(pheap->Synchronize)); return TRUE; @@ -873,7 +883,7 @@ DWORD WINAPI HeapSize(HANDLE hheap, DWORD flags, LPCVOID pmem) PHEAP_BLOCK palloc=((PHEAP_BLOCK)pmem-1); DWORD retval=0; - DPRINT("HeapSize( 0x%lX, 0x%lX, 0x%lX )\n", + aprintf("HeapSize( 0x%lX, 0x%lX, 0x%lX )\n", (ULONG) hheap, flags, (ULONG) pmem ); if(pheap->Magic!=MAGIC_HEAP) @@ -931,7 +941,7 @@ BOOL WINAPI HeapValidate(HANDLE hheap, DWORD flags, LPCVOID pmem) pnext=HEAP_NEXT(pcheck); if((pprev)&&(HEAP_PREV(pcheck)!=pprev)) { - DPRINT("HeapValidate: linked list invalid, region 0x%lX," + dprintf("HeapValidate: linked list invalid, region 0x%lX," " previous region 0x%lX, list says 0x%lX\n", (ULONG)pcheck, (ULONG)pprev, (ULONG) HEAP_PREV(pcheck)); return FALSE; @@ -955,13 +965,13 @@ BOOL WINAPI HeapValidate(HANDLE hheap, DWORD flags, LPCVOID pmem) pnextfrag=(PHEAP_FRAGMENT)((LPVOID)pfrag+add); if(pfrag->Magic!=HEAP_FRAG_MAGIC) { - DPRINT("HeapValidate: fragment %d magic invalid, region 0x%lX," + dprintf("HeapValidate: fragment %d magic invalid, region 0x%lX," " previous region 0x%lX\n", i, (ULONG)pcheck, (ULONG)pprev); return FALSE; } if(pfrag->Number!=i) { - DPRINT("HeapValidate: fragment %d number invalid, region 0x%lX," + dprintf("HeapValidate: fragment %d number invalid, region 0x%lX," " previous region 0x%lX\n", i, (ULONG)pcheck, (ULONG)pprev); return FALSE; } @@ -969,7 +979,7 @@ BOOL WINAPI HeapValidate(HANDLE hheap, DWORD flags, LPCVOID pmem) number++; if(pfrag->Sub!=psub) { - DPRINT("HeapValidate: fragment %d suballoc invalid, region 0x%lX," + dprintf("HeapValidate: fragment %d suballoc invalid, region 0x%lX," " previous region 0x%lX\n", i, (ULONG)pcheck, (ULONG)pprev); return FALSE; } @@ -978,11 +988,11 @@ BOOL WINAPI HeapValidate(HANDLE hheap, DWORD flags, LPCVOID pmem) } if(number!=psub->NumberFree) { - DPRINT("HeapValidate: invalid number of free fragments, region 0x%lX," + dprintf("HeapValidate: invalid number of free fragments, region 0x%lX," " previous region 0x%lX\n", (ULONG)pcheck, (ULONG)pprev); return FALSE; } - DPRINT("HeapValidate: [0x%08lX-0x%08lX] suballocated," + dprintf("HeapValidate: [0x%08lX-0x%08lX] suballocated," " bucket size=%d, bitmap=0x%08lX\n", (ULONG) pcheck, (ULONG) pnext, pbucket->Size, psub->Bitmap); } @@ -990,22 +1000,22 @@ BOOL WINAPI HeapValidate(HANDLE hheap, DWORD flags, LPCVOID pmem) { if(HEAP_RSIZE(pcheck)!=HEAP_SIZE(pcheck)) { - DPRINT("HeapValidate: invalid size of free region 0x%lX," + dprintf("HeapValidate: invalid size of free region 0x%lX," " previous region 0x%lX\n", (ULONG) pcheck, (ULONG) pprev); return FALSE; } - DPRINT("HeapValidate: [0x%08lX-0x%08lX] free\n", + dprintf("HeapValidate: [0x%08lX-0x%08lX] free\n", (ULONG) pcheck, (ULONG) pnext ); } else if(HEAP_ISNORMAL(pcheck)) { - DPRINT("HeapValidate: [0x%08lX-0x%08lX] allocated\n", + dprintf("HeapValidate: [0x%08lX-0x%08lX] allocated\n", (ULONG) pcheck, (ULONG) pnext ); } else { - DPRINT("HeapValidate: invalid tag %x, region 0x%lX," + dprintf("HeapValidate: invalid tag %x, region 0x%lX," " previous region 0x%lX\n", pcheck->Size>>28, (ULONG)pcheck, (ULONG)pprev); return FALSE; diff --git a/reactos/lib/kernel32/mem/utils.c b/reactos/lib/kernel32/mem/utils.c index 3d2e37ab6a3..9ca717d75c0 100644 --- a/reactos/lib/kernel32/mem/utils.c +++ b/reactos/lib/kernel32/mem/utils.c @@ -1,13 +1,11 @@ #include - -#define NDEBUG #include VOID CopyMemory(PVOID Destination, CONST VOID* Source, DWORD Length) { DWORD i; - DPRINT("CopyMemory(Destination %x, Source %x, Length %d)\n", + dprintf("CopyMemory(Destination %x, Source %x, Length %d)\n", Destination,Source,Length); for (i=0; i #include #include -// RJJ: (we dont have it) #include +//#include + + + + + /* system global and local atom tables */ @@ -319,7 +324,7 @@ AWGLAddAtom( if(lpfree && atomlen) { lpfree->q = q; lpfree->refcnt = 1; - wcsncpy(&at->AtomData[lpfree->idx],lpString,atomlen); + lstrcpynW(&at->AtomData[lpfree->idx],lpString,atomlen); return freeindex + ATOMBASE; } @@ -396,7 +401,7 @@ AWGLFindAtom( if(lp->q == q) { if(HIWORD(lpString) == 0) return ATOMBASE + index; - if(wcsicmp(&at->AtomData[lp->idx],lpString) == 0) + if(lstrcmpiW(&at->AtomData[lp->idx],lpString) == 0) return ATOMBASE + index; } } @@ -421,7 +426,7 @@ AWGLGetAtomName(ATOMTABLE *at, ATOM atom, WCHAR *lpString,int len) if (atomlen < len) lstrcpyW(lpString,atomstr); else { - wcsncpy(lpString,atomstr,len-1); + lstrcpynW(lpString,atomstr,len-1); lpString[len-1] = '\0'; } return (UINT)lstrlenW(lpString); diff --git a/reactos/lib/kernel32/misc/console.c b/reactos/lib/kernel32/misc/console.c new file mode 100644 index 00000000000..019f765cd22 --- /dev/null +++ b/reactos/lib/kernel32/misc/console.c @@ -0,0 +1,168 @@ +#include +#include + +HANDLE StdInput = NULL; +HANDLE StdOutput = NULL; +HANDLE StdError = NULL; + + + + +#define FSCTL_GET_CONSOLE_SCREEN_BUFFER_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 254, DO_DIRECT_IO, FILE_READ_ACCESS|FILE_WRITE_ACCESS) +#define FSCTL_SET_CONSOLE_SCREEN_BUFFER_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 255, DO_DIRECT_IO, FILE_READ_ACCESS|FILE_WRITE_ACCESS) + +HANDLE +STDCALL +GetStdHandle( + DWORD nStdHandle + ) +{ + if ( nStdHandle == STD_INPUT_HANDLE ) + return StdInput; + if ( nStdHandle == STD_OUTPUT_HANDLE ) + return StdOutput; + if ( nStdHandle == STD_ERROR_HANDLE ) + return StdError; +/* + if ( nStdHandle == STD_AUX_HANDLE ) + return StdError; + if ( nStdHandle == STD_PRINT_HANDLE ) + return StdError; +*/ + return NULL; + +} + +WINBOOL +STDCALL +WriteConsoleA( + HANDLE hConsoleOutput, + CONST VOID *lpBuffer, + DWORD nNumberOfCharsToWrite, + LPDWORD lpNumberOfCharsWritten, + LPVOID lpReserved + ) +{ + return WriteFile(hConsoleOutput, lpBuffer, nNumberOfCharsToWrite,lpNumberOfCharsWritten, lpReserved); +} + + +WINBOOL +STDCALL +ReadConsoleA( + HANDLE hConsoleInput, + LPVOID lpBuffer, + DWORD nNumberOfCharsToRead, + LPDWORD lpNumberOfCharsRead, + LPVOID lpReserved + ) +{ + return ReadFile(hConsoleInput,lpBuffer,nNumberOfCharsToRead,lpNumberOfCharsRead,lpReserved); +} + +WINBOOL +STDCALL +AllocConsole( VOID ) +{ + StdInput = CreateFile("\\Device\\Keyboard", + FILE_GENERIC_READ, + 0, + NULL, + OPEN_EXISTING, + 0, + NULL); + + StdOutput = CreateFile("\\Device\\BlueScreen", + FILE_GENERIC_WRITE|FILE_GENERIC_READ, + 0, + NULL, + OPEN_EXISTING, + 0, + NULL); + + StdError = StdOutput; + + return TRUE; +} + + +WINBOOL +STDCALL +FreeConsole( VOID ) +{ + return TRUE; +} + + +WINBOOL +STDCALL +GetConsoleScreenBufferInfo( + HANDLE hConsoleOutput, + PCONSOLE_SCREEN_BUFFER_INFO lpConsoleScreenBufferInfo + ) +{ + DWORD dwBytesReturned; + if( !DeviceIoControl(hConsoleOutput, + FSCTL_GET_CONSOLE_SCREEN_BUFFER_INFO, + NULL,0, + lpConsoleScreenBufferInfo,sizeof(CONSOLE_SCREEN_BUFFER_INFO),&dwBytesReturned,NULL )) + return FALSE; + + return TRUE; +} + +WINBOOL +STDCALL +SetConsoleCursorPosition( + HANDLE hConsoleOutput, + COORD dwCursorPosition + ) +{ + DWORD dwBytesReturned; + CONSOLE_SCREEN_BUFFER_INFO ConsoleScreenBufferInfo; + + if( !GetConsoleScreenBufferInfo(hConsoleOutput,&ConsoleScreenBufferInfo) ) + return FALSE; +// ConsoleScreenBufferInfo.dwCursorPosition.X = dwCursorPosition.X; +// ConsoleScreenBufferInfo.dwCursorPosition.Y = dwCursorPosition.Y; + return TRUE; + if( !DeviceIoControl( + hConsoleOutput, + FSCTL_SET_CONSOLE_SCREEN_BUFFER_INFO, + &ConsoleScreenBufferInfo, + sizeof(CONSOLE_SCREEN_BUFFER_INFO), + NULL, + 0, + &dwBytesReturned, + NULL )) + return FALSE; + + return TRUE; +} + +WINBOOL +STDCALL +FillConsoleOutputCharacterA( + HANDLE hConsoleOutput, + CHAR cCharacter, + DWORD nLength, + COORD dwWriteCoord, + LPDWORD lpNumberOfCharsWritten + ) +{ + return FillConsoleOutputCharacterW(hConsoleOutput, + (WCHAR) cCharacter,nLength, dwWriteCoord,lpNumberOfCharsWritten); +} + +WINBOOL +STDCALL +FillConsoleOutputCharacterW( + HANDLE hConsoleOutput, + WCHAR cCharacter, + DWORD nLength, + COORD dwWriteCoord, + LPDWORD lpNumberOfCharsWritten + ) +{ + return FALSE; +} diff --git a/reactos/lib/kernel32/misc/dllmain.c b/reactos/lib/kernel32/misc/dllmain.c index 7fcd1f5ea0d..e1af10b457e 100644 --- a/reactos/lib/kernel32/misc/dllmain.c +++ b/reactos/lib/kernel32/misc/dllmain.c @@ -10,6 +10,7 @@ #include #include +#include #include WINBOOL @@ -20,13 +21,12 @@ DllMain ( LPVOID lpReserved ); -NT_PEB Peb; - - -NT_PEB *CurrentPeb; NT_TEB *Teb; -PROCESSINFOW ProcessInfo; + + + + @@ -37,12 +37,17 @@ DllMain ( ULONG ul_reason_for_call, LPVOID lpReserved ) { + switch( ul_reason_for_call ) { case DLL_PROCESS_ATTACH: { - CurrentPeb = &Peb; - CurrentPeb->ProcessHeap = HeapCreate(HEAP_GENERATE_EXCEPTIONS,8192,0); + + GetCurrentPeb()->ProcessHeap = HeapCreate(HEAP_GENERATE_EXCEPTIONS,8192,0); InitAtomTable(13); + SetCurrentDirectoryW(L"C:"); + // SetSystemDirectoryW(L"C:\\Reactos\\System"); + // SetWindowsDirectoryW(L"C:\\Reactos"); + } case DLL_THREAD_ATTACH: { diff --git a/reactos/lib/kernel32/misc/env.c b/reactos/lib/kernel32/misc/env.c index 77a6e523a18..6124a0a9b7e 100644 --- a/reactos/lib/kernel32/misc/env.c +++ b/reactos/lib/kernel32/misc/env.c @@ -14,17 +14,43 @@ #include #define MAX_ENVIRONMENT_VARS 255 +#define MAX_VALUE 1024 typedef struct _ENV_ELEMENT { UNICODE_STRING Name; UNICODE_STRING Value; + WINBOOL Valid; } ENV_ELEMENT; ENV_ELEMENT Environment[MAX_ENVIRONMENT_VARS+1]; UINT nEnvVar = 0; -int wcsncmp2(CONST WCHAR *s, CONST WCHAR *t,UINT n); +DWORD +STDCALL +GetEnvironmentVariableA( + LPCSTR lpName, + LPSTR lpBuffer, + DWORD nSize + ) +{ + WCHAR BufferW[MAX_VALUE]; + WCHAR NameW[MAX_PATH]; + DWORD RetValue; + int i=0; + while ((*lpName)!=0 && i < MAX_PATH) + { + NameW[i] = *lpName; + lpName++; + i++; + } + NameW[i] = 0; + + RetValue = GetEnvironmentVariableW(NameW,BufferW,nSize); + for(i=0;i 0; s++, t++, n--) - if ( *s == 0 ) - return 0; - return *s - *t; -} +WINBOOL +STDCALL +SetEnvironmentVariableA( + LPCSTR lpName, + LPCSTR lpValue + ) +{ + WCHAR NameW[MAX_PATH]; + WCHAR ValueW[MAX_VALUE]; + + int i=0; + while ((*lpName)!=0 && i < MAX_PATH) + { + NameW[i] = *lpName; + lpName++; + i++; + } + NameW[i] = 0; + + i = 0; + + while ((*lpValue)!=0 && i < MAX_PATH) + { + ValueW[i] = *lpValue; + lpValue++; + i++; + } + ValueW[i] = 0; + return SetEnvironmentVariableW(NameW,ValueW); + + +} WINBOOL STDCALL @@ -80,31 +131,54 @@ SetEnvironmentVariableW( while (i < nEnvVar) { - if ( wcsncmp2(Environment[i].Name.Buffer,lpName,min(NameLen,Environment[i].Name.Length)) != 0 ) { - lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,Environment[i].Value.MaximumLength)); - return TRUE; + if ( wcsnicmp(Environment[i].Name.Buffer,lpName,min(NameLen,Environment[i].Name.Length/sizeof(WCHAR))) != 0 ) { + if ( lpValue != NULL ) { + lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,Environment[i].Value.MaximumLength/sizeof(WCHAR))); + return TRUE; + } + else { + Environment[i].Valid = FALSE; + Environment[i].Value.Length = 0; + Environment[i].Name.Length = 0; + return FALSE; + } + + } i++; } - if ( nEnvVar > MAX_ENVIRONMENT_VARS ) + if ( nEnvVar >= MAX_ENVIRONMENT_VARS ) return FALSE; - NameBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,MAX_PATH*sizeof(WCHAR)); - ValueBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,1024*sizeof(WCHAR)); - - Environment[i].Name.Buffer = NameBuffer; - Environment[i].Name.MaximumLength = MAX_PATH; - lstrcpynW(Environment[i].Name.Buffer,lpValue,min(NameLen,Environment[i].Name.MaximumLength)); - Environment[i].Name.Length = NameLen; - Environment[i].Value.Buffer = ValueBuffer; - Environment[i].Value.MaximumLength = 1024; - lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,Environment[i].Value.MaximumLength)); - Environment[i].Value.Length = ValueLen; + while (i < nEnvVar) + { + if ( Environment[i].Valid == FALSE ) + break; + i++; + } + if ( i == nEnvVar ) { + NameBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,MAX_PATH*sizeof(WCHAR) ); + ValueBuffer = (WCHAR *)HeapAlloc(GetProcessHeap(),HEAP_GENERATE_EXCEPTIONS|HEAP_ZERO_MEMORY,MAX_VALUE*sizeof(WCHAR) ); + + Environment[i].Name.Buffer = NameBuffer; + Environment[i].Name.MaximumLength = MAX_PATH*sizeof(WCHAR); + + Environment[i].Value.Buffer = ValueBuffer; + Environment[i].Value.MaximumLength = MAX_VALUE*sizeof(WCHAR); + nEnvVar++; + } + Environment[i].Valid = TRUE; + + lstrcpynW(Environment[i].Name.Buffer,lpValue,min(NameLen,(Environment[i].Name.MaximumLength-sizeof(WCHAR))/sizeof(WCHAR))); + Environment[i].Name.Length = NameLen*sizeof(WCHAR); + + + lstrcpynW(Environment[i].Value.Buffer,lpValue,min(ValueLen,(Environment[i].Value.MaximumLength-sizeof(WCHAR)))/sizeof(WCHAR)); + Environment[i].Value.Length = ValueLen*sizeof(WCHAR); - nEnvVar++; return TRUE; @@ -140,7 +214,7 @@ GetVersionExW( lpVersionInformation->dwMinorVersion = 0; lpVersionInformation->dwBuildNumber = 12; lpVersionInformation->dwPlatformId = VER_PLATFORM_WIN32_NT; - lstrcpyW((WCHAR *)lpVersionInformation->szCSDVersion,L"ReactOs Pre-Alpha 12"); + lstrcpyW((WCHAR *)lpVersionInformation->szCSDVersion,L"Ariadne was here..."); return TRUE; } @@ -155,7 +229,153 @@ GetVersionExA( lpVersionInformation->dwMinorVersion = 0; lpVersionInformation->dwBuildNumber = 12; lpVersionInformation->dwPlatformId = VER_PLATFORM_WIN32_NT; - lstrcpyA((char *)lpVersionInformation->szCSDVersion,"ReactOs Pre-Alpha 12"); + lstrcpyA((char *)lpVersionInformation->szCSDVersion,"ReactOs Pre-Alpha"); + return TRUE; +} + +VOID GetSystemTime( + LPSYSTEMTIME lpSystemTime + ) +{ + NTSTATUS errCode; +memset(lpSystemTime,sizeof(SYSTEMTIME),0); +// errCode = NtQuerySystemTime ( +// (TIME *)lpSystemTime +// ); + return; +} + +WINBOOL +STDCALL +SetSystemTime( + CONST SYSTEMTIME *lpSystemTime + ) +{ + NTSTATUS errCode; + LARGE_INTEGER NewSystemTime; + errCode = NtSetSystemTime ( + (LARGE_INTEGER *)lpSystemTime, + &NewSystemTime + ); + if ( !NT_SUCCESS(errCode) ) + return FALSE; + return TRUE; +} + + + + + + +VOID +STDCALL +GetLocalTime( + LPSYSTEMTIME lpSystemTime + ) +{ + GetSystemTime(lpSystemTime); +} + + +WINBOOL +STDCALL +SetLocalTime( + CONST SYSTEMTIME *lpSystemTime + ) +{ + return SetSystemTime(lpSystemTime); +} + +LPSTR +STDCALL +GetEnvironmentStringsA( + VOID + ) +{ + WCHAR *EnvironmentStringsW; + char *EnvironmentStringsA; + int size = 0; + int i; + EnvironmentStringsW = GetEnvironmentStringsW(); + EnvironmentStringsA = (char *)EnvironmentStringsW; + + for(i=0;iCid).UniqueProcess; - dprintf("TempFileName '%w'\n",TempFileName); - for (i=0; TempFileName[i]!=' ' && TempFileName[i] != 0; i++); - TempFileName[i]=0; - - } - if (TempFileName[1] != ':') - { - GetCurrentDirectoryW(MAX_PATH,TempDirectoryName); - wcscat(TempApplicationName,TempDirectoryName); - } - wcscat(TempApplicationName,TempFileName); - - RtlInitUnicodeString(&ApplicationNameString, TempApplicationName); - - dprintf("ApplicationName %w\n",ApplicationNameString.Buffer); - - InitializeObjectAttributes(&ObjectAttributes, - &ApplicationNameString, - OBJ_CASE_INSENSITIVE, - NULL, - SecurityDescriptor); - - /* - * Try to open the executable - */ - - errCode = NtOpenFile(&hFile, - SYNCHRONIZE|FILE_EXECUTE|FILE_READ_DATA, - &ObjectAttributes, - &IoStatusBlock, - FILE_SHARE_DELETE|FILE_SHARE_READ, - FILE_SYNCHRONOUS_IO_NONALERT|FILE_NON_DIRECTORY_FILE); - - if ( !NT_SUCCESS(errCode) ) - { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - - errCode = NtCreateSection(&hSection, - SECTION_ALL_ACCESS, - NULL, - NULL, - PAGE_EXECUTE, - SEC_IMAGE, - hFile); - NtClose(hFile); - - if ( !NT_SUCCESS(errCode) ) - { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - - errCode = NtCreateProcess(&hProcess, - PROCESS_ALL_ACCESS, - NULL, - NtCurrentProcess(), - bInheritHandles, - NULL, - NULL, - NULL); - - BaseAddress = (PVOID)0x10000; - LARGE_INTEGER_QUAD_PART(SectionOffset) = 0; - Size = 0x10000; - NtMapViewOfSection(hSection, - hProcess, - &BaseAddress, - 0, - Size, - &SectionOffset, - &Size, - 0, - MEM_COMMIT, - PAGE_READWRITE); - - - NtClose(hSection); - - if ( !NT_SUCCESS(errCode) ) - { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - -#if 0 - PriorityClass = NORMAL_PRIORITY_CLASS; - NtSetInformationProcess(hProcess, - ProcessBasePriority, - &PriorityClass, - sizeof(KPRIORITY)); -#endif - dprintf("Creating thread for process\n"); - lpStartAddress = BaseAddress; - hThread = CreateRemoteThread(hProcess, - lpThreadAttributes, - 4096, // 1 page ?? - lpStartAddress, - lpParameter, - dwCreationFlags, - &lpProcessInformation->dwThreadId); - - if ( hThread == NULL ) - return FALSE; - - lpProcessInformation->hProcess = hProcess; - lpProcessInformation->hThread = hThread; - - GetProcessId(hProcess,&lpProcessInformation->dwProcessId); - - return TRUE; } +unsigned char CommandLineA[MAX_PATH]; - -HANDLE STDCALL OpenProcess(DWORD dwDesiredAccess, - WINBOOL bInheritHandle, - DWORD dwProcessId) +LPSTR +STDCALL +GetCommandLineA( + VOID + ) +{ + WCHAR *CommandLineW; + ULONG i = 0; + + CommandLineW = GetCommandLineW(); + while ((CommandLineW[i])!=0 && i < MAX_PATH) + { + CommandLineA[i] = (unsigned char)CommandLineW[i]; + i++; + } + CommandLineA[i] = 0; + return CommandLineA; +} +LPWSTR +STDCALL +GetCommandLineW( + VOID + ) +{ + return GetCurrentPeb()->StartupInfo->CommandLine; +} + +wchar_t **CommandLineToArgvW(LPCWSTR lpCmdLine, int * pNumArgs ) { - NTSTATUS errCode; - HANDLE ProcessHandle; - OBJECT_ATTRIBUTES ObjectAttributes; - CLIENT_ID ClientId ; - - ClientId.UniqueProcess = (HANDLE)dwProcessId; - ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); - ObjectAttributes.RootDirectory = (HANDLE)NULL; - ObjectAttributes.SecurityDescriptor = NULL; - ObjectAttributes.SecurityQualityOfService = NULL; - - if ( bInheritHandle == TRUE ) - ObjectAttributes.Attributes = OBJ_INHERIT; - else - ObjectAttributes.Attributes = 0; - - errCode = NtOpenProcess(&ProcessHandle, - dwDesiredAccess, - &ObjectAttributes, - &ClientId); - if (!NT_SUCCESS(errCode)) - { - SetLastError(RtlNtStatusToDosError(errCode)); return NULL; - } - return ProcessHandle; +} + + + +WINBOOL +STDCALL +GetExitCodeProcess( + HANDLE hProcess, + LPDWORD lpExitCode + ) +{ + NTSTATUS errCode; + PROCESS_BASIC_INFORMATION ProcessBasic; + ULONG BytesWritten; + + errCode = NtQueryInformationProcess(hProcess,ProcessBasicInformation,&ProcessBasic,sizeof(PROCESS_BASIC_INFORMATION),&BytesWritten); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + memcpy( lpExitCode ,&ProcessBasic.ExitStatus,sizeof(DWORD)); + return TRUE; + +} + +WINBOOL +STDCALL +GetProcessId( + HANDLE hProcess, + LPDWORD lpProcessId + ) +{ + NTSTATUS errCode; + PROCESS_BASIC_INFORMATION ProcessBasic; + ULONG BytesWritten; + + errCode = NtQueryInformationProcess(hProcess,ProcessBasicInformation,&ProcessBasic,sizeof(PROCESS_BASIC_INFORMATION),&BytesWritten); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + memcpy( lpProcessId ,&ProcessBasic.UniqueProcessId,sizeof(DWORD)); + return TRUE; + +} + +WINBOOL +STDCALL +CreateProcessA( + LPCSTR lpApplicationName, + LPSTR lpCommandLine, + LPSECURITY_ATTRIBUTES lpProcessAttributes, + LPSECURITY_ATTRIBUTES lpThreadAttributes, + WINBOOL bInheritHandles, + DWORD dwCreationFlags, + LPVOID lpEnvironment, + LPCSTR lpCurrentDirectory, + LPSTARTUPINFO lpStartupInfo, + LPPROCESS_INFORMATION lpProcessInformation + ) +{ + WCHAR ApplicationNameW[MAX_PATH]; + WCHAR CommandLineW[MAX_PATH]; + WCHAR CurrentDirectoryW[MAX_PATH]; + + + ULONG i; + + i = 0; + while ((*lpApplicationName)!=0 && i < MAX_PATH) + { + ApplicationNameW[i] = *lpApplicationName; + lpApplicationName++; + i++; + } + ApplicationNameW[i] = 0; + + + i = 0; + while ((*lpCommandLine)!=0 && i < MAX_PATH) + { + CommandLineW[i] = *lpCommandLine; + lpCommandLine++; + i++; + } + CommandLineW[i] = 0; + + i = 0; + while ((*lpCurrentDirectory)!=0 && i < MAX_PATH) + { + CurrentDirectoryW[i] = *lpCurrentDirectory; + lpCurrentDirectory++; + i++; + } + CurrentDirectoryW[i] = 0; + + return CreateProcessW(ApplicationNameW,CommandLineW, lpProcessAttributes,lpThreadAttributes, + bInheritHandles,dwCreationFlags,lpEnvironment,CurrentDirectoryW,lpStartupInfo, + lpProcessInformation); + + +} + + +WINBOOL +STDCALL +CreateProcessW( + LPCWSTR lpApplicationName, + LPWSTR lpCommandLine, + LPSECURITY_ATTRIBUTES lpProcessAttributes, + LPSECURITY_ATTRIBUTES lpThreadAttributes, + WINBOOL bInheritHandles, + DWORD dwCreationFlags, + LPVOID lpEnvironment, + LPCWSTR lpCurrentDirectory, + LPSTARTUPINFO lpStartupInfo, + LPPROCESS_INFORMATION lpProcessInformation + ) +{ + HANDLE hFile, hSection, hProcess, hThread; + KPRIORITY PriorityClass; + OBJECT_ATTRIBUTES ObjectAttributes; + IO_STATUS_BLOCK IoStatusBlock; + BOOLEAN CreateSuspended; + + NTSTATUS errCode; + + UNICODE_STRING ApplicationNameString; + + + + LPTHREAD_START_ROUTINE lpStartAddress = NULL; + LPVOID lpParameter = NULL; + + hFile = NULL; + + ApplicationNameString.Length = lstrlenW(lpApplicationName)*sizeof(WCHAR); + + ApplicationNameString.Buffer = (WCHAR *)lpApplicationName; + ApplicationNameString.MaximumLength = ApplicationNameString.Length+sizeof(WCHAR); + + + ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); + ObjectAttributes.RootDirectory = NULL; + + + + if ( lpProcessAttributes != NULL ) { + if ( lpProcessAttributes->bInheritHandle ) + ObjectAttributes.Attributes = OBJ_INHERIT; + else + ObjectAttributes.Attributes = 0; + ObjectAttributes.SecurityDescriptor = lpProcessAttributes->lpSecurityDescriptor; + } + ObjectAttributes.Attributes |= OBJ_CASE_INSENSITIVE; + + errCode = NtOpenFile(&hFile,(SYNCHRONIZE|FILE_EXECUTE), &ObjectAttributes, + &IoStatusBlock,(FILE_SHARE_DELETE|FILE_SHARE_READ),(FILE_SYNCHRONOUS_IO_NONALERT|FILE_NON_DIRECTORY_FILE)); + + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + + errCode = NtCreateSection(&hSection,SECTION_ALL_ACCESS,NULL,NULL,PAGE_EXECUTE,SEC_IMAGE,hFile); + NtClose(hFile); + + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + + + if ( lpProcessAttributes != NULL ) { + if ( lpProcessAttributes->bInheritHandle ) + ObjectAttributes.Attributes = OBJ_INHERIT; + else + ObjectAttributes.Attributes = 0; + ObjectAttributes.SecurityDescriptor = lpProcessAttributes->lpSecurityDescriptor; + } + + errCode = NtCreateProcess(&hProcess,PROCESS_ALL_ACCESS, &ObjectAttributes,NtCurrentProcess(),bInheritHandles,hSection,NULL,NULL); + NtClose(hSection); + + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + + PriorityClass = NORMAL_PRIORITY_CLASS; + NtSetInformationProcess(hProcess,ProcessBasePriority,&PriorityClass,sizeof(KPRIORITY)); + + if ( ( dwCreationFlags & CREATE_SUSPENDED ) == CREATE_SUSPENDED) + CreateSuspended = TRUE; + else + CreateSuspended = FALSE; + + hThread = CreateRemoteThread( + hProcess, + lpThreadAttributes, + 4096, // 1 page ?? + lpStartAddress, + lpParameter, + CREATE_SUSPENDED, + &lpProcessInformation->dwThreadId + ); + + + if ( hThread == NULL ) + return FALSE; + + + + lpProcessInformation->hProcess = hProcess; + lpProcessInformation->hThread = hThread; + + + + + GetProcessId(hProcess,&lpProcessInformation->dwProcessId); + + + + return TRUE; + + + } + + + +HANDLE +STDCALL +OpenProcess( + DWORD dwDesiredAccess, + WINBOOL bInheritHandle, + DWORD dwProcessId + ) +{ + + + NTSTATUS errCode; + HANDLE ProcessHandle; + OBJECT_ATTRIBUTES ObjectAttributes; + CLIENT_ID ClientId ; + + ClientId.UniqueProcess = (HANDLE)dwProcessId; + ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); + ObjectAttributes.RootDirectory = (HANDLE)NULL; + ObjectAttributes.SecurityDescriptor = NULL; + ObjectAttributes.SecurityQualityOfService = NULL; + + if ( bInheritHandle == TRUE ) + ObjectAttributes.Attributes = OBJ_INHERIT; + else + ObjectAttributes.Attributes = 0; + + errCode = NtOpenProcess ( &ProcessHandle, dwDesiredAccess, &ObjectAttributes, &ClientId); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return NULL; + } + return ProcessHandle; } @@ -420,7 +395,6 @@ UINT WinExec ( LPCSTR lpCmdLine, UINT uCmdShow ) } - VOID RegisterWaitForInputIdle(WaitForInputIdleType lpfnRegisterWaitForInputIdle) { lpfnGlobalRegisterWaitForInputIdle = lpfnRegisterWaitForInputIdle; @@ -454,11 +428,10 @@ SleepEx( BOOL bAlertable ) { - TIME Interval; + LARGE_INTEGER Interval; NTSTATUS errCode; + SET_LARGE_INTEGER_LOW_PART(Interval,dwMilliseconds*1000); - Interval.LowPart = dwMilliseconds * 1000; - Interval.HighPart = 0; errCode = NtDelayExecution(bAlertable,&Interval); if ( !NT_SUCCESS(errCode) ) { SetLastError(RtlNtStatusToDosError(errCode)); @@ -485,8 +458,8 @@ GetStartupInfoW( } lpStartupInfo->cb = sizeof(STARTUPINFO); - lstrcpyW(lpStartupInfo->lpDesktop, pPeb->StartupInfo->Desktop); - lstrcpyW(lpStartupInfo->lpTitle, pPeb->StartupInfo->Title); + lstrcpyW(lpStartupInfo->lpDesktop,(WCHAR *) pPeb->StartupInfo->Desktop); + lstrcpyW(lpStartupInfo->lpTitle, (WCHAR *)pPeb->StartupInfo->Title); lpStartupInfo->dwX = pPeb->StartupInfo->dwX; lpStartupInfo->dwY = pPeb->StartupInfo->dwY; lpStartupInfo->dwXSize = pPeb->StartupInfo->dwXSize; @@ -532,7 +505,7 @@ GetStartupInfoA( while ((pPeb->StartupInfo->Desktop[i])!=0 && i < MAX_PATH) { - lpStartupInfo->lpDesktop[i] = (unsigned char)pPeb->StartupInfo->Desktop[i]; + lpStartupInfo->lpDesktop[i] = (char)pPeb->StartupInfo->Desktop[i]; i++; } lpStartupInfo->lpDesktop[i] = 0; @@ -540,7 +513,7 @@ GetStartupInfoA( i = 0; while ((pPeb->StartupInfo->Title[i])!=0 && i < MAX_PATH) { - lpStartupInfo->lpTitle[i] = (unsigned char)pPeb->StartupInfo->Title[i]; + lpStartupInfo->lpTitle[i] = (char)pPeb->StartupInfo->Title[i]; i++; } lpStartupInfo->lpTitle[i] = 0; @@ -584,9 +557,18 @@ FlushInstructionCache( return TRUE; } -VOID STDCALL ExitProcess(UINT uExitCode) -{ - NtTerminateProcess(NtCurrentProcess() ,uExitCode); +VOID +STDCALL +ExitProcess( + UINT uExitCode + ) +{ + + NtTerminateProcess( + NtCurrentProcess() , + uExitCode + ); + } VOID @@ -623,3 +605,33 @@ FatalAppExitW( } +HMODULE +STDCALL +GetModuleHandleA( + LPCSTR lpModuleName + ) +{ + if ( lpModuleName == NULL ) + return 0x00010000; // starting address of current module + else + return NULL; // should return the address of the specified module + + return NULL; + +} + +HMODULE +STDCALL +GetModuleHandleW( + LPCWSTR lpModuleName + ) +{ + if ( lpModuleName == NULL ) + return 0x00010000; // starting address of current module + else + return NULL; // should return the address of the specified module + + return NULL; +} + + diff --git a/reactos/lib/kernel32/thread/thread.c b/reactos/lib/kernel32/thread/thread.c index 68e44d7b633..a6e47ef9628 100644 --- a/reactos/lib/kernel32/thread/thread.c +++ b/reactos/lib/kernel32/thread/thread.c @@ -1,372 +1,362 @@ -/* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS system libraries - * FILE: lib/kernel32/thread/thread.c - * PURPOSE: Thread functions - * PROGRAMMER: Ariadne ( ariadne@xs4all.nl) - Tls functions are modified from WINE - * UPDATE HISTORY: - * Created 01/11/98 - */ - -#include -#include -#include -#include -#include - -HANDLE -STDCALL -CreateThread( - LPSECURITY_ATTRIBUTES lpThreadAttributes, - DWORD dwStackSize, - LPTHREAD_START_ROUTINE lpStartAddress, - LPVOID lpParameter, - DWORD dwCreationFlags, - LPDWORD lpThreadId - ) -{ - return CreateRemoteThread(NtCurrentProcess(),lpThreadAttributes,dwStackSize, - lpStartAddress,lpParameter,dwCreationFlags,lpThreadId); -} - - - - -HANDLE -STDCALL -CreateRemoteThread( - HANDLE hProcess, - LPSECURITY_ATTRIBUTES lpThreadAttributes, - DWORD dwStackSize, - LPTHREAD_START_ROUTINE lpStartAddress, - LPVOID lpParameter, - DWORD dwCreationFlags, - LPDWORD lpThreadId - ) -{ - NTSTATUS errCode; - HANDLE ThreadHandle; - OBJECT_ATTRIBUTES ObjectAttributes; - CLIENT_ID ClientId; - CONTEXT ThreadContext; - INITIAL_TEB InitialTeb; - BOOLEAN CreateSuspended = FALSE; - ULONG BaseAddress; - - ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); - ObjectAttributes.RootDirectory = NULL; - ObjectAttributes.ObjectName = NULL; - ObjectAttributes.Attributes = 0; - if ( lpThreadAttributes != NULL ) { - if ( lpThreadAttributes->bInheritHandle ) - ObjectAttributes.Attributes = OBJ_INHERIT; - ObjectAttributes.SecurityDescriptor = lpThreadAttributes->lpSecurityDescriptor; - } - ObjectAttributes.SecurityQualityOfService = NULL; - - if ( ( dwCreationFlags & CREATE_SUSPENDED ) == CREATE_SUSPENDED ) - CreateSuspended = TRUE; - else - CreateSuspended = FALSE; - - BaseAddress = 0; - ZwAllocateVirtualMemory(hProcess, - &BaseAddress, - 0, - &dwStackSize, - MEM_COMMIT, - PAGE_READWRITE); - - - memset(&ThreadContext,0,sizeof(CONTEXT)); - ThreadContext.Eip = lpStartAddress; - ThreadContext.SegGs = USER_DS; - ThreadContext.SegFs = USER_DS; - ThreadContext.SegEs = USER_DS; - ThreadContext.SegDs = USER_DS; - ThreadContext.SegCs = USER_CS; - ThreadContext.SegSs = USER_DS; - ThreadContext.Esp = BaseAddress + dwStackSize; - ThreadContext.EFlags = (1<<1) + (1<<9); - - - errCode = NtCreateThread(&ThreadHandle, - THREAD_ALL_ACCESS, - &ObjectAttributes, - hProcess, - &ClientId, - &ThreadContext, - &InitialTeb, - CreateSuspended); - if ( lpThreadId != NULL ) - memcpy(lpThreadId, &ClientId.UniqueThread,sizeof(ULONG)); - - return ThreadHandle; -} - -NT_TEB *GetTeb(VOID) -{ - return NULL; -} - -WINBOOL STDCALL SwitchToThread(VOID ) -{ - NTSTATUS errCode; - errCode = NtYieldExecution(); - return TRUE; -} - -DWORD STDCALL GetCurrentThreadId() -{ - - return (DWORD)(GetTeb()->Cid).UniqueThread; -} - -VOID STDCALL ExitThread(UINT uExitCode) -{ - NTSTATUS errCode; - - errCode = NtTerminateThread( - NtCurrentThread() , - uExitCode - ); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - } - return; -} - -WINBOOL -STDCALL -GetThreadTimes( - HANDLE hThread, - LPFILETIME lpCreationTime, - LPFILETIME lpExitTime, - LPFILETIME lpKernelTime, - LPFILETIME lpUserTime - ) -{ - NTSTATUS errCode; - KERNEL_USER_TIMES KernelUserTimes; - ULONG ReturnLength; - errCode = NtQueryInformationThread(hThread,ThreadTimes,&KernelUserTimes,sizeof(KERNEL_USER_TIMES),&ReturnLength); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - memcpy(lpCreationTime, &KernelUserTimes.CreateTime, sizeof(FILETIME)); - memcpy(lpExitTime, &KernelUserTimes.ExitTime, sizeof(FILETIME)); - memcpy(lpKernelTime, &KernelUserTimes.KernelTime, sizeof(FILETIME)); - memcpy(lpUserTime, &KernelUserTimes.UserTime, sizeof(FILETIME)); - return TRUE; - -} - - -WINBOOL -STDCALL GetThreadContext( - HANDLE hThread, - LPCONTEXT lpContext - ) -{ - NTSTATUS errCode; - errCode = NtGetContextThread(hThread,lpContext); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - return TRUE; -} - -WINBOOL -STDCALL -SetThreadContext( - HANDLE hThread, - CONST CONTEXT *lpContext - ) -{ - NTSTATUS errCode; - - errCode = NtSetContextThread(hThread,(void *)lpContext); - if (!NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - return TRUE; -} - - - -WINBOOL -STDCALL -GetExitCodeThread( - HANDLE hThread, - LPDWORD lpExitCode - ) -{ - NTSTATUS errCode; - THREAD_BASIC_INFORMATION ThreadBasic; - ULONG DataWritten; - errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - memcpy( lpExitCode ,&ThreadBasic.ExitStatus,sizeof(DWORD)); - return TRUE; - -} - - -DWORD -STDCALL -ResumeThread( - HANDLE hThread - ) -{ - NTSTATUS errCode; - ULONG PreviousResumeCount; - - errCode = NtResumeThread(hThread,&PreviousResumeCount ); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return -1; - } - return PreviousResumeCount; -} - -DWORD -STDCALL -SuspendThread( - HANDLE hThread - ) -{ - NTSTATUS errCode; - ULONG PreviousSuspendCount; - - errCode = NtSuspendThread(hThread,&PreviousSuspendCount ); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return -1; - } - return PreviousSuspendCount; -} - - -DWORD -STDCALL -SetThreadAffinityMask( - HANDLE hThread, - DWORD dwThreadAffinityMask - ) -{ - return 0; -} - - -WINBOOL -STDCALL -SetThreadPriority( - HANDLE hThread, - int nPriority - ) -{ - NTSTATUS errCode; - THREAD_BASIC_INFORMATION ThreadBasic; - ULONG DataWritten; - errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - ThreadBasic.BasePriority = nPriority; - errCode = NtSetInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION)); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return FALSE; - } - return TRUE; -} - - -int -STDCALL -GetThreadPriority( - HANDLE hThread - ) -{ - NTSTATUS errCode; - THREAD_BASIC_INFORMATION ThreadBasic; - ULONG DataWritten; - errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); - if ( !NT_SUCCESS(errCode) ) { - SetLastError(RtlNtStatusToDosError(errCode)); - return THREAD_PRIORITY_ERROR_RETURN; - } - return ThreadBasic.BasePriority; -} - - -/* (WIN32) Thread Local Storage ******************************************** */ - -DWORD STDCALL -TlsAlloc(VOID) -{ - DWORD dwTlsIndex = GetTeb()->dwTlsIndex; - - - void **TlsData = GetTeb()->TlsData; - - - if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) - { - TlsData[dwTlsIndex] = NULL; - return (dwTlsIndex++); - } - return (0xFFFFFFFFUL); -} - -WINBOOL STDCALL -TlsFree(DWORD dwTlsIndex) -{ - - return (TRUE); -} - -LPVOID STDCALL -TlsGetValue(DWORD dwTlsIndex) -{ - - - void **TlsData = GetTeb()->TlsData; - - - if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) - { - - SetLastError(NO_ERROR); - return (TlsData[dwTlsIndex]); - } - SetLastError(1); - return (NULL); -} - -WINBOOL STDCALL -TlsSetValue(DWORD dwTlsIndex, LPVOID lpTlsValue) -{ - - - void **TlsData = GetTeb()->TlsData; - - - if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) - { - - TlsData[dwTlsIndex] = lpTlsValue; - return (TRUE); - } - return (FALSE); -} - -/*************************************************************/ +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * FILE: lib/kernel32/thread/thread.c + * PURPOSE: Thread functions + * PROGRAMMER: Ariadne ( ariadne@xs4all.nl) + Tls functions are modified from WINE + * UPDATE HISTORY: + * Created 01/11/98 + */ + +#include +#include +#include +#include + + +HANDLE +STDCALL +CreateThread( + LPSECURITY_ATTRIBUTES lpThreadAttributes, + DWORD dwStackSize, + LPTHREAD_START_ROUTINE lpStartAddress, + LPVOID lpParameter, + DWORD dwCreationFlags, + LPDWORD lpThreadId + ) +{ + return CreateRemoteThread(NtCurrentProcess(),lpThreadAttributes,dwStackSize, + lpStartAddress,lpParameter,dwCreationFlags,lpThreadId); +} + + + + +HANDLE +STDCALL +CreateRemoteThread( + HANDLE hProcess, + LPSECURITY_ATTRIBUTES lpThreadAttributes, + DWORD dwStackSize, + LPTHREAD_START_ROUTINE lpStartAddress, + LPVOID lpParameter, + DWORD dwCreationFlags, + LPDWORD lpThreadId + ) +{ + NTSTATUS errCode; + HANDLE ThreadHandle; + OBJECT_ATTRIBUTES ObjectAttributes; + CLIENT_ID ClientId; + CONTEXT ThreadContext; + INITIAL_TEB InitialTeb; + BOOLEAN CreateSuspended = FALSE; + + ObjectAttributes.Length = sizeof(OBJECT_ATTRIBUTES); + ObjectAttributes.RootDirectory = NULL; + ObjectAttributes.ObjectName = NULL; + ObjectAttributes.Attributes = 0; + if ( lpThreadAttributes != NULL ) { + if ( lpThreadAttributes->bInheritHandle ) + ObjectAttributes.Attributes = OBJ_INHERIT; + ObjectAttributes.SecurityDescriptor = lpThreadAttributes->lpSecurityDescriptor; + } + ObjectAttributes.SecurityQualityOfService = NULL; + + if ( ( dwCreationFlags & CREATE_SUSPENDED ) == CREATE_SUSPENDED ) + CreateSuspended = TRUE; + else + CreateSuspended = FALSE; + // fix context + GetThreadContext(NtCurrentThread(),&ThreadContext); + // fix teb [ stack context ] --> check the image file + + errCode = NtCreateThread( + &ThreadHandle, + THREAD_ALL_ACCESS, + &ObjectAttributes, + hProcess, + &ClientId, + &ThreadContext, + &InitialTeb, + CreateSuspended + ); + if ( lpThreadId != NULL ) + memcpy(lpThreadId, &ClientId.UniqueThread,sizeof(ULONG)); + + return ThreadHandle; +} + +NT_TEB *GetTeb(VOID) +{ + return NULL; +} + +WINBOOL STDCALL +SwitchToThread(VOID ) +{ + NTSTATUS errCode; + errCode = NtYieldExecution(); + return TRUE; +} + +DWORD +STDCALL +GetCurrentThreadId() +{ + + return (DWORD)(GetTeb()->Cid).UniqueThread; +} + +VOID +STDCALL +ExitThread( + UINT uExitCode + ) +{ + NTSTATUS errCode; + + errCode = NtTerminateThread( + NtCurrentThread() , + uExitCode + ); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + } + return; +} + +WINBOOL +STDCALL +GetThreadTimes( + HANDLE hThread, + LPFILETIME lpCreationTime, + LPFILETIME lpExitTime, + LPFILETIME lpKernelTime, + LPFILETIME lpUserTime + ) +{ + NTSTATUS errCode; + KERNEL_USER_TIMES KernelUserTimes; + ULONG ReturnLength; + errCode = NtQueryInformationThread(hThread,ThreadTimes,&KernelUserTimes,sizeof(KERNEL_USER_TIMES),&ReturnLength); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + memcpy(lpCreationTime, &KernelUserTimes.CreateTime, sizeof(FILETIME)); + memcpy(lpExitTime, &KernelUserTimes.ExitTime, sizeof(FILETIME)); + memcpy(lpKernelTime, &KernelUserTimes.KernelTime, sizeof(FILETIME)); + memcpy(lpUserTime, &KernelUserTimes.UserTime, sizeof(FILETIME)); + return TRUE; + +} + + +WINBOOL +STDCALL GetThreadContext( + HANDLE hThread, + LPCONTEXT lpContext + ) +{ + NTSTATUS errCode; + errCode = NtGetContextThread(hThread,lpContext); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + return TRUE; +} + +WINBOOL +STDCALL +SetThreadContext( + HANDLE hThread, + CONST CONTEXT *lpContext + ) +{ + NTSTATUS errCode; + + errCode = NtSetContextThread(hThread,(void *)lpContext); + if (!NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + return TRUE; +} + + + +WINBOOL +STDCALL +GetExitCodeThread( + HANDLE hThread, + LPDWORD lpExitCode + ) +{ + NTSTATUS errCode; + THREAD_BASIC_INFORMATION ThreadBasic; + ULONG DataWritten; + errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + memcpy( lpExitCode ,&ThreadBasic.ExitStatus,sizeof(DWORD)); + return TRUE; + +} + + +DWORD +STDCALL +ResumeThread( + HANDLE hThread + ) +{ + NTSTATUS errCode; + ULONG PreviousResumeCount; + + errCode = NtResumeThread(hThread,&PreviousResumeCount ); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return -1; + } + return PreviousResumeCount; +} + +DWORD +STDCALL +SuspendThread( + HANDLE hThread + ) +{ + NTSTATUS errCode; + ULONG PreviousSuspendCount; + + errCode = NtSuspendThread(hThread,&PreviousSuspendCount ); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return -1; + } + return PreviousSuspendCount; +} + + +DWORD +STDCALL +SetThreadAffinityMask( + HANDLE hThread, + DWORD dwThreadAffinityMask + ) +{ + return 0; +} + + +WINBOOL +STDCALL +SetThreadPriority( + HANDLE hThread, + int nPriority + ) +{ + NTSTATUS errCode; + THREAD_BASIC_INFORMATION ThreadBasic; + ULONG DataWritten; + errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + ThreadBasic.BasePriority = nPriority; + errCode = NtSetInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION)); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return FALSE; + } + return TRUE; +} + + +int +STDCALL +GetThreadPriority( + HANDLE hThread + ) +{ + NTSTATUS errCode; + THREAD_BASIC_INFORMATION ThreadBasic; + ULONG DataWritten; + errCode = NtQueryInformationThread(hThread,ThreadBasicInformation,&ThreadBasic,sizeof(THREAD_BASIC_INFORMATION),&DataWritten); + if ( !NT_SUCCESS(errCode) ) { + SetLastError(RtlNtStatusToDosError(errCode)); + return THREAD_PRIORITY_ERROR_RETURN; + } + return ThreadBasic.BasePriority; +} + + +/* (WIN32) Thread Local Storage ******************************************** */ + +DWORD STDCALL +TlsAlloc(VOID) +{ + DWORD dwTlsIndex = GetTeb()->dwTlsIndex; + + + void **TlsData = GetTeb()->TlsData; + + + if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) + { + TlsData[dwTlsIndex] = NULL; + return (dwTlsIndex++); + } + return (0xFFFFFFFFUL); +} + +WINBOOL STDCALL +TlsFree(DWORD dwTlsIndex) +{ + + return (TRUE); +} + +LPVOID STDCALL +TlsGetValue(DWORD dwTlsIndex) +{ + + + void **TlsData = GetTeb()->TlsData; + + + if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) + { + + SetLastError(NO_ERROR); + return (TlsData[dwTlsIndex]); + } + SetLastError(1); + return (NULL); +} + +WINBOOL STDCALL +TlsSetValue(DWORD dwTlsIndex, LPVOID lpTlsValue) +{ + + + void **TlsData = GetTeb()->TlsData; + + + if (dwTlsIndex < sizeof(TlsData) / sizeof(TlsData[0])) + { + + TlsData[dwTlsIndex] = lpTlsValue; + return (TRUE); + } + return (FALSE); +} + +/*************************************************************/ diff --git a/reactos/lib/ntdll/string/wstring.c b/reactos/lib/ntdll/string/wstring.c index 2057bf5ab68..a730920ef6b 100644 --- a/reactos/lib/ntdll/string/wstring.c +++ b/reactos/lib/ntdll/string/wstring.c @@ -488,7 +488,7 @@ UNIMPLEMENTED; #endif -unsigned long wstrlen(PWSTR s) +size_t wstrlen(const wchar_t *s) { return wcslen(s); } diff --git a/reactos/makedisk.bat b/reactos/makedisk.bat new file mode 100644 index 00000000000..53336a2998f --- /dev/null +++ b/reactos/makedisk.bat @@ -0,0 +1,11 @@ +@echo off +echo copying latest files to a:... +copy /Y bootflop.bat a:\autoexec.bat +copy /Y loaders\dos\loadros.com a: +copy /Y apps\shell\shell.bin a: +copy /Y ntoskrnl\kimage.bin a: +copy /Y services\dd\blue\blues.o a: +copy /Y services\dd\keyboard\keyboard.o a: +copy /Y services\dd\ide\ide.o a: +copy /Y services\fs\vfat\vfatfsd.o a: + diff --git a/reactos/makefile.dos b/reactos/makefile.dos index cf9fba3a4ae..a9730eb4f23 100644 --- a/reactos/makefile.dos +++ b/reactos/makefile.dos @@ -30,7 +30,7 @@ LOADERS = dos # # Select the device drivers and filesystems you want # -KERNEL_SERVICES = parallel keyboard null mouse serial sound ide test sdisk \ +KERNEL_SERVICES = parallel keyboard blues null mouse serial sound ide test sdisk \ minix vfat APPS = hello shell @@ -73,7 +73,6 @@ minix: dummy template: dummy make -C services/fs/template - ide-test: dummy make -C services/dd/ide-test @@ -95,6 +94,9 @@ parallel: dummy keyboard: dummy make -C services/dd/keyboard +blues: dummy + make -C services/dd/blue + mouse: dummy make -C services/dd/mouse diff --git a/reactos/makefile_rex b/reactos/makefile_rex index 7ccf186e183..68e76f53bf2 100644 --- a/reactos/makefile_rex +++ b/reactos/makefile_rex @@ -30,8 +30,8 @@ LOADERS = dos # # Select the device drivers and filesystems you want # -KERNEL_SERVICES = parallel keyboard null mouse serial sound ide test sdisk \ - minix vfat ext2 +KERNEL_SERVICES = parallel keyboard blues null mouse serial sound ide test sdisk \ + minix vfat # ext2fs APPS = hello shell @@ -95,6 +95,9 @@ parallel: dummy keyboard: dummy make -C services/dd/keyboard +blues: dummy + make -C services/dd/blue + mouse: dummy make -C services/dd/mouse @@ -104,8 +107,8 @@ serial: dummy sound: dummy make -C services/dd/sound -ext2: dummy - make -C services/fs/ext2 +ext2fs: dummy + make -C services/fs/ext2fs # # Kernel loaders diff --git a/reactos/ntoskrnl/exports.lst b/reactos/ntoskrnl/exports.lst index 61e28f77fff..b81051c8c0d 100644 --- a/reactos/ntoskrnl/exports.lst +++ b/reactos/ntoskrnl/exports.lst @@ -7,6 +7,11 @@ # # # +__putchar +__goxy +__wherex +__wherey +__getscreensize free_page get_dma_page DbgPrint diff --git a/reactos/ntoskrnl/hal/x86/printk.c b/reactos/ntoskrnl/hal/x86/printk.c index 9142f8d7062..380cbcd3979 100644 --- a/reactos/ntoskrnl/hal/x86/printk.c +++ b/reactos/ntoskrnl/hal/x86/printk.c @@ -160,7 +160,7 @@ void HalDisplayString(char* string) printk("%s",string); } -static void putchar(char c) +void __putchar(char c) /* * FUNCTION: Writes a character to the console and updates the cursor position * ARGUMENTS: @@ -281,7 +281,7 @@ asmlinkage void printk(const char* fmt, ...) while ((*str)!=0) { - putchar(*str); + __putchar(*str); str++; } @@ -324,7 +324,7 @@ ULONG DbgPrint(PCH Format, ...) while ((*str)!=0) { - putchar(*str); + __putchar(*str); str++; } @@ -357,3 +357,30 @@ void HalInitConsole(boot_param* bp) cursorx=bp->cursorx; cursory=bp->cursory; } + + +void __goxy(unsigned x, unsigned y) +{ + + cursorx = x; + cursory = y; + +} + +unsigned __wherex (void) +{ + return cursorx; +} + + +unsigned __wherey (void) +{ + return cursory; +} + +void __getscreensize (unsigned *maxx, unsigned *maxy) +{ + + *maxx = (unsigned)(NR_COLUMNS); + *maxy = (unsigned)(NR_ROWS); +} diff --git a/reactos/ntoskrnl/io/create.c b/reactos/ntoskrnl/io/create.c index cd70ab3db29..844e8b6a910 100644 --- a/reactos/ntoskrnl/io/create.c +++ b/reactos/ntoskrnl/io/create.c @@ -136,6 +136,8 @@ NTSTATUS ZwCreateFile(PHANDLE FileHandle, FileObject->FileName.Buffer = ExAllocatePool(NonPagedPool, ObjectAttributes->ObjectName->Length); FileObject->FileName.Length = ObjectAttributes->ObjectName->Length; + FileObject->FileName.MaximumLength = + ObjectAttributes->ObjectName->MaximumLength; RtlCopyUnicodeString(&(FileObject->FileName), ObjectAttributes->ObjectName); } diff --git a/reactos/ntoskrnl/io/fs.c b/reactos/ntoskrnl/io/fs.c index 151679376e2..b95be9c2c91 100644 --- a/reactos/ntoskrnl/io/fs.c +++ b/reactos/ntoskrnl/io/fs.c @@ -13,7 +13,7 @@ #include #include -#define NDEBUG +//#define NDEBUG #include /* TYPES *******************************************************************/ @@ -35,7 +35,7 @@ NTSTATUS STDCALL NtFsControlFile( IN HANDLE DeviceHandle, - IN HANDLE Event OPTIONAL, + IN HANDLE EventHandle OPTIONAL, IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, IN PVOID ApcContext OPTIONAL, OUT PIO_STATUS_BLOCK IoStatusBlock, @@ -47,7 +47,7 @@ NtFsControlFile( ) { return(ZwFsControlFile(DeviceHandle, - Event, + EventHandle, ApcRoutine, ApcContext, IoStatusBlock, @@ -62,7 +62,7 @@ NTSTATUS STDCALL ZwFsControlFile( IN HANDLE DeviceHandle, - IN HANDLE Event OPTIONAL, + IN HANDLE EventHandle OPTIONAL, IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, IN PVOID ApcContext OPTIONAL, OUT PIO_STATUS_BLOCK IoStatusBlock, @@ -73,7 +73,88 @@ ZwFsControlFile( IN ULONG OutputBufferSize ) { - UNIMPLEMENTED; + NTSTATUS Status = -1; + PFILE_OBJECT FileObject; + PIRP Irp; + PIO_STACK_LOCATION StackPtr; + KEVENT Event; + + + if ( InputBufferSize > 0 ) { + + Status = ObReferenceObjectByHandle(DeviceHandle, + FILE_WRITE_DATA|FILE_READ_DATA, + NULL, + UserMode, + (PVOID *) &FileObject, + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + KeInitializeEvent(&Event,NotificationEvent,FALSE); + Irp = IoBuildSynchronousFsdRequest(IRP_MJ_DEVICE_CONTROL, + FileObject->DeviceObject, + InputBuffer, + InputBufferSize, + 0, + &Event, + IoStatusBlock); + StackPtr = IoGetNextIrpStackLocation(Irp); + if ( StackPtr == NULL ) + return -1; + StackPtr->Parameters.DeviceIoControl.IoControlCode = IoControlCode; + StackPtr->FileObject = FileObject; + StackPtr->Parameters.Write.Length = InputBufferSize; + DPRINT("FileObject->DeviceObject %x\n",FileObject->DeviceObject); + Status = IoCallDriver(FileObject->DeviceObject,Irp); + if (Status==STATUS_PENDING && (FileObject->Flags & FO_SYNCHRONOUS_IO)) + { + KeWaitForSingleObject(&Event,Executive,KernelMode,FALSE,NULL); + return Irp->IoStatus.Status; + } + } + + if ( OutputBufferSize > 0 ) { + CHECKPOINT; + Status = ObReferenceObjectByHandle(DeviceHandle, + FILE_WRITE_DATA|FILE_READ_DATA, + NULL, + UserMode, + (PVOID *) &FileObject, + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + CHECKPOINT; + KeInitializeEvent(&Event,NotificationEvent,FALSE); + CHECKPOINT; + Irp = IoBuildSynchronousFsdRequest(IRP_MJ_DEVICE_CONTROL, + FileObject->DeviceObject, + OutputBuffer, + OutputBufferSize, + 0, + &Event, + IoStatusBlock); + CHECKPOINT; + StackPtr = IoGetNextIrpStackLocation(Irp); + if ( StackPtr == NULL ) + return -1; + StackPtr->Parameters.DeviceIoControl.IoControlCode = IoControlCode; + StackPtr->FileObject = FileObject; + StackPtr->Parameters.Read.Length = OutputBufferSize; + DPRINT("FileObject->DeviceObject %x\n",FileObject->DeviceObject); + Status = IoCallDriver(FileObject->DeviceObject,Irp); + if (Status==STATUS_PENDING && (FileObject->Flags & FO_SYNCHRONOUS_IO)) + { + KeWaitForSingleObject(&Event,Executive,KernelMode,FALSE,NULL); + return Irp->IoStatus.Status; + } + } + CHECKPOINT; + return(Status); } VOID IoInitFileSystemImplementation(VOID) @@ -155,9 +236,7 @@ NTSTATUS IoTryToMountStorageDevice(PDEVICE_OBJECT DeviceObject) current_entry = current_entry->Flink; } } -CHECKPOINT; KeReleaseSpinLock(&FileSystemListLock,oldlvl); -CHECKPOINT; return(STATUS_UNRECOGNIZED_VOLUME); } diff --git a/reactos/ntoskrnl/io/symlink.c b/reactos/ntoskrnl/io/symlink.c index d7b4d90fc6d..19f2e9682fd 100644 --- a/reactos/ntoskrnl/io/symlink.c +++ b/reactos/ntoskrnl/io/symlink.c @@ -159,12 +159,13 @@ NTSTATUS IoCreateSymbolicLink(PUNICODE_STRING SymbolicLinkName, return(STATUS_UNSUCCESSFUL); } - SymbolicLink->TargetName.Buffer = ExAllocatePool(NonPagedPool, - ((wstrlen(DeviceName->Buffer)+1)*2)); - SymbolicLink->TargetName.MaximumLength = wstrlen(DeviceName->Buffer); SymbolicLink->TargetName.Length = 0; - RtlCopyUnicodeString(&(SymbolicLink->TargetName),DeviceName); - DPRINT("DeviceName %w\n",SymbolicLink->TargetName.Buffer); + SymbolicLink->TargetName.MaximumLength = + ((wstrlen(DeviceName->Buffer) + 1) * sizeof(WCHAR)); + SymbolicLink->TargetName.Buffer = ExAllocatePool(NonPagedPool, + SymbolicLink->TargetName.MaximumLength); + RtlCopyUnicodeString(&(SymbolicLink->TargetName), DeviceName); + DPRINT("DeviceName %w\n", SymbolicLink->TargetName.Buffer); InitializeObjectAttributes(&(SymbolicLink->Target), &(SymbolicLink->TargetName),0,NULL,NULL); DPRINT("%s() = STATUS_SUCCESS\n",__FUNCTION__); diff --git a/reactos/ntoskrnl/ke/main.c b/reactos/ntoskrnl/ke/main.c index 606d6002ee7..ce99a6073ea 100644 --- a/reactos/ntoskrnl/ke/main.c +++ b/reactos/ntoskrnl/ke/main.c @@ -1,356 +1,185 @@ /* - * 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 - - #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"); - } - - extern int edata; - extern int end; - - 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; - unsigned int start1; - boot_param bp; - - memset((void *)&edata,0,((int)&end)-((int)&edata)); - - /* - * Copy the parameters to a local buffer because lowmem will go away - */ - memcpy(&bp,_bp,sizeof(boot_param)); - - /* - * Initalize the console (before printing anything) - */ - HalInitConsole(&bp); - - DbgPrint("Starting ReactOS "KERNEL_VERSION"\n"); - - start = KERNEL_BASE + PAGE_ROUND_UP(bp.module_length[0]); - if (start < ((int)&end)) - { - DbgPrint("start %x end %x\n",start,(int)&end); - DbgPrint("Kernel booted incorrectly, aborting\n"); - DbgPrint("Reduce the amount of uninitialized data\n"); - for(;;); - } - start1 = start+PAGE_ROUND_UP(bp.module_length[1]); - - - /* - * Initalize various critical subsystems - */ - HalInit(&bp); - MmInitialize(&bp); - KeInit(); - ObInit(); - PsInit(); - IoInit(); - + LdrInitModuleManagement(); - /* - * Initalize services loaded at boot time - */ - DPRINT("%d files loaded\n",bp.nr_files); - - start = KERNEL_BASE + PAGE_ROUND_UP(bp.module_length[0]); - start1 = start+PAGE_ROUND_UP(bp.module_length[1]); - for (i=1;i -//#define NDEBUG +#define NDEBUG #include /* MACROS ********************************************************************/ @@ -36,6 +36,7 @@ POBJECT_TYPE ObModuleType = NULL; /* FORWARD DECLARATIONS ******************************************************/ +NTSTATUS LdrLoadDriver(PUNICODE_STRING Filename); NTSTATUS LdrProcessDriver(PVOID ModuleLoadBase); /* PE Driver load support */ @@ -58,7 +59,7 @@ static NTSTATUS LdrProcessBinImage(HANDLE ProcessHandle, HANDLE ModuleHandle, HA /* FUNCTIONS *****************************************************************/ -VOID LdrInitModuleManagment(VOID) +VOID LdrInitModuleManagement(VOID) { ANSI_STRING AnsiString; @@ -82,6 +83,36 @@ VOID LdrInitModuleManagment(VOID) RtlAnsiStringToUnicodeString(&ObModuleType->TypeName, &AnsiString, TRUE); } +/* + * load the auto config drivers. + */ +VOID LdrLoadAutoConfigDrivers(VOID) +{ + NTSTATUS Status; + ANSI_STRING AnsiDriverName; + UNICODE_STRING DriverName; + + RtlInitAnsiString(&AnsiDriverName,"\\??\\C:\\reactos\\system\\drivers\\keyboard.o"); + RtlAnsiStringToUnicodeString(&DriverName, &AnsiDriverName, TRUE); + Status = LdrLoadDriver(&DriverName); + RtlFreeUnicodeString(&DriverName); + if (!NT_SUCCESS(Status)) + { + DbgPrint("driver load failed, status;%d(%x)\n", Status, Status); + DbgPrintErrorMessage(Status); + } + RtlInitAnsiString(&AnsiDriverName,"\\??\\C:\\reactos\\system\\drivers\\blues.o"); + RtlAnsiStringToUnicodeString(&DriverName, &AnsiDriverName, TRUE); + Status = LdrLoadDriver(&DriverName); + RtlFreeUnicodeString(&DriverName); + if (!NT_SUCCESS(Status)) + { + DbgPrint("driver load failed, status;%d(%x)\n", Status, Status); + DbgPrintErrorMessage(Status); + } + +} + /* * FUNCTION: Loads a kernel driver * ARGUMENTS: diff --git a/reactos/ntoskrnl/mm/virtual.c b/reactos/ntoskrnl/mm/virtual.c index 5c0485b83c5..686ec728f79 100644 --- a/reactos/ntoskrnl/mm/virtual.c +++ b/reactos/ntoskrnl/mm/virtual.c @@ -1,746 +1,747 @@ -/* - * COPYRIGHT: See COPYING in the top directory - * PROJECT: ReactOS kernel - * FILE: ntoskrnl/mm/virtual.c - * 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) - * 30/9/98: Implemented ZwxxxVirtualMemory functions - */ - -/* INCLUDE *****************************************************************/ - -#include - -#include -#include -#include -#include -#include -#include - -#define NDEBUG -#include - -/* TYPES *******************************************************************/ - -extern unsigned int etext; -extern unsigned int end; - -static MEMORY_AREA* kernel_text_desc = NULL; -static MEMORY_AREA* kernel_data_desc = NULL; -static MEMORY_AREA* kernel_param_desc = NULL; -static MEMORY_AREA* kernel_pool_desc = NULL; - -/* 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; - PVOID BaseAddress; - ULONG Length; - ULONG ParamLength = kernel_len; - - DPRINT("VirtualInit() %x\n",bp); - - MmInitMemoryAreas(); - ExInitNonPagedPool(KERNEL_BASE+ PAGE_ROUND_UP(kernel_len) + PAGESIZE); - - - /* - * Setup the system area descriptor list - */ - BaseAddress = (PVOID)KERNEL_BASE; - Length = PAGE_ROUND_UP(((ULONG)&etext)) - KERNEL_BASE; - ParamLength = ParamLength - Length; - MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, - Length,0,&kernel_text_desc); - - Length = PAGE_ROUND_UP(((ULONG)&end)) - PAGE_ROUND_UP(((ULONG)&etext)); - ParamLength = ParamLength - Length; - DPRINT("Length %x\n",Length); - BaseAddress = (PVOID)PAGE_ROUND_UP(((ULONG)&etext)); - MmCreateMemoryArea(KernelMode, - NULL, - MEMORY_AREA_SYSTEM, - &BaseAddress, - Length, - 0, - &kernel_data_desc); - - - BaseAddress = (PVOID)PAGE_ROUND_UP(((ULONG)&end)); - Length = ParamLength; - MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, - Length,0,&kernel_param_desc); - - BaseAddress = (PVOID)(KERNEL_BASE + PAGE_ROUND_UP(kernel_len) + PAGESIZE); - Length = NONPAGED_POOL_SIZE; - MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, - Length,0,&kernel_pool_desc); - -// MmDumpMemoryAreas(); - CHECKPOINT; - - MmInitSectionImplementation(); -} - -ULONG MmCommitedSectionHandleFault(MEMORY_AREA* MemoryArea, ULONG Address) -{ - set_page(Address,0x7,get_free_page()); - return(TRUE); -} - -NTSTATUS MmSectionHandleFault(MEMORY_AREA* MemoryArea, PVOID Address) -{ - LARGE_INTEGER Offset; - IO_STATUS_BLOCK IoStatus; - - DPRINT("MmSectionHandleFault(MemoryArea %x, Address %x)\n", - MemoryArea,Address); - - set_page((DWORD)Address,0x7,get_free_page()); - - LARGE_INTEGER_QUAD_PART(Offset) = (Address - MemoryArea->BaseAddress) + - MemoryArea->Data.SectionData.ViewOffset; - - DPRINT("MemoryArea->Data.SectionData.Section->FileObject %x\n", - MemoryArea->Data.SectionData.Section->FileObject); - - if (MemoryArea->Data.SectionData.Section->FileObject == NULL) - { - return(STATUS_UNSUCCESSFUL); - } - - IoPageRead(MemoryArea->Data.SectionData.Section->FileObject, - (PVOID)Address, - &Offset, - &IoStatus); - - DPRINT("Returning from MmSectionHandleFault()\n"); - - return(STATUS_SUCCESS); -} - -asmlinkage int page_fault_handler(unsigned int cs, - unsigned int eip) -/* - * FUNCTION: Handle a page fault - */ -{ - KPROCESSOR_MODE FaultMode; - MEMORY_AREA* MemoryArea; - KIRQL oldlvl; - ULONG stat; - - /* - * 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); - - if (KeGetCurrentIrql()!=PASSIVE_LEVEL) - { - DbgPrint("Recursive page fault detected\n"); - return(0); -// KeBugCheck(0); - } - - KeRaiseIrql(DISPATCH_LEVEL,&oldlvl); - - /* - * 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); - } - FaultMode = UserMode; - } - else - { - FaultMode = KernelMode; - } - - MemoryArea = MmOpenMemoryAreaByAddress(PsGetCurrentProcess(),(PVOID)cr2); - if (MemoryArea==NULL) - { - printk("%s:%d\n",__FILE__,__LINE__); - return(0); - } - - switch (MemoryArea->Type) - { - case MEMORY_AREA_SYSTEM: - stat = 0; - break; - - case MEMORY_AREA_SECTION_VIEW_COMMIT: - if (MmSectionHandleFault(MemoryArea, (PVOID)cr2)==STATUS_SUCCESS) - { - stat=1; - } - else - { - stat = 0; - } - break; - - case MEMORY_AREA_COMMIT: - stat = MmCommitedSectionHandleFault(MemoryArea,cr2); - break; - - default: - stat = 0; - break; - } - if (stat) - { - KeLowerIrql(oldlvl); - } - return(stat); -} - -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* MemoryArea; - - MemoryArea = MmOpenMemoryAreaByAddress(PsGetCurrentProcess(), - VirtualAddress); - - if (MemoryArea == NULL) - { - return(FALSE); - } - return(TRUE); -} - -NTSTATUS -STDCALL -NtAllocateVirtualMemory( - IN HANDLE ProcessHandle, - IN OUT PVOID *BaseAddress, - IN ULONG ZeroBits, - IN OUT PULONG RegionSize, - IN ULONG AllocationType, - IN ULONG Protect - ) -{ - return(ZwAllocateVirtualMemory(ProcessHandle, - BaseAddress, - ZeroBits, - RegionSize, - AllocationType, - Protect)); -} - -NTSTATUS -STDCALL -ZwAllocateVirtualMemory( - IN HANDLE ProcessHandle, - IN OUT PVOID *BaseAddress, - IN ULONG ZeroBits, - IN OUT PULONG RegionSize, - IN ULONG AllocationType, - IN ULONG Protect - ) -/* - * FUNCTION: Allocates a block of virtual memory in the process address space - * ARGUMENTS: - * ProcessHandle = The handle of the process which owns the virtual memory - * BaseAddress = A pointer to the virtual memory allocated. If you - * supply a non zero value the system will try to - * allocate the memory at the address supplied. It round - * it down to a multiple of the page size. - * ZeroBits = (OPTIONAL) You can specify the number of high order bits - * that must be zero, ensuring that the memory will be - * allocated at a address below a certain value. - * RegionSize = The number of bytes to allocate - * AllocationType = Indicates the type of virtual memory you like to - * allocated, can be one of the values : MEM_COMMIT, - * MEM_RESERVE, MEM_RESET, MEM_TOP_DOWN - * Protect = Indicates the protection type of the pages allocated, can be - * a combination of PAGE_READONLY, PAGE_READWRITE, - * PAGE_EXECUTE_READ, PAGE_EXECUTE_READWRITE, PAGE_GUARD, - * PAGE_NOACCESS - * REMARKS: - * This function maps to the win32 VirtualAllocEx. Virtual memory is - * process based so the protocol starts with a ProcessHandle. I - * splitted the functionality of obtaining the actual address and - * specifying the start address in two parameters ( BaseAddress and - * StartAddress ) The NumberOfBytesAllocated specify the range and the - * AllocationType and ProctectionType map to the other two parameters. - * RETURNS: Status - */ -{ - PEPROCESS Process; - MEMORY_AREA* MemoryArea; - ULONG Type; - NTSTATUS Status; - - DPRINT("ZwAllocateVirtualMemory(ProcessHandle %x, *BaseAddress %x, " - "ZeroBits %d, RegionSize %d, AllocationType %x, Protect %x)\n", - ProcessHandle,*BaseAddress,ZeroBits,*RegionSize,AllocationType, - Protect); - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_VM_OPERATION, - NULL, - UserMode, - (PVOID*)(&Process), - NULL); - if (Status != STATUS_SUCCESS) - { - DPRINT("ZwAllocateVirtualMemory() = %x\n",Status); - return(Status); - } - - if (AllocationType & MEM_RESERVE) - { - Type = MEMORY_AREA_RESERVE; - } - else - { - Type = MEMORY_AREA_COMMIT; - } - - if ((*BaseAddress) != 0) - { - MemoryArea = MmOpenMemoryAreaByAddress(Process, *BaseAddress); - - if (MemoryArea != NULL) - { - if (MemoryArea->BaseAddress == (*BaseAddress) && - MemoryArea->Length == *RegionSize) - { - MemoryArea->Type = Type; - MemoryArea->Attributes =Protect; - DPRINT("*BaseAddress %x\n",*BaseAddress); - return(STATUS_SUCCESS); - } - - MemoryArea = MmSplitMemoryArea(Process, - MemoryArea, - *BaseAddress, - *RegionSize, - Type, - Protect); - DPRINT("*BaseAddress %x\n",*BaseAddress); - return(STATUS_SUCCESS); - } - } - - //FIXME RegionSize should be passed as pointer - - - Status = MmCreateMemoryArea(UserMode, - Process, - Type, - BaseAddress, - *RegionSize, - Protect, - &MemoryArea); - - if (Status != STATUS_SUCCESS) - { - DPRINT("ZwAllocateVirtualMemory() = %x\n",Status); - return(Status); - } - - DPRINT("*BaseAddress %x\n",*BaseAddress); - - return(STATUS_SUCCESS); -} - -NTSTATUS STDCALL NtFlushVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN ULONG NumberOfBytesToFlush, - OUT PULONG NumberOfBytesFlushed OPTIONAL) -{ - return(ZwFlushVirtualMemory(ProcessHandle, - BaseAddress, - NumberOfBytesToFlush, - NumberOfBytesFlushed)); -} - -NTSTATUS STDCALL ZwFlushVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN ULONG NumberOfBytesToFlush, - OUT PULONG NumberOfBytesFlushed OPTIONAL) - -/* - * FUNCTION: Flushes virtual memory to file - * ARGUMENTS: - * ProcessHandle = Points to the process that allocated the virtual - * memory - * BaseAddress = Points to the memory address - * NumberOfBytesToFlush = Limits the range to flush, - * NumberOfBytesFlushed = Actual number of bytes flushed - * RETURNS: Status - */ -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtFreeVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID *BaseAddress, - IN PULONG RegionSize, - IN ULONG FreeType) -{ - return(ZwFreeVirtualMemory(ProcessHandle, - BaseAddress, - RegionSize, - FreeType)); -} - -NTSTATUS STDCALL ZwFreeVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID *BaseAddress, - IN PULONG RegionSize, - IN ULONG FreeType) - -/* - * FUNCTION: Frees a range of virtual memory - * ARGUMENTS: - * ProcessHandle = Points to the process that allocated the virtual - * memory - * BaseAddress = Points to the memory address, rounded down to a - * multiple of the pagesize - * RegionSize = Limits the range to free, rounded up to a multiple of - * the paging size - * FreeType = Can be one of the values: MEM_DECOMMIT, or MEM_RELEASE - * RETURNS: Status - */ -{ - MEMORY_AREA* MemoryArea; - NTSTATUS Status; - PEPROCESS Process; - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_VM_OPERATION, - PsProcessType, - UserMode, - (PVOID*)(&Process), - NULL); - if (Status != STATUS_SUCCESS) - { - DbgPrint("ZwFreeVirtualMemory() = %x\n",Status); - return(Status); - } - - MemoryArea = MmOpenMemoryAreaByAddress(Process,*BaseAddress); - if (MemoryArea == NULL) - { - return(STATUS_UNSUCCESSFUL); - } - - if (FreeType == MEM_RELEASE) - { - if (MemoryArea->BaseAddress != (*BaseAddress)) - { - return(STATUS_UNSUCCESSFUL); - } - MmFreeMemoryArea(PsGetCurrentProcess(), - BaseAddress, - 0, - TRUE); - return(STATUS_SUCCESS); - } - - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtLockVirtualMemory(HANDLE ProcessHandle, - PVOID BaseAddress, - ULONG NumberOfBytesToLock, - PULONG NumberOfBytesLocked) -{ - return(ZwLockVirtualMemory(ProcessHandle, - BaseAddress, - NumberOfBytesToLock, - NumberOfBytesLocked)); -} - -NTSTATUS STDCALL ZwLockVirtualMemory(HANDLE ProcessHandle, - PVOID BaseAddress, - ULONG NumberOfBytesToLock, - PULONG NumberOfBytesLocked) -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtProtectVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN ULONG NumberOfBytesToProtect, - IN ULONG NewAccessProtection, - OUT PULONG OldAccessProtection) -{ - return(ZwProtectVirtualMemory(ProcessHandle, - BaseAddress, - NumberOfBytesToProtect, - NewAccessProtection, - OldAccessProtection)); -} - -VOID MmChangeAreaProtection(PEPROCESS Process, - PVOID BaseAddress, - ULONG Length, - ULONG Protect) -{ - ULONG i; - - for (i=0; i<(Length/PAGESIZE); i++) - { - if (MmIsPagePresent(Process, BaseAddress + (i*PAGESIZE))) - { - MmSetPageProtect(Process, BaseAddress + (i*PAGESIZE), Protect); - } - } -} - -NTSTATUS STDCALL ZwProtectVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN ULONG NumberOfBytesToProtect, - IN ULONG NewAccessProtection, - OUT PULONG OldAccessProtection) -{ - PMEMORY_AREA MemoryArea; - PEPROCESS Process; - NTSTATUS Status; - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_VM_OPERATION, - PsProcessType, - UserMode, - (PVOID*)(&Process), - NULL); - if (Status != STATUS_SUCCESS) - { - DbgPrint("ZwProtectVirtualMemory() = %x\n",Status); - return(Status); - } - - MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); - if (MemoryArea == NULL) - { - DbgPrint("ZwProtectVirtualMemory() = %x\n",STATUS_UNSUCCESSFUL); - return(STATUS_UNSUCCESSFUL); - } - - *OldAccessProtection = MemoryArea->Attributes; - - if (MemoryArea->BaseAddress == BaseAddress && - MemoryArea->Length == NumberOfBytesToProtect) - { - MemoryArea->Attributes = NewAccessProtection; - } - else - { - MemoryArea = MmSplitMemoryArea(Process, - MemoryArea, - BaseAddress, - NumberOfBytesToProtect, - MemoryArea->Type, - NewAccessProtection); - } - MmChangeAreaProtection(Process,BaseAddress,NumberOfBytesToProtect, - NewAccessProtection); - return(STATUS_SUCCESS); -} - - -NTSTATUS STDCALL NtQueryVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID Address, - IN IN CINT VirtualMemoryInformationClass, - OUT PVOID VirtualMemoryInformation, - IN ULONG Length, - OUT PULONG ResultLength) -{ - return(ZwQueryVirtualMemory(ProcessHandle, - Address, - VirtualMemoryInformationClass, - VirtualMemoryInformation, - Length, - ResultLength)); -} - -NTSTATUS STDCALL ZwQueryVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID Address, - IN CINT VirtualMemoryInformationClass, - OUT PVOID VirtualMemoryInformation, - IN ULONG Length, - OUT PULONG ResultLength) -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtReadVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - OUT PVOID Buffer, - IN ULONG NumberOfBytesToRead, - OUT PULONG NumberOfBytesRead) -{ - return(ZwReadVirtualMemory(ProcessHandle, - BaseAddress, - Buffer, - NumberOfBytesToRead, - NumberOfBytesRead)); -} - -NTSTATUS STDCALL ZwReadVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - OUT PVOID Buffer, - IN ULONG NumberOfBytesToRead, - OUT PULONG NumberOfBytesRead) -{ - PEPROCESS Process; - MEMORY_AREA* MemoryArea; - ULONG i; - NTSTATUS Status; - PULONG CurrentEntry; - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_VM_READ, - NULL, - UserMode, - (PVOID*)(&Process), - NULL); - if (Status != STATUS_SUCCESS) - { - return(Status); - } - - MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); - - if (MemoryArea == NULL) - { - return(STATUS_UNSUCCESSFUL); - } - if (MemoryArea->Length > NumberOfBytesToRead) - { - NumberOfBytesToRead = MemoryArea->Length; - } - - *NumberOfBytesRead = NumberOfBytesToRead; - - for (i=0; i<(NumberOfBytesToRead/PAGESIZE); i++) - { - CurrentEntry = MmGetPageEntry(Process, (DWORD)BaseAddress + (i*PAGESIZE)); - RtlCopyMemory(Buffer + (i*PAGESIZE), - (PVOID)physical_to_linear(PAGE_MASK(*CurrentEntry)), - PAGESIZE); - - } - return(STATUS_SUCCESS); -} - -NTSTATUS STDCALL NtUnlockVirtualMemory(HANDLE ProcessHandle, - PVOID BaseAddress, - ULONG NumberOfBytesToUnlock, - PULONG NumberOfBytesUnlocked OPTIONAL) -{ - return(ZwUnlockVirtualMemory(ProcessHandle, - BaseAddress, - NumberOfBytesToUnlock, - NumberOfBytesUnlocked)); -} - -NTSTATUS STDCALL ZwUnlockVirtualMemory(HANDLE ProcessHandle, - PVOID BaseAddress, - ULONG NumberOfBytesToUnlock, - PULONG NumberOfBytesUnlocked OPTIONAL) -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtWriteVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN PVOID Buffer, - IN ULONG NumberOfBytesToWrite, - OUT PULONG NumberOfBytesWritten) -{ - return(ZwWriteVirtualMemory(ProcessHandle, - BaseAddress, - Buffer, - NumberOfBytesToWrite, - NumberOfBytesWritten)); -} - -NTSTATUS STDCALL ZwWriteVirtualMemory(IN HANDLE ProcessHandle, - IN PVOID BaseAddress, - IN PVOID Buffer, - IN ULONG NumberOfBytesToWrite, - OUT PULONG NumberOfBytesWritten) -{ - PEPROCESS Process; - MEMORY_AREA* MemoryArea; - ULONG i; - NTSTATUS Status; - PULONG CurrentEntry; - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_VM_WRITE, - NULL, - UserMode, - (PVOID*)(&Process), - NULL); - if (Status != STATUS_SUCCESS) - { - return(Status); - } - - MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); - - if (MemoryArea == NULL) - { - return(STATUS_UNSUCCESSFUL); - } - if (MemoryArea->Length > NumberOfBytesToWrite) - { - NumberOfBytesToWrite = MemoryArea->Length; - } - - *NumberOfBytesWritten = NumberOfBytesToWrite; - - for (i=0; i<(NumberOfBytesToWrite/PAGESIZE); i++) - { - CurrentEntry = MmGetPageEntry(Process, (DWORD)BaseAddress + (i*PAGESIZE)); - RtlCopyMemory((PVOID)physical_to_linear(PAGE_MASK(*CurrentEntry)), - Buffer + (i*PAGESIZE), - PAGESIZE); - - } - return(STATUS_SUCCESS); -} - +/* + * COPYRIGHT: See COPYING in the top directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/mm/virtual.c + * 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) + * 30/9/98: Implemented ZwxxxVirtualMemory functions + */ + +/* INCLUDE *****************************************************************/ + +#include + +#include +#include +#include +#include +#include +#include + +#define NDEBUG +#include + +/* TYPES *******************************************************************/ + +extern unsigned int etext; +extern unsigned int end; + +static MEMORY_AREA* kernel_text_desc = NULL; +static MEMORY_AREA* kernel_data_desc = NULL; +static MEMORY_AREA* kernel_param_desc = NULL; +static MEMORY_AREA* kernel_pool_desc = NULL; + +/* 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; + PVOID BaseAddress; + ULONG Length; + ULONG ParamLength = kernel_len; + + DPRINT("VirtualInit() %x\n",bp); + + MmInitMemoryAreas(); + ExInitNonPagedPool(KERNEL_BASE+ PAGE_ROUND_UP(kernel_len) + PAGESIZE); + + + /* + * Setup the system area descriptor list + */ + BaseAddress = (PVOID)KERNEL_BASE; + Length = PAGE_ROUND_UP(((ULONG)&etext)) - KERNEL_BASE; + ParamLength = ParamLength - Length; + MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, + Length,0,&kernel_text_desc); + + Length = PAGE_ROUND_UP(((ULONG)&end)) - PAGE_ROUND_UP(((ULONG)&etext)); + ParamLength = ParamLength - Length; + DPRINT("Length %x\n",Length); + BaseAddress = (PVOID)PAGE_ROUND_UP(((ULONG)&etext)); + MmCreateMemoryArea(KernelMode, + NULL, + MEMORY_AREA_SYSTEM, + &BaseAddress, + Length, + 0, + &kernel_data_desc); + + + BaseAddress = (PVOID)PAGE_ROUND_UP(((ULONG)&end)); + Length = ParamLength; + MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, + Length,0,&kernel_param_desc); + + BaseAddress = (PVOID)(KERNEL_BASE + PAGE_ROUND_UP(kernel_len) + PAGESIZE); + Length = NONPAGED_POOL_SIZE; + MmCreateMemoryArea(KernelMode,NULL,MEMORY_AREA_SYSTEM,&BaseAddress, + Length,0,&kernel_pool_desc); + +// MmDumpMemoryAreas(); + CHECKPOINT; + + MmInitSectionImplementation(); +} + +ULONG MmCommitedSectionHandleFault(MEMORY_AREA* MemoryArea, ULONG Address) +{ + set_page(Address,0x7,get_free_page()); + return(TRUE); +} + +NTSTATUS MmSectionHandleFault(MEMORY_AREA* MemoryArea, PVOID Address) +{ + LARGE_INTEGER Offset; + IO_STATUS_BLOCK IoStatus; + + DPRINT("MmSectionHandleFault(MemoryArea %x, Address %x)\n", + MemoryArea,Address); + + set_page((DWORD)Address,0x7,get_free_page()); + + LARGE_INTEGER_QUAD_PART(Offset) = (Address - MemoryArea->BaseAddress) + + MemoryArea->Data.SectionData.ViewOffset; + + DPRINT("MemoryArea->Data.SectionData.Section->FileObject %x\n", + MemoryArea->Data.SectionData.Section->FileObject); + + if (MemoryArea->Data.SectionData.Section->FileObject == NULL) + { + return(STATUS_UNSUCCESSFUL); + } + + IoPageRead(MemoryArea->Data.SectionData.Section->FileObject, + (PVOID)Address, + &Offset, + &IoStatus); + + DPRINT("Returning from MmSectionHandleFault()\n"); + + return(STATUS_SUCCESS); +} + +asmlinkage int page_fault_handler(unsigned int cs, + unsigned int eip) +/* + * FUNCTION: Handle a page fault + */ +{ + KPROCESSOR_MODE FaultMode; + MEMORY_AREA* MemoryArea; + KIRQL oldlvl; + ULONG stat; + + /* + * 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); + + if (KeGetCurrentIrql()!=PASSIVE_LEVEL) + { + DbgPrint("Recursive page fault detected\n"); + return(0); +// KeBugCheck(0); + } + + KeRaiseIrql(DISPATCH_LEVEL,&oldlvl); + + /* + * 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); + } + FaultMode = UserMode; + } + else + { + FaultMode = KernelMode; + } + + MemoryArea = MmOpenMemoryAreaByAddress(PsGetCurrentProcess(),(PVOID)cr2); + if (MemoryArea==NULL) + { + printk("%s:%d\n",__FILE__,__LINE__); + return(0); + } + + switch (MemoryArea->Type) + { + case MEMORY_AREA_SYSTEM: + stat = 0; + break; + + case MEMORY_AREA_SECTION_VIEW_COMMIT: + if (MmSectionHandleFault(MemoryArea, (PVOID)cr2)==STATUS_SUCCESS) + { + stat=1; + } + else + { + stat = 0; + } + break; + + case MEMORY_AREA_COMMIT: + stat = MmCommitedSectionHandleFault(MemoryArea,cr2); + break; + + default: + stat = 0; + break; + } + if (stat) + { + KeLowerIrql(oldlvl); + } + return(stat); +} + +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* MemoryArea; + + MemoryArea = MmOpenMemoryAreaByAddress(PsGetCurrentProcess(), + VirtualAddress); + + if (MemoryArea == NULL) + { + return(FALSE); + } + return(TRUE); +} + +NTSTATUS +STDCALL +NtAllocateVirtualMemory( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG ZeroBits, + IN OUT PULONG RegionSize, + IN ULONG AllocationType, + IN ULONG Protect + ) +{ + return(ZwAllocateVirtualMemory(ProcessHandle, + BaseAddress, + ZeroBits, + RegionSize, + AllocationType, + Protect)); +} + +NTSTATUS +STDCALL +ZwAllocateVirtualMemory( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG ZeroBits, + IN OUT PULONG RegionSize, + IN ULONG AllocationType, + IN ULONG Protect + ) +/* + * FUNCTION: Allocates a block of virtual memory in the process address space + * ARGUMENTS: + * ProcessHandle = The handle of the process which owns the virtual memory + * BaseAddress = A pointer to the virtual memory allocated. If you + * supply a non zero value the system will try to + * allocate the memory at the address supplied. It round + * it down to a multiple of the page size. + * ZeroBits = (OPTIONAL) You can specify the number of high order bits + * that must be zero, ensuring that the memory will be + * allocated at a address below a certain value. + * RegionSize = The number of bytes to allocate + * AllocationType = Indicates the type of virtual memory you like to + * allocated, can be one of the values : MEM_COMMIT, + * MEM_RESERVE, MEM_RESET, MEM_TOP_DOWN + * Protect = Indicates the protection type of the pages allocated, can be + * a combination of PAGE_READONLY, PAGE_READWRITE, + * PAGE_EXECUTE_READ, PAGE_EXECUTE_READWRITE, PAGE_GUARD, + * PAGE_NOACCESS + * REMARKS: + * This function maps to the win32 VirtualAllocEx. Virtual memory is + * process based so the protocol starts with a ProcessHandle. I + * splitted the functionality of obtaining the actual address and + * specifying the start address in two parameters ( BaseAddress and + * StartAddress ) The NumberOfBytesAllocated specify the range and the + * AllocationType and ProctectionType map to the other two parameters. + * RETURNS: Status + */ +{ + PEPROCESS Process; + MEMORY_AREA* MemoryArea; + ULONG Type; + NTSTATUS Status; + + DPRINT("ZwAllocateVirtualMemory(ProcessHandle %x, *BaseAddress %x, " + "ZeroBits %d, RegionSize %d, AllocationType %x, Protect %x)\n", + ProcessHandle,*BaseAddress,ZeroBits,*RegionSize,AllocationType, + Protect); + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_VM_OPERATION, + NULL, + UserMode, + (PVOID*)(&Process), + NULL); + if (Status != STATUS_SUCCESS) + { + DPRINT("ZwAllocateVirtualMemory() = %x\n",Status); + return(Status); + } + + if (AllocationType & MEM_RESERVE) + { + Type = MEMORY_AREA_RESERVE; + } + else + { + Type = MEMORY_AREA_COMMIT; + } + + if ((*BaseAddress) != 0) + { + MemoryArea = MmOpenMemoryAreaByAddress(Process, *BaseAddress); + + if (MemoryArea != NULL) + { + if (MemoryArea->BaseAddress == (*BaseAddress) && + MemoryArea->Length == *RegionSize) + { + MemoryArea->Type = Type; + MemoryArea->Attributes =Protect; + DPRINT("*BaseAddress %x\n",*BaseAddress); + return(STATUS_SUCCESS); + } + + MemoryArea = MmSplitMemoryArea(Process, + MemoryArea, + *BaseAddress, + *RegionSize, + Type, + Protect); + DPRINT("*BaseAddress %x\n",*BaseAddress); + return(STATUS_SUCCESS); + } + } + + //FIXME RegionSize should be passed as pointer + + + Status = MmCreateMemoryArea(UserMode, + Process, + Type, + BaseAddress, + *RegionSize, + Protect, + &MemoryArea); + + if (Status != STATUS_SUCCESS) + { + DPRINT("ZwAllocateVirtualMemory() = %x\n",Status); + return(Status); + } + + DPRINT("*BaseAddress %x\n",*BaseAddress); + + return(STATUS_SUCCESS); +} + +NTSTATUS STDCALL NtFlushVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN ULONG NumberOfBytesToFlush, + OUT PULONG NumberOfBytesFlushed OPTIONAL) +{ + return(ZwFlushVirtualMemory(ProcessHandle, + BaseAddress, + NumberOfBytesToFlush, + NumberOfBytesFlushed)); +} + +NTSTATUS STDCALL ZwFlushVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN ULONG NumberOfBytesToFlush, + OUT PULONG NumberOfBytesFlushed OPTIONAL) + +/* + * FUNCTION: Flushes virtual memory to file + * ARGUMENTS: + * ProcessHandle = Points to the process that allocated the virtual + * memory + * BaseAddress = Points to the memory address + * NumberOfBytesToFlush = Limits the range to flush, + * NumberOfBytesFlushed = Actual number of bytes flushed + * RETURNS: Status + */ +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtFreeVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID *BaseAddress, + IN PULONG RegionSize, + IN ULONG FreeType) +{ + return(ZwFreeVirtualMemory(ProcessHandle, + BaseAddress, + RegionSize, + FreeType)); +} + +NTSTATUS STDCALL ZwFreeVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID *BaseAddress, + IN PULONG RegionSize, + IN ULONG FreeType) + +/* + * FUNCTION: Frees a range of virtual memory + * ARGUMENTS: + * ProcessHandle = Points to the process that allocated the virtual + * memory + * BaseAddress = Points to the memory address, rounded down to a + * multiple of the pagesize + * RegionSize = Limits the range to free, rounded up to a multiple of + * the paging size + * FreeType = Can be one of the values: MEM_DECOMMIT, or MEM_RELEASE + * RETURNS: Status + */ +{ + MEMORY_AREA* MemoryArea; + NTSTATUS Status; + PEPROCESS Process; + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_VM_OPERATION, + PsProcessType, + UserMode, + (PVOID*)(&Process), + NULL); + if (Status != STATUS_SUCCESS) + { + DbgPrint("ZwFreeVirtualMemory() = %x\n",Status); + return(Status); + } + + MemoryArea = MmOpenMemoryAreaByAddress(Process,*BaseAddress); + if (MemoryArea == NULL) + { + return(STATUS_UNSUCCESSFUL); + } + + if (FreeType == MEM_RELEASE) + { + if (MemoryArea->BaseAddress != (*BaseAddress)) + { + return(STATUS_UNSUCCESSFUL); + } + MmFreeMemoryArea(PsGetCurrentProcess(), + BaseAddress, + 0, + TRUE); + return(STATUS_SUCCESS); + } + + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtLockVirtualMemory(HANDLE ProcessHandle, + PVOID BaseAddress, + ULONG NumberOfBytesToLock, + PULONG NumberOfBytesLocked) +{ + return(ZwLockVirtualMemory(ProcessHandle, + BaseAddress, + NumberOfBytesToLock, + NumberOfBytesLocked)); +} + +NTSTATUS STDCALL ZwLockVirtualMemory(HANDLE ProcessHandle, + PVOID BaseAddress, + ULONG NumberOfBytesToLock, + PULONG NumberOfBytesLocked) +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtProtectVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN ULONG NumberOfBytesToProtect, + IN ULONG NewAccessProtection, + OUT PULONG OldAccessProtection) +{ + return(ZwProtectVirtualMemory(ProcessHandle, + BaseAddress, + NumberOfBytesToProtect, + NewAccessProtection, + OldAccessProtection)); +} + +VOID MmChangeAreaProtection(PEPROCESS Process, + PVOID BaseAddress, + ULONG Length, + ULONG Protect) +{ + ULONG i; + + for (i=0; i<(Length/PAGESIZE); i++) + { + if (MmIsPagePresent(Process, BaseAddress + (i*PAGESIZE))) + { + MmSetPageProtect(Process, BaseAddress + (i*PAGESIZE), Protect); + } + } +} + +NTSTATUS STDCALL ZwProtectVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN ULONG NumberOfBytesToProtect, + IN ULONG NewAccessProtection, + OUT PULONG OldAccessProtection) +{ + PMEMORY_AREA MemoryArea; + PEPROCESS Process; + NTSTATUS Status; + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_VM_OPERATION, + PsProcessType, + UserMode, + (PVOID*)(&Process), + NULL); + if (Status != STATUS_SUCCESS) + { + DbgPrint("ZwProtectVirtualMemory() = %x\n",Status); + return(Status); + } + + MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); + if (MemoryArea == NULL) + { + DbgPrint("ZwProtectVirtualMemory() = %x\n",STATUS_UNSUCCESSFUL); + return(STATUS_UNSUCCESSFUL); + } + + *OldAccessProtection = MemoryArea->Attributes; + + if (MemoryArea->BaseAddress == BaseAddress && + MemoryArea->Length == NumberOfBytesToProtect) + { + MemoryArea->Attributes = NewAccessProtection; + } + else + { + MemoryArea = MmSplitMemoryArea(Process, + MemoryArea, + BaseAddress, + NumberOfBytesToProtect, + MemoryArea->Type, + NewAccessProtection); + } + MmChangeAreaProtection(Process,BaseAddress,NumberOfBytesToProtect, + NewAccessProtection); + return(STATUS_SUCCESS); +} + + +NTSTATUS STDCALL NtQueryVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID Address, + IN IN CINT VirtualMemoryInformationClass, + OUT PVOID VirtualMemoryInformation, + IN ULONG Length, + OUT PULONG ResultLength) +{ + return(ZwQueryVirtualMemory(ProcessHandle, + Address, + VirtualMemoryInformationClass, + VirtualMemoryInformation, + Length, + ResultLength)); +} + +NTSTATUS STDCALL ZwQueryVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID Address, + IN CINT VirtualMemoryInformationClass, + OUT PVOID VirtualMemoryInformation, + IN ULONG Length, + OUT PULONG ResultLength) +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtReadVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + OUT PVOID Buffer, + IN ULONG NumberOfBytesToRead, + OUT PULONG NumberOfBytesRead) +{ + return(ZwReadVirtualMemory(ProcessHandle, + BaseAddress, + Buffer, + NumberOfBytesToRead, + NumberOfBytesRead)); +} + +NTSTATUS STDCALL ZwReadVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + OUT PVOID Buffer, + IN ULONG NumberOfBytesToRead, + OUT PULONG NumberOfBytesRead) +{ + PEPROCESS Process; + MEMORY_AREA* MemoryArea; + ULONG i; + NTSTATUS Status; + PULONG CurrentEntry; + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_VM_READ, + NULL, + UserMode, + (PVOID*)(&Process), + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); + + if (MemoryArea == NULL) + { + return(STATUS_UNSUCCESSFUL); + } + if (MemoryArea->Length > NumberOfBytesToRead) + { + NumberOfBytesToRead = MemoryArea->Length; + } + + *NumberOfBytesRead = NumberOfBytesToRead; + + for (i=0; i<(NumberOfBytesToRead/PAGESIZE); i++) + { + CurrentEntry = MmGetPageEntry(Process, (DWORD)BaseAddress + (i*PAGESIZE)); + RtlCopyMemory(Buffer + (i*PAGESIZE), + (PVOID)physical_to_linear(PAGE_MASK(*CurrentEntry)), + PAGESIZE); + + } + return(STATUS_SUCCESS); +} + +NTSTATUS STDCALL NtUnlockVirtualMemory(HANDLE ProcessHandle, + PVOID BaseAddress, + ULONG NumberOfBytesToUnlock, + PULONG NumberOfBytesUnlocked OPTIONAL) +{ + return(ZwUnlockVirtualMemory(ProcessHandle, + BaseAddress, + NumberOfBytesToUnlock, + NumberOfBytesUnlocked)); +} + +NTSTATUS STDCALL ZwUnlockVirtualMemory(HANDLE ProcessHandle, + PVOID BaseAddress, + ULONG NumberOfBytesToUnlock, + PULONG NumberOfBytesUnlocked OPTIONAL) +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtWriteVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN PVOID Buffer, + IN ULONG NumberOfBytesToWrite, + OUT PULONG NumberOfBytesWritten) +{ + return(ZwWriteVirtualMemory(ProcessHandle, + BaseAddress, + Buffer, + NumberOfBytesToWrite, + NumberOfBytesWritten)); +} + +NTSTATUS STDCALL ZwWriteVirtualMemory(IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN PVOID Buffer, + IN ULONG NumberOfBytesToWrite, + OUT PULONG NumberOfBytesWritten) +{ + PEPROCESS Process; + MEMORY_AREA* MemoryArea; + ULONG i; + NTSTATUS Status; + PULONG CurrentEntry; + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_VM_WRITE, + NULL, + UserMode, + (PVOID*)(&Process), + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + MemoryArea = MmOpenMemoryAreaByAddress(Process,BaseAddress); + + if (MemoryArea == NULL) + { + return(STATUS_UNSUCCESSFUL); + } + if (MemoryArea->Length > NumberOfBytesToWrite) + { + NumberOfBytesToWrite = MemoryArea->Length; + } + + *NumberOfBytesWritten = NumberOfBytesToWrite; + + for (i=0; i<(NumberOfBytesToWrite/PAGESIZE); i++) + { + CurrentEntry = MmGetPageEntry(Process, (DWORD)BaseAddress + (i*PAGESIZE)); + RtlCopyMemory((PVOID)physical_to_linear(PAGE_MASK(*CurrentEntry)), + Buffer + (i*PAGESIZE), + PAGESIZE); + + } + return(STATUS_SUCCESS); +} + + diff --git a/reactos/ntoskrnl/ob/namespc.c b/reactos/ntoskrnl/ob/namespc.c index c74c8391820..584dc48b04e 100644 --- a/reactos/ntoskrnl/ob/namespc.c +++ b/reactos/ntoskrnl/ob/namespc.c @@ -1,554 +1,555 @@ -/* - * 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 ****************************************************************/ - -POBJECT_TYPE ObDirectoryType = NULL; - -static struct -{ - OBJECT_HEADER hdr; -// DIRECTORY_OBJECT directory; - LIST_ENTRY head; - KSPIN_LOCK Lock; -} namespc_root = {{0,},}; - -/* FUNCTIONS **************************************************************/ - -NTSTATUS NtOpenDirectoryObject(PHANDLE DirectoryHandle, - ACCESS_MASK DesiredAccess, - POBJECT_ATTRIBUTES ObjectAttributes) -{ - return(ZwOpenDirectoryObject(DirectoryHandle, - DesiredAccess, - ObjectAttributes)); -} - -NTSTATUS ZwOpenDirectoryObject(PHANDLE DirectoryHandle, - ACCESS_MASK DesiredAccess, - POBJECT_ATTRIBUTES ObjectAttributes) -/* - * FUNCTION: Opens a namespace directory object - * ARGUMENTS: - * DirectoryHandle (OUT) = Variable which receives the directory handle - * DesiredAccess = Desired access to the directory - * ObjectAttributes = Structure describing the directory - * RETURNS: Status - * NOTES: Undocumented - */ -{ - PVOID Object; - NTSTATUS Status; - PWSTR Ignored; - - *DirectoryHandle = 0; - - Status = ObOpenObjectByName(ObjectAttributes,&Object,&Ignored); - if (!NT_SUCCESS(Status)) - { - return(Status); - } - - if (BODY_TO_HEADER(Object)->Type!=OBJTYP_DIRECTORY) - { - return(STATUS_UNSUCCESSFUL); - } - - *DirectoryHandle = ObInsertHandle(KeGetCurrentProcess(),Object, - DesiredAccess,FALSE); - CHECKPOINT; - return(STATUS_SUCCESS); -} - -NTSTATUS NtQueryDirectoryObject(IN HANDLE DirObjHandle, - OUT POBJDIR_INFORMATION DirObjInformation, - IN ULONG BufferLength, - IN BOOLEAN GetNextIndex, - IN BOOLEAN IgnoreInputIndex, - IN OUT PULONG ObjectIndex, - OUT PULONG DataWritten OPTIONAL) -{ - return(ZwQueryDirectoryObject(DirObjHandle, - DirObjInformation, - BufferLength, - GetNextIndex, - IgnoreInputIndex, - ObjectIndex, - DataWritten)); -} - -NTSTATUS ZwQueryDirectoryObject(IN HANDLE DirObjHandle, - OUT POBJDIR_INFORMATION DirObjInformation, - IN ULONG BufferLength, - IN BOOLEAN GetNextIndex, - IN BOOLEAN IgnoreInputIndex, - IN OUT PULONG ObjectIndex, - OUT PULONG DataWritten OPTIONAL) -/* - * FUNCTION: Reads information from a namespace directory - * ARGUMENTS: - * DirObjInformation (OUT) = Buffer to hold the data read - * BufferLength = Size of the buffer in bytes - * GetNextIndex = If TRUE then set ObjectIndex to the index of the - * next object - * If FALSE then set ObjectIndex to the number of - * objects in the directory - * IgnoreInputIndex = If TRUE start reading at index 0 - * If FALSE start reading at the index specified - * by object index - * ObjectIndex = Zero based index into the directory, interpretation - * depends on IgnoreInputIndex and GetNextIndex - * DataWritten (OUT) = Caller supplied storage for the number of bytes - * written (or NULL) - * RETURNS: Status - */ -{ - PDIRECTORY_OBJECT dir = NULL; - ULONG EntriesToRead; - PLIST_ENTRY current_entry; - POBJECT_HEADER current; - ULONG i=0; - ULONG EntriesToSkip; - NTSTATUS Status; - - DPRINT("ZwQueryDirectoryObject(DirObjHandle %x)\n",DirObjHandle); - DPRINT("dir %x namespc_root %x\n",dir,HEADER_TO_BODY(&(namespc_root.hdr))); - -// assert_irql(PASSIVE_LEVEL); - - Status = ObReferenceObjectByHandle(DirObjHandle, - DIRECTORY_QUERY, - ObDirectoryType, - UserMode, - (PVOID*)&dir, - NULL); - if (Status != STATUS_SUCCESS) - { - return(Status); - } - - EntriesToRead = BufferLength / sizeof(OBJDIR_INFORMATION); - *DataWritten = 0; - - DPRINT("EntriesToRead %d\n",EntriesToRead); - - current_entry = dir->head.Flink; - - /* - * Optionally, skip over some entries at the start of the directory - */ - if (!IgnoreInputIndex) - { - CHECKPOINT; - - EntriesToSkip = *ObjectIndex; - while ( iFlink; - } - } - - DPRINT("DirObjInformation %x\n",DirObjInformation); - - /* - * Read the maximum entries possible into the buffer - */ - while ( ihead))) - { - current = CONTAINING_RECORD(current_entry,OBJECT_HEADER,Entry); - DPRINT("Scanning %w\n",current->Name.Buffer); - DirObjInformation[i].ObjectName.Buffer = - ExAllocatePool(NonPagedPool,(current->Name.Length+1)*2); - DirObjInformation[i].ObjectName.Length = current->Name.Length; - DirObjInformation[i].ObjectName.MaximumLength = current->Name.Length; - DPRINT("DirObjInformation[i].ObjectName.Buffer %x\n", - DirObjInformation[i].ObjectName.Buffer); - RtlCopyUnicodeString(&DirObjInformation[i].ObjectName, - &(current->Name)); - i++; - current_entry = current_entry->Flink; - (*DataWritten) = (*DataWritten) + sizeof(OBJDIR_INFORMATION); - CHECKPOINT; - } - CHECKPOINT; - - /* - * Optionally, count the number of entries in the directory - */ - if (GetNextIndex) - { - *ObjectIndex=i; - } - else - { - while ( current_entry!=(&(dir->head)) ) - { - current_entry=current_entry->Flink; - i++; - } - *ObjectIndex=i; - } - return(STATUS_SUCCESS); -} - - -NTSTATUS ObReferenceObjectByName(PUNICODE_STRING ObjectPath, - ULONG Attributes, - PACCESS_STATE PassedAccessState, - ACCESS_MASK DesiredAccess, - POBJECT_TYPE ObjectType, - KPROCESSOR_MODE AccessMode, - PVOID ParseContext, - PVOID* ObjectPtr) -{ - UNIMPLEMENTED; -} - -NTSTATUS ObOpenObjectByName(POBJECT_ATTRIBUTES ObjectAttributes, - PVOID* Object, PWSTR* UnparsedSection) -{ - NTSTATUS Status; - - DPRINT("ObOpenObjectByName(ObjectAttributes %x, Object %x)\n", - ObjectAttributes,Object); - DPRINT("ObjectAttributes = {ObjectName %x ObjectName->Buffer %w}\n", - ObjectAttributes->ObjectName,ObjectAttributes->ObjectName->Buffer); - DPRINT("ObjectAttributes->ObjectName->Length %d\n", - ObjectAttributes->ObjectName->Length); - - *Object = NULL; - Status = ObLookupObject(ObjectAttributes->RootDirectory, - ObjectAttributes->ObjectName->Buffer, - Object, - UnparsedSection, - ObjectAttributes->Attributes); - DPRINT("*Object %x\n",*Object); - DPRINT("ObjectAttributes->ObjectName->Length %d\n", - ObjectAttributes->ObjectName->Length); - return(Status); -} - -void ObInit(void) -/* - * FUNCTION: Initialize the object manager namespace - */ -{ - ANSI_STRING AnsiString; - - ObDirectoryType = ExAllocatePool(NonPagedPool,sizeof(OBJECT_TYPE)); - - ObDirectoryType->TotalObjects = 0; - ObDirectoryType->TotalHandles = 0; - ObDirectoryType->MaxObjects = ULONG_MAX; - ObDirectoryType->MaxHandles = ULONG_MAX; - ObDirectoryType->PagedPoolCharge = 0; - ObDirectoryType->NonpagedPoolCharge = sizeof(DIRECTORY_OBJECT); - ObDirectoryType->Dump = NULL; - ObDirectoryType->Open = NULL; - ObDirectoryType->Close = NULL; - ObDirectoryType->Delete = NULL; - ObDirectoryType->Parse = NULL; - ObDirectoryType->Security = NULL; - ObDirectoryType->QueryName = NULL; - ObDirectoryType->OkayToClose = NULL; - - RtlInitAnsiString(&AnsiString,"Directory"); - RtlAnsiStringToUnicodeString(&ObDirectoryType->TypeName, - &AnsiString,TRUE); - - ObInitializeObjectHeader(ObDirectoryType,NULL,&namespc_root.hdr); - InitializeListHead(&namespc_root.head); -} - -NTSTATUS NtCreateDirectoryObject(PHANDLE DirectoryHandle, - ACCESS_MASK DesiredAccess, - POBJECT_ATTRIBUTES ObjectAttributes) -{ - return(ZwCreateDirectoryObject(DirectoryHandle, - DesiredAccess, - ObjectAttributes)); -} - -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, - ObDirectoryType); - - /* - * Initialize the object body - */ - InitializeListHead(&dir->head); - KeInitializeSpinLock(&(dir->Lock)); - - return(STATUS_SUCCESS); -} - -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 - */ -{ - DPRINT("InitializeObjectAttributes(InitializedAttributes %x " - "ObjectName %x Attributes %x RootDirectory %x)\n", - InitializedAttributes,ObjectName,Attributes,RootDirectory); - InitializedAttributes->Length=sizeof(OBJECT_ATTRIBUTES); - InitializedAttributes->RootDirectory=RootDirectory; - InitializedAttributes->ObjectName=ObjectName; - InitializedAttributes->Attributes=Attributes; - InitializedAttributes->SecurityDescriptor=SecurityDescriptor; - InitializedAttributes->SecurityQualityOfService=NULL; -} - -static PVOID ObDirLookup(PDIRECTORY_OBJECT dir, PWSTR name, - ULONG Attributes) -/* - * 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 = dir->head.Flink; - POBJECT_HEADER current_obj; - - DPRINT("ObDirLookup(dir %x, name %w)\n",dir,name); - - if (name[0]==0) - { - return(dir); - } - if (name[0]=='.'&&name[1]==0) - { - return(dir); - } - if (name[0]=='.'&&name[1]=='.'&&name[2]==0) - { - return(BODY_TO_HEADER(dir)->Parent); - } - while (current!=(&(dir->head))) - { - current_obj = CONTAINING_RECORD(current,OBJECT_HEADER,Entry); - DPRINT("Scanning %w\n",current_obj->Name.Buffer); - if (Attributes & OBJ_CASE_INSENSITIVE) - { - if (wcsicmp(current_obj->Name.Buffer, name)==0) - { - DPRINT("Found it %x\n",HEADER_TO_BODY(current_obj)); - return(HEADER_TO_BODY(current_obj)); - } - } - else - { - if ( wcscmp(current_obj->Name.Buffer, name)==0) - { - DPRINT("Found it %x\n",HEADER_TO_BODY(current_obj)); - return(HEADER_TO_BODY(current_obj)); - } - } - current = current->Flink; - } - DPRINT("%s() = NULL\n",__FUNCTION__); - return(NULL); -} - -VOID ObRemoveEntry(POBJECT_HEADER Header) -{ - KIRQL oldlvl; - - DPRINT("ObRemoveEntry(Header %x)\n",Header); - - KeAcquireSpinLock(&(Header->Parent->Lock),&oldlvl); - RemoveEntryList(&(Header->Entry)); - KeReleaseSpinLock(&(Header->Parent->Lock),oldlvl); -} - -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); - - /* - * Insert ourselves in our parents list - */ - InsertTailList(&parent->head,&Object->Entry); -} - -NTSTATUS ObLookupObject(HANDLE rootdir, PWSTR string, PVOID* Object, - PWSTR* UnparsedSection, ULONG Attributes) -/* - * 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 = NULL; - NTSTATUS Status; - - DPRINT("ObLookupObject(rootdir %x, string %x, string %w, Object %x, " - "UnparsedSection %x)\n",rootdir,string,string,Object, - UnparsedSection); - - - *UnparsedSection = NULL; - *Object = NULL; - - if (rootdir==NULL) - { - current_dir = HEADER_TO_BODY(&(namespc_root.hdr)); - } - else - { - ObReferenceObjectByHandle(rootdir,DIRECTORY_TRAVERSE,NULL, - UserMode,(PVOID*)¤t_dir,NULL); - } - - /* - * Bit of a hack this - */ - if (string[0]==0) - { - *Object=current_dir; - return(STATUS_SUCCESS); - } - - if (string[0]!='\\') - { - DbgPrint("(%s:%d) Non absolute pathname passed to %s\n",__FILE__, - __LINE__,__FUNCTION__); - return(STATUS_UNSUCCESSFUL); - } - - next = &string[0]; - current = next+1; - - while (next!=NULL && - BODY_TO_HEADER(current_dir)->ObjectType==ObDirectoryType) - { - *next = '\\'; - current = next+1; - next = wcschr(next+1,'\\'); - if (next!=NULL) - { - *next=0; - } - - DPRINT("current %w current[5] %x next %x ",current,current[5],next); - if (next!=NULL) - { - DPRINT("(next+1) %w",next+1); - } - DPRINT("\n",0); - - current_dir=(PDIRECTORY_OBJECT)ObDirLookup(current_dir,current, - Attributes); - if (current_dir==NULL) - { - DbgPrint("(%s:%d) Path component %w not found\n",__FILE__, - __LINE__,current); - return(STATUS_UNSUCCESSFUL); - } - - if (BODY_TO_HEADER(current_dir)->ObjectType==IoSymbolicLinkType) - { - current_dir = IoOpenSymlink(current_dir); - } - - } - DPRINT("next %x\n",next); - DPRINT("current %x current %w\n",current,current); - if (next==NULL) - { - if (current_dir==NULL) - { - Status = STATUS_UNSUCCESSFUL; - } - else - { - Status = STATUS_SUCCESS; - } - } - else - { - CHECKPOINT; - *next = '\\'; - *UnparsedSection = next; - if (BODY_TO_HEADER(current_dir)->ObjectType == IoDeviceType) - { - Status = STATUS_FS_QUERY_REQUIRED; - } - else - { - Status = STATUS_UNSUCCESSFUL; - } - } - CHECKPOINT; - *Object = current_dir; - DPRINT("(%s:%d) current_dir %x\n",__FILE__,__LINE__,current_dir); - - return(Status); -} - +/* + * 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 ****************************************************************/ + +POBJECT_TYPE ObDirectoryType = NULL; + +static struct +{ + OBJECT_HEADER hdr; +// DIRECTORY_OBJECT directory; + LIST_ENTRY head; + KSPIN_LOCK Lock; +} namespc_root = {{0,},}; + +/* FUNCTIONS **************************************************************/ + +NTSTATUS NtOpenDirectoryObject(PHANDLE DirectoryHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes) +{ + return(ZwOpenDirectoryObject(DirectoryHandle, + DesiredAccess, + ObjectAttributes)); +} + +NTSTATUS ZwOpenDirectoryObject(PHANDLE DirectoryHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes) +/* + * FUNCTION: Opens a namespace directory object + * ARGUMENTS: + * DirectoryHandle (OUT) = Variable which receives the directory handle + * DesiredAccess = Desired access to the directory + * ObjectAttributes = Structure describing the directory + * RETURNS: Status + * NOTES: Undocumented + */ +{ + PVOID Object; + NTSTATUS Status; + PWSTR Ignored; + + *DirectoryHandle = 0; + + Status = ObOpenObjectByName(ObjectAttributes,&Object,&Ignored); + if (!NT_SUCCESS(Status)) + { + return(Status); + } + + if (BODY_TO_HEADER(Object)->Type!=OBJTYP_DIRECTORY) + { + return(STATUS_UNSUCCESSFUL); + } + + *DirectoryHandle = ObInsertHandle(KeGetCurrentProcess(),Object, + DesiredAccess,FALSE); + CHECKPOINT; + return(STATUS_SUCCESS); +} + +NTSTATUS NtQueryDirectoryObject(IN HANDLE DirObjHandle, + OUT POBJDIR_INFORMATION DirObjInformation, + IN ULONG BufferLength, + IN BOOLEAN GetNextIndex, + IN BOOLEAN IgnoreInputIndex, + IN OUT PULONG ObjectIndex, + OUT PULONG DataWritten OPTIONAL) +{ + return(ZwQueryDirectoryObject(DirObjHandle, + DirObjInformation, + BufferLength, + GetNextIndex, + IgnoreInputIndex, + ObjectIndex, + DataWritten)); +} + +NTSTATUS ZwQueryDirectoryObject(IN HANDLE DirObjHandle, + OUT POBJDIR_INFORMATION DirObjInformation, + IN ULONG BufferLength, + IN BOOLEAN GetNextIndex, + IN BOOLEAN IgnoreInputIndex, + IN OUT PULONG ObjectIndex, + OUT PULONG DataWritten OPTIONAL) +/* + * FUNCTION: Reads information from a namespace directory + * ARGUMENTS: + * DirObjInformation (OUT) = Buffer to hold the data read + * BufferLength = Size of the buffer in bytes + * GetNextIndex = If TRUE then set ObjectIndex to the index of the + * next object + * If FALSE then set ObjectIndex to the number of + * objects in the directory + * IgnoreInputIndex = If TRUE start reading at index 0 + * If FALSE start reading at the index specified + * by object index + * ObjectIndex = Zero based index into the directory, interpretation + * depends on IgnoreInputIndex and GetNextIndex + * DataWritten (OUT) = Caller supplied storage for the number of bytes + * written (or NULL) + * RETURNS: Status + */ +{ + PDIRECTORY_OBJECT dir = NULL; + ULONG EntriesToRead; + PLIST_ENTRY current_entry; + POBJECT_HEADER current; + ULONG i=0; + ULONG EntriesToSkip; + NTSTATUS Status; + + DPRINT("ZwQueryDirectoryObject(DirObjHandle %x)\n",DirObjHandle); + DPRINT("dir %x namespc_root %x\n",dir,HEADER_TO_BODY(&(namespc_root.hdr))); + +// assert_irql(PASSIVE_LEVEL); + + Status = ObReferenceObjectByHandle(DirObjHandle, + DIRECTORY_QUERY, + ObDirectoryType, + UserMode, + (PVOID*)&dir, + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + EntriesToRead = BufferLength / sizeof(OBJDIR_INFORMATION); + *DataWritten = 0; + + DPRINT("EntriesToRead %d\n",EntriesToRead); + + current_entry = dir->head.Flink; + + /* + * Optionally, skip over some entries at the start of the directory + */ + if (!IgnoreInputIndex) + { + CHECKPOINT; + + EntriesToSkip = *ObjectIndex; + while ( iFlink; + } + } + + DPRINT("DirObjInformation %x\n",DirObjInformation); + + /* + * Read the maximum entries possible into the buffer + */ + while ( ihead))) + { + current = CONTAINING_RECORD(current_entry,OBJECT_HEADER,Entry); + DPRINT("Scanning %w\n",current->Name.Buffer); + DirObjInformation[i].ObjectName.Buffer = + ExAllocatePool(NonPagedPool, current->Name.Length + sizeof(WCHAR)); + DirObjInformation[i].ObjectName.Length = current->Name.Length; + DirObjInformation[i].ObjectName.MaximumLength = current->Name.Length + sizeof(WCHAR); + DPRINT("DirObjInformation[i].ObjectName.Buffer %x\n", + DirObjInformation[i].ObjectName.Buffer); + RtlCopyUnicodeString(&DirObjInformation[i].ObjectName, + &(current->Name)); + i++; + current_entry = current_entry->Flink; + (*DataWritten) = (*DataWritten) + sizeof(OBJDIR_INFORMATION); + CHECKPOINT; + } + CHECKPOINT; + + /* + * Optionally, count the number of entries in the directory + */ + if (GetNextIndex) + { + *ObjectIndex=i; + } + else + { + while ( current_entry!=(&(dir->head)) ) + { + current_entry=current_entry->Flink; + i++; + } + *ObjectIndex=i; + } + return(STATUS_SUCCESS); +} + + +NTSTATUS ObReferenceObjectByName(PUNICODE_STRING ObjectPath, + ULONG Attributes, + PACCESS_STATE PassedAccessState, + ACCESS_MASK DesiredAccess, + POBJECT_TYPE ObjectType, + KPROCESSOR_MODE AccessMode, + PVOID ParseContext, + PVOID* ObjectPtr) +{ + UNIMPLEMENTED; +} + +NTSTATUS ObOpenObjectByName(POBJECT_ATTRIBUTES ObjectAttributes, + PVOID* Object, PWSTR* UnparsedSection) +{ + NTSTATUS Status; + + DPRINT("ObOpenObjectByName(ObjectAttributes %x, Object %x)\n", + ObjectAttributes,Object); + DPRINT("ObjectAttributes = {ObjectName %x ObjectName->Buffer %w}\n", + ObjectAttributes->ObjectName,ObjectAttributes->ObjectName->Buffer); + DPRINT("ObjectAttributes->ObjectName->Length %d\n", + ObjectAttributes->ObjectName->Length); + + *Object = NULL; + Status = ObLookupObject(ObjectAttributes->RootDirectory, + ObjectAttributes->ObjectName->Buffer, + Object, + UnparsedSection, + ObjectAttributes->Attributes); + DPRINT("*Object %x\n",*Object); + DPRINT("ObjectAttributes->ObjectName->Length %d\n", + ObjectAttributes->ObjectName->Length); + return(Status); +} + +void ObInit(void) +/* + * FUNCTION: Initialize the object manager namespace + */ +{ + ANSI_STRING AnsiString; + + ObDirectoryType = ExAllocatePool(NonPagedPool,sizeof(OBJECT_TYPE)); + + ObDirectoryType->TotalObjects = 0; + ObDirectoryType->TotalHandles = 0; + ObDirectoryType->MaxObjects = ULONG_MAX; + ObDirectoryType->MaxHandles = ULONG_MAX; + ObDirectoryType->PagedPoolCharge = 0; + ObDirectoryType->NonpagedPoolCharge = sizeof(DIRECTORY_OBJECT); + ObDirectoryType->Dump = NULL; + ObDirectoryType->Open = NULL; + ObDirectoryType->Close = NULL; + ObDirectoryType->Delete = NULL; + ObDirectoryType->Parse = NULL; + ObDirectoryType->Security = NULL; + ObDirectoryType->QueryName = NULL; + ObDirectoryType->OkayToClose = NULL; + + RtlInitAnsiString(&AnsiString,"Directory"); + RtlAnsiStringToUnicodeString(&ObDirectoryType->TypeName, + &AnsiString,TRUE); + + ObInitializeObjectHeader(ObDirectoryType,NULL,&namespc_root.hdr); + InitializeListHead(&namespc_root.head); +} + +NTSTATUS NtCreateDirectoryObject(PHANDLE DirectoryHandle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes) +{ + return(ZwCreateDirectoryObject(DirectoryHandle, + DesiredAccess, + ObjectAttributes)); +} + +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, + ObDirectoryType); + + /* + * Initialize the object body + */ + InitializeListHead(&dir->head); + KeInitializeSpinLock(&(dir->Lock)); + + return(STATUS_SUCCESS); +} + +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 + */ +{ + DPRINT("InitializeObjectAttributes(InitializedAttributes %x " + "ObjectName %x Attributes %x RootDirectory %x)\n", + InitializedAttributes,ObjectName,Attributes,RootDirectory); + InitializedAttributes->Length=sizeof(OBJECT_ATTRIBUTES); + InitializedAttributes->RootDirectory=RootDirectory; + InitializedAttributes->ObjectName=ObjectName; + InitializedAttributes->Attributes=Attributes; + InitializedAttributes->SecurityDescriptor=SecurityDescriptor; + InitializedAttributes->SecurityQualityOfService=NULL; +} + +static PVOID ObDirLookup(PDIRECTORY_OBJECT dir, PWSTR name, + ULONG Attributes) +/* + * 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 = dir->head.Flink; + POBJECT_HEADER current_obj; + + DPRINT("ObDirLookup(dir %x, name %w)\n",dir,name); + + if (name[0]==0) + { + return(dir); + } + if (name[0]=='.'&&name[1]==0) + { + return(dir); + } + if (name[0]=='.'&&name[1]=='.'&&name[2]==0) + { + return(BODY_TO_HEADER(dir)->Parent); + } + while (current!=(&(dir->head))) + { + current_obj = CONTAINING_RECORD(current,OBJECT_HEADER,Entry); + DPRINT("Scanning %w\n",current_obj->Name.Buffer); + if (Attributes & OBJ_CASE_INSENSITIVE) + { + if (wcsicmp(current_obj->Name.Buffer, name)==0) + { + DPRINT("Found it %x\n",HEADER_TO_BODY(current_obj)); + return(HEADER_TO_BODY(current_obj)); + } + } + else + { + if ( wcscmp(current_obj->Name.Buffer, name)==0) + { + DPRINT("Found it %x\n",HEADER_TO_BODY(current_obj)); + return(HEADER_TO_BODY(current_obj)); + } + } + current = current->Flink; + } + DPRINT("%s() = NULL\n",__FUNCTION__); + return(NULL); +} + +VOID ObRemoveEntry(POBJECT_HEADER Header) +{ + KIRQL oldlvl; + + DPRINT("ObRemoveEntry(Header %x)\n",Header); + + KeAcquireSpinLock(&(Header->Parent->Lock),&oldlvl); + RemoveEntryList(&(Header->Entry)); + KeReleaseSpinLock(&(Header->Parent->Lock),oldlvl); +} + +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); + + /* + * Insert ourselves in our parents list + */ + InsertTailList(&parent->head,&Object->Entry); +} + +NTSTATUS ObLookupObject(HANDLE rootdir, PWSTR string, PVOID* Object, + PWSTR* UnparsedSection, ULONG Attributes) +/* + * 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 = NULL; + NTSTATUS Status; + + DPRINT("ObLookupObject(rootdir %x, string %x, string %w, Object %x, " + "UnparsedSection %x)\n",rootdir,string,string,Object, + UnparsedSection); + + + *UnparsedSection = NULL; + *Object = NULL; + + if (rootdir==NULL) + { + current_dir = HEADER_TO_BODY(&(namespc_root.hdr)); + } + else + { + ObReferenceObjectByHandle(rootdir,DIRECTORY_TRAVERSE,NULL, + UserMode,(PVOID*)¤t_dir,NULL); + } + + /* + * Bit of a hack this + */ + if (string[0]==0) + { + *Object=current_dir; + return(STATUS_SUCCESS); + } + + if (string[0]!='\\') + { + DbgPrint("(%s:%d) Non absolute pathname passed to %s\n",__FILE__, + __LINE__,__FUNCTION__); + return(STATUS_UNSUCCESSFUL); + } + + next = &string[0]; + current = next+1; + + while (next!=NULL && + BODY_TO_HEADER(current_dir)->ObjectType==ObDirectoryType) + { + *next = '\\'; + current = next+1; + next = wcschr(next+1,'\\'); + if (next!=NULL) + { + *next=0; + } + + DPRINT("current %w current[5] %x next %x ",current,current[5],next); + if (next!=NULL) + { + DPRINT("(next+1) %w",next+1); + } + DPRINT("\n",0); + + current_dir=(PDIRECTORY_OBJECT)ObDirLookup(current_dir,current, + Attributes); + if (current_dir==NULL) + { + DbgPrint("(%s:%d) Path component %w not found\n",__FILE__, + __LINE__,current); + return(STATUS_UNSUCCESSFUL); + } + + if (BODY_TO_HEADER(current_dir)->ObjectType==IoSymbolicLinkType) + { + current_dir = IoOpenSymlink(current_dir); + } + + } + DPRINT("next %x\n",next); + DPRINT("current %x current %w\n",current,current); + if (next==NULL) + { + if (current_dir==NULL) + { + Status = STATUS_UNSUCCESSFUL; + } + else + { + Status = STATUS_SUCCESS; + } + } + else + { + CHECKPOINT; + *next = '\\'; + *UnparsedSection = next; + if (BODY_TO_HEADER(current_dir)->ObjectType == IoDeviceType) + { + Status = STATUS_FS_QUERY_REQUIRED; + } + else + { + Status = STATUS_UNSUCCESSFUL; + } + } + CHECKPOINT; + *Object = current_dir; + DPRINT("(%s:%d) current_dir %x\n",__FILE__,__LINE__,current_dir); + + return(Status); +} + + diff --git a/reactos/ntoskrnl/ob/object.c b/reactos/ntoskrnl/ob/object.c index a5717bda745..b5580856a66 100644 --- a/reactos/ntoskrnl/ob/object.c +++ b/reactos/ntoskrnl/ob/object.c @@ -1,387 +1,389 @@ -/* - * 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 -#include - -#define NDEBUG -#include - -/* FUNCTIONS ************************************************************/ - -NTSTATUS STDCALL NtSetInformationObject(IN HANDLE ObjectHandle, - IN CINT ObjectInformationClass, - IN PVOID ObjectInformation, - IN ULONG Length) -{ - return(ZwSetInformationObject(ObjectHandle, - ObjectInformationClass, - ObjectInformation, - Length)); -} - -NTSTATUS STDCALL ZwSetInformationObject(IN HANDLE ObjectHandle, - IN CINT ObjectInformationClass, - IN PVOID ObjectInformation, - IN ULONG Length) -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtQueryObject(IN HANDLE ObjectHandle, - IN CINT ObjectInformationClass, - OUT PVOID ObjectInformation, - IN ULONG Length, - OUT PULONG ResultLength) -{ - return(ZwQueryObject(ObjectHandle, - ObjectInformationClass, - ObjectInformation, - Length, - ResultLength)); -} - -NTSTATUS STDCALL ZwQueryObject(IN HANDLE ObjectHandle, - IN CINT ObjectInformationClass, - OUT PVOID ObjectInformation, - IN ULONG Length, - OUT PULONG ResultLength) -{ - UNIMPLEMENTED -} - -NTSTATUS NtMakeTemporaryObject(HANDLE Handle) -{ - return(ZwMakeTemporaryObject(Handle)); -} - -NTSTATUS ZwMakeTemporaryObject(HANDLE Handle) -{ - PVOID Object; - NTSTATUS Status; - POBJECT_HEADER ObjectHeader; - - Status = ObReferenceObjectByHandle(Handle, - 0, - NULL, - KernelMode, - &Object, - NULL); - if (Status != STATUS_SUCCESS) - { - return(Status); - } - - ObjectHeader = BODY_TO_HEADER(Object); - ObjectHeader->Permanent = FALSE; - - ObDereferenceObject(Object); - - return(STATUS_SUCCESS); -} - -PVOID ObGenericCreateObject(PHANDLE Handle, - ACCESS_MASK DesiredAccess, - POBJECT_ATTRIBUTES ObjectAttributes, - POBJECT_TYPE Type) -/* - * FUNCTION: Creates a new object - */ -{ - POBJECT_HEADER hdr = NULL; - PWSTR path; - PWSTR name; - PWSTR Ignored; - PULONG addr; - PWSTR Buffer; - - DPRINT("ObGenericCreateObject(Handle %x, DesiredAccess %x," - "ObjectAttributes %x, Type %x)\n",Handle,DesiredAccess, - ObjectAttributes,Type); - - /* - * Allocate the object body and header - */ - hdr=(POBJECT_HEADER)ExAllocatePool(NonPagedPool,OBJECT_ALLOC_SIZE(Type)); - DPRINT("OBJECT_ALLOC_SIZE(Type) %d\n",OBJECT_ALLOC_SIZE(Type)); - if (hdr==NULL) - { - return(NULL); - } - DPRINT("hdr %x\n",hdr); - - - /* - * If unnamed then initalize - */ - if (ObjectAttributes==NULL || ObjectAttributes->ObjectName==NULL) - { - ObInitializeObjectHeader(Type,NULL,hdr); - if (Handle != NULL) - { - *Handle = ObInsertHandle(KeGetCurrentProcess(), - HEADER_TO_BODY(hdr), - DesiredAccess, - FALSE); - } - return(HEADER_TO_BODY(hdr)); - } - - - /* - * Copy the object name into a buffer - */ -// DbgPrint("ObjectAttributes->ObjectName %x\n",ObjectAttributes->ObjectName); -// DbgPrint("ObjectAttributes->ObjectName->Length %d\n", -// ObjectAttributes->ObjectName->Length); -// DbgPrint("ObjectAttributes->ObjectName->MaximumLength %d\n", -// ObjectAttributes->ObjectName->MaximumLength); - Buffer = ExAllocatePool(NonPagedPool, - ((ObjectAttributes->ObjectName->Length+1)*2)); - if (Buffer==NULL) - { - return(NULL); - } - memcpy(Buffer, ObjectAttributes->ObjectName->Buffer, - (ObjectAttributes->ObjectName->Length+1)*2); - - /* - * Seperate the name into a path and name - */ - name = wcsrchr(Buffer,'\\'); - if (name==NULL) - { - name=Buffer; - path=NULL; - } - else - { - path=Buffer; - *name=0; - name=name+1; - } - DPRINT("name %w path %w\n",name,path); - - ObLookupObject(ObjectAttributes->RootDirectory, - path, - &hdr->Parent, - &Ignored, - 0L); - - /* - * Initialize the object header - */ - ObInitializeObjectHeader(Type,name,hdr); - - - ObCreateEntry(hdr->Parent,hdr); - - DPRINT("Handle %x\n",Handle); - if (Handle != NULL) - { - *Handle = ObInsertHandle(KeGetCurrentProcess(), - HEADER_TO_BODY(hdr), - DesiredAccess, - FALSE); - } - - return(HEADER_TO_BODY(hdr)); -} - -VOID ObInitializeObjectHeader(POBJECT_TYPE Type, PWSTR name, - POBJECT_HEADER ObjectHeader) -/* - * FUNCTION: Creates a new object - * ARGUMENT: - * id = Identifier for the type of object - * obj = Pointer to the header of the object - */ -{ - PWSTR temp_name; - - DPRINT("ObInitializeObjectHeader(id %x name %w obj %x)\n",Type, - name,ObjectHeader); - - ObjectHeader->HandleCount = 1; - ObjectHeader->RefCount = 1; - ObjectHeader->ObjectType = Type; - ObjectHeader->Permanent = FALSE; - if (name==NULL) - { - ObjectHeader->Name.Length=0; - ObjectHeader->Name.Buffer=NULL; - } - else - { - RtlInitUnicodeString(&(ObjectHeader->Name),name); - } -} - - -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; - - DPRINT("ObReferenceObjectByPointer(%x)\n",ObjectBody); - - Object = BODY_TO_HEADER(ObjectBody); - Object->RefCount++; - return(STATUS_SUCCESS); -} - -NTSTATUS ObPerformRetentionChecks(POBJECT_HEADER Header) -{ - if (Header->RefCount == 0 && Header->HandleCount == 0 && - !Header->Permanent) - { - if (Header->Name.Buffer != NULL) - { - ObRemoveEntry(Header); - } - ExFreePool(Header); - } - 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 Header = BODY_TO_HEADER(ObjectBody); - - DPRINT("ObDeferenceObject(ObjectBody %x) RefCount %d\n",ObjectBody, - Header->RefCount); - - Header->RefCount--; - ObPerformRetentionChecks(Header); -} - - -NTSTATUS NtClose(HANDLE Handle) -{ - return(ZwClose(Handle)); -} - -NTSTATUS ZwClose(HANDLE Handle) -/* - * FUNCTION: Closes a handle reference to an object - * ARGUMENTS: - * Handle = handle to close - * RETURNS: Status - */ -{ - PVOID ObjectBody; - POBJECT_HEADER Header; - PHANDLE_REP HandleRep; - - assert_irql(PASSIVE_LEVEL); - - HandleRep = ObTranslateHandle(KeGetCurrentProcess(),Handle); - if (HandleRep == NULL) - { - return(STATUS_INVALID_HANDLE); - } - ObjectBody = HandleRep->ObjectBody; - - HandleRep->ObjectBody = NULL; - - Header = BODY_TO_HEADER(ObjectBody); - - Header->HandleCount--; - ObPerformRetentionChecks(Header); - - 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 - */ -{ - PHANDLE_REP HandleRep; - POBJECT_HEADER ObjectHeader; - - ASSERT_IRQL(PASSIVE_LEVEL); - - DPRINT("ObReferenceObjectByHandle(Handle %x, DesiredAccess %x, " - "ObjectType %x, AccessMode %d, Object %x)\n",Handle,DesiredAccess, - ObjectType,AccessMode,Object); - - if (Handle == NtCurrentProcess()) - { - *Object = PsGetCurrentProcess(); - return(STATUS_SUCCESS); - } - if (Handle == NtCurrentThread()) - { - *Object = PsGetCurrentThread(); - return(STATUS_SUCCESS); - } - - HandleRep = ObTranslateHandle(KeGetCurrentProcess(),Handle); - if (HandleRep == NULL || HandleRep->ObjectBody == NULL) - { - return(STATUS_INVALID_HANDLE); - } - - ObjectHeader = BODY_TO_HEADER(HandleRep->ObjectBody); - - if (ObjectType != NULL && ObjectType != ObjectHeader->ObjectType) - { - return(STATUS_UNSUCCESSFUL); - } - - if (!(HandleRep->GrantedAccess & DesiredAccess)) - { - return(STATUS_ACCESS_DENIED); - } - - ObjectHeader->RefCount++; - - *Object = HandleRep->ObjectBody; - - return(STATUS_SUCCESS); -} +/* + * 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 +#include + +#define NDEBUG +#include + +/* FUNCTIONS ************************************************************/ + +NTSTATUS STDCALL NtSetInformationObject(IN HANDLE ObjectHandle, + IN CINT ObjectInformationClass, + IN PVOID ObjectInformation, + IN ULONG Length) +{ + return(ZwSetInformationObject(ObjectHandle, + ObjectInformationClass, + ObjectInformation, + Length)); +} + +NTSTATUS STDCALL ZwSetInformationObject(IN HANDLE ObjectHandle, + IN CINT ObjectInformationClass, + IN PVOID ObjectInformation, + IN ULONG Length) +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtQueryObject(IN HANDLE ObjectHandle, + IN CINT ObjectInformationClass, + OUT PVOID ObjectInformation, + IN ULONG Length, + OUT PULONG ResultLength) +{ + return(ZwQueryObject(ObjectHandle, + ObjectInformationClass, + ObjectInformation, + Length, + ResultLength)); +} + +NTSTATUS STDCALL ZwQueryObject(IN HANDLE ObjectHandle, + IN CINT ObjectInformationClass, + OUT PVOID ObjectInformation, + IN ULONG Length, + OUT PULONG ResultLength) +{ + UNIMPLEMENTED +} + +NTSTATUS NtMakeTemporaryObject(HANDLE Handle) +{ + return(ZwMakeTemporaryObject(Handle)); +} + +NTSTATUS ZwMakeTemporaryObject(HANDLE Handle) +{ + PVOID Object; + NTSTATUS Status; + POBJECT_HEADER ObjectHeader; + + Status = ObReferenceObjectByHandle(Handle, + 0, + NULL, + KernelMode, + &Object, + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + ObjectHeader = BODY_TO_HEADER(Object); + ObjectHeader->Permanent = FALSE; + + ObDereferenceObject(Object); + + return(STATUS_SUCCESS); +} + +PVOID ObGenericCreateObject(PHANDLE Handle, + ACCESS_MASK DesiredAccess, + POBJECT_ATTRIBUTES ObjectAttributes, + POBJECT_TYPE Type) +/* + * FUNCTION: Creates a new object + */ +{ + POBJECT_HEADER hdr = NULL; + PWSTR path; + PWSTR name; + PWSTR Ignored; + PULONG addr; + PWSTR Buffer; + + DPRINT("ObGenericCreateObject(Handle %x, DesiredAccess %x," + "ObjectAttributes %x, Type %x)\n",Handle,DesiredAccess, + ObjectAttributes,Type); + + /* + * Allocate the object body and header + */ + hdr=(POBJECT_HEADER)ExAllocatePool(NonPagedPool,OBJECT_ALLOC_SIZE(Type)); + DPRINT("OBJECT_ALLOC_SIZE(Type) %d\n",OBJECT_ALLOC_SIZE(Type)); + if (hdr==NULL) + { + return(NULL); + } + DPRINT("hdr %x\n",hdr); + + + /* + * If unnamed then initalize + */ + if (ObjectAttributes==NULL || ObjectAttributes->ObjectName==NULL) + { + ObInitializeObjectHeader(Type,NULL,hdr); + if (Handle != NULL) + { + *Handle = ObInsertHandle(KeGetCurrentProcess(), + HEADER_TO_BODY(hdr), + DesiredAccess, + FALSE); + } + return(HEADER_TO_BODY(hdr)); + } + + + /* + * Copy the object name into a buffer + */ +// DbgPrint("ObjectAttributes->ObjectName %x\n",ObjectAttributes->ObjectName); +// DbgPrint("ObjectAttributes->ObjectName->Length %d\n", +// ObjectAttributes->ObjectName->Length); +// DbgPrint("ObjectAttributes->ObjectName->MaximumLength %d\n", +// ObjectAttributes->ObjectName->MaximumLength); + Buffer = ExAllocatePool(NonPagedPool, + ((ObjectAttributes->ObjectName->Length + 1) * + sizeof(WCHAR))); + if (Buffer==NULL) + { + return(NULL); + } + memcpy(Buffer, ObjectAttributes->ObjectName->Buffer, + (ObjectAttributes->ObjectName->Length + 1) * sizeof(WCHAR)); + + /* + * Seperate the name into a path and name + */ + name = wcsrchr(Buffer,'\\'); + if (name==NULL) + { + name=Buffer; + path=NULL; + } + else + { + path=Buffer; + *name=0; + name=name+1; + } + DPRINT("name %w path %w\n",name,path); + + ObLookupObject(ObjectAttributes->RootDirectory, + path, + &hdr->Parent, + &Ignored, + 0L); + + /* + * Initialize the object header + */ + ObInitializeObjectHeader(Type,name,hdr); + + + ObCreateEntry(hdr->Parent,hdr); + + DPRINT("Handle %x\n",Handle); + if (Handle != NULL) + { + *Handle = ObInsertHandle(KeGetCurrentProcess(), + HEADER_TO_BODY(hdr), + DesiredAccess, + FALSE); + } + + return(HEADER_TO_BODY(hdr)); +} + +VOID ObInitializeObjectHeader(POBJECT_TYPE Type, PWSTR name, + POBJECT_HEADER ObjectHeader) +/* + * FUNCTION: Creates a new object + * ARGUMENT: + * id = Identifier for the type of object + * obj = Pointer to the header of the object + */ +{ + PWSTR temp_name; + + DPRINT("ObInitializeObjectHeader(id %x name %w obj %x)\n",Type, + name,ObjectHeader); + + ObjectHeader->HandleCount = 1; + ObjectHeader->RefCount = 1; + ObjectHeader->ObjectType = Type; + ObjectHeader->Permanent = FALSE; + if (name==NULL) + { + ObjectHeader->Name.Length=0; + ObjectHeader->Name.Buffer=NULL; + } + else + { + RtlInitUnicodeString(&(ObjectHeader->Name),name); + } +} + + +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; + + DPRINT("ObReferenceObjectByPointer(%x)\n",ObjectBody); + + Object = BODY_TO_HEADER(ObjectBody); + Object->RefCount++; + return(STATUS_SUCCESS); +} + +NTSTATUS ObPerformRetentionChecks(POBJECT_HEADER Header) +{ + if (Header->RefCount == 0 && Header->HandleCount == 0 && + !Header->Permanent) + { + if (Header->Name.Buffer != NULL) + { + ObRemoveEntry(Header); + } + ExFreePool(Header); + } + 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 Header = BODY_TO_HEADER(ObjectBody); + + DPRINT("ObDeferenceObject(ObjectBody %x) RefCount %d\n",ObjectBody, + Header->RefCount); + + Header->RefCount--; + ObPerformRetentionChecks(Header); +} + + +NTSTATUS NtClose(HANDLE Handle) +{ + return(ZwClose(Handle)); +} + +NTSTATUS ZwClose(HANDLE Handle) +/* + * FUNCTION: Closes a handle reference to an object + * ARGUMENTS: + * Handle = handle to close + * RETURNS: Status + */ +{ + PVOID ObjectBody; + POBJECT_HEADER Header; + PHANDLE_REP HandleRep; + + assert_irql(PASSIVE_LEVEL); + + HandleRep = ObTranslateHandle(KeGetCurrentProcess(),Handle); + if (HandleRep == NULL) + { + return(STATUS_INVALID_HANDLE); + } + ObjectBody = HandleRep->ObjectBody; + + HandleRep->ObjectBody = NULL; + + Header = BODY_TO_HEADER(ObjectBody); + + Header->HandleCount--; + ObPerformRetentionChecks(Header); + + 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 + */ +{ + PHANDLE_REP HandleRep; + POBJECT_HEADER ObjectHeader; + + ASSERT_IRQL(PASSIVE_LEVEL); + + DPRINT("ObReferenceObjectByHandle(Handle %x, DesiredAccess %x, " + "ObjectType %x, AccessMode %d, Object %x)\n",Handle,DesiredAccess, + ObjectType,AccessMode,Object); + + if (Handle == NtCurrentProcess()) + { + *Object = PsGetCurrentProcess(); + return(STATUS_SUCCESS); + } + if (Handle == NtCurrentThread()) + { + *Object = PsGetCurrentThread(); + return(STATUS_SUCCESS); + } + + HandleRep = ObTranslateHandle(KeGetCurrentProcess(),Handle); + if (HandleRep == NULL || HandleRep->ObjectBody == NULL) + { + return(STATUS_INVALID_HANDLE); + } + + ObjectHeader = BODY_TO_HEADER(HandleRep->ObjectBody); + + if (ObjectType != NULL && ObjectType != ObjectHeader->ObjectType) + { + return(STATUS_UNSUCCESSFUL); + } + + if (!(HandleRep->GrantedAccess & DesiredAccess)) + { + return(STATUS_ACCESS_DENIED); + } + + ObjectHeader->RefCount++; + + *Object = HandleRep->ObjectBody; + + return(STATUS_SUCCESS); +} + diff --git a/reactos/ntoskrnl/ps/process.c b/reactos/ntoskrnl/ps/process.c index 1a811ab1ce4..dbcf3fb0f1f 100644 --- a/reactos/ntoskrnl/ps/process.c +++ b/reactos/ntoskrnl/ps/process.c @@ -1,312 +1,313 @@ -/* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS kernel - * FILE: ntoskrnl/ps/process.c - * PURPOSE: Process managment - * PROGRAMMER: David Welch (welch@mcmail.com) - * REVISION HISTORY: - * 21/07/98: Created - */ - -/* INCLUDES ******************************************************************/ - -#include -#include -#include -#include - -#define NDEBUG -#include - -/* GLOBALS ******************************************************************/ - -PEPROCESS SystemProcess = NULL; -HANDLE SystemProcessHandle = NULL; - -POBJECT_TYPE PsProcessType = NULL; - -/* FUNCTIONS *****************************************************************/ - -VOID PsInitProcessManagment(VOID) -{ - ANSI_STRING AnsiString; - PKPROCESS KProcess; - - /* - * Register the process object type - */ - - PsProcessType = ExAllocatePool(NonPagedPool, sizeof(OBJECT_TYPE)); - - PsProcessType->TotalObjects = 0; - PsProcessType->TotalHandles = 0; - PsProcessType->MaxObjects = ULONG_MAX; - PsProcessType->MaxHandles = ULONG_MAX; - PsProcessType->PagedPoolCharge = 0; - PsProcessType->NonpagedPoolCharge = sizeof(EPROCESS); - PsProcessType->Dump = NULL; - PsProcessType->Open = NULL; - PsProcessType->Close = NULL; - PsProcessType->Delete = NULL; - PsProcessType->Parse = NULL; - PsProcessType->Security = NULL; - PsProcessType->QueryName = NULL; - PsProcessType->OkayToClose = NULL; - - RtlInitAnsiString(&AnsiString,"Process"); - RtlAnsiStringToUnicodeString(&PsProcessType->TypeName,&AnsiString,TRUE); - - /* - * Initialize the system process - */ - SystemProcess = ObGenericCreateObject(NULL,PROCESS_ALL_ACCESS,NULL, - PsProcessType); - KProcess = &SystemProcess->Pcb; - - InitializeListHead(&(KProcess->MemoryAreaList)); - ObInitializeHandleTable(NULL,FALSE,KProcess); - KProcess->PageTableDirectory = get_page_directory(); - - SystemProcessHandle = ObInsertHandle(KProcess,SystemProcess, - PROCESS_ALL_ACCESS,FALSE); -} - -PKPROCESS KeGetCurrentProcess(VOID) -/* - * FUNCTION: Returns a pointer to the current process - */ -{ - return(&(PsGetCurrentProcess()->Pcb)); -} - -struct _EPROCESS* PsGetCurrentProcess(VOID) -/* - * FUNCTION: Returns a pointer to the current process - */ -{ - if (PsGetCurrentThread()==NULL - || PsGetCurrentThread()->ThreadsProcess==NULL) - { - return(SystemProcess); - } - else - { - return(PsGetCurrentThread()->ThreadsProcess); - } -} - -NTSTATUS STDCALL NtCreateProcess( - OUT PHANDLE ProcessHandle, - IN ACCESS_MASK DesiredAccess, - IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, - IN HANDLE ParentProcessHandle, - IN BOOLEAN InheritObjectTable, - IN HANDLE SectionHandle OPTIONAL, - IN HANDLE DebugPort OPTIONAL, - IN HANDLE ExceptionPort OPTIONAL) -{ - return(ZwCreateProcess(ProcessHandle, - DesiredAccess, - ObjectAttributes, - ParentProcessHandle, - InheritObjectTable, - SectionHandle, - DebugPort, - ExceptionPort)); -} - -NTSTATUS STDCALL ZwCreateProcess( - OUT PHANDLE ProcessHandle, - IN ACCESS_MASK DesiredAccess, - IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, - IN HANDLE ParentProcessHandle, - IN BOOLEAN InheritObjectTable, - IN HANDLE SectionHandle OPTIONAL, - IN HANDLE DebugPort OPTIONAL, - IN HANDLE ExceptionPort OPTIONAL) -/* - * FUNCTION: Creates a process. - * ARGUMENTS: - * ProcessHandle (OUT) = Caller supplied storage for the resulting - * handle - * DesiredAccess = Specifies the allowed or desired access to the - * process can be a combination of - * STANDARD_RIGHTS_REQUIRED| .. - * ObjectAttribute = Initialized attributes for the object, contains - * the rootdirectory and the filename - * ParentProcess = Handle to the parent process. - * InheritObjectTable = Specifies to inherit the objects of the parent - * process if true. - * SectionHandle = Handle to a section object to back the image file - * DebugPort = Handle to a DebugPort if NULL the system default debug - * port will be used. - * ExceptionPort = Handle to a exception port. - * REMARKS: - * This function maps to the win32 CreateProcess. - * RETURNS: Status - */ -{ - PEPROCESS Process; - PEPROCESS ParentProcess; - PULONG PageDirectory; - PULONG CurrentPageDirectory; - ULONG i; - PKPROCESS KProcess; - ULONG Base; - ULONG Length; - LARGE_INTEGER Offset; - NTSTATUS Status; - - DPRINT("ZwCreateProcess(ObjectAttributes %x)\n",ObjectAttributes); - - Status = ObReferenceObjectByHandle(ParentProcessHandle, - PROCESS_CREATE_PROCESS, - PsProcessType, - UserMode, - &ParentProcessHandle, - NULL); - - if (Status != STATUS_SUCCESS) - { - DPRINT("ZwCreateProcess() = %x\n",Status); - return(Status); - } - - Process = ObGenericCreateObject(ProcessHandle, - DesiredAccess, - ObjectAttributes, - PsProcessType); - KeInitializeDispatcherHeader(&Process->Pcb.DispatcherHeader, - 0, - sizeof(EPROCESS), - FALSE); - KProcess = &(Process->Pcb); - - InitializeListHead(&(KProcess->MemoryAreaList)); - ObInitializeHandleTable(KProcess,InheritObjectTable,KProcess); - - PageDirectory = physical_to_linear((ULONG)get_free_page()); - KProcess->PageTableDirectory = PageDirectory; - - CurrentPageDirectory = get_page_directory(); - - memset(PageDirectory,0,PAGESIZE); - for (i=768;i<1024;i++) - { - PageDirectory[i]=CurrentPageDirectory[i]; - } - - /* - * FIXME: I don't what I'm supposed to know with a section handle - */ - if (SectionHandle != NULL) - { - DbgPrint("ZwCreateProcess() non-NULL SectionHandle\n"); - return(STATUS_UNSUCCESSFUL); - } - - Process->Pcb.ProcessState = PROCESS_STATE_ACTIVE; - - return(STATUS_SUCCESS); -} - - -NTSTATUS STDCALL NtOpenProcess (OUT PHANDLE ProcessHandle, - IN ACCESS_MASK DesiredAccess, - IN POBJECT_ATTRIBUTES ObjectAttributes, - IN PCLIENT_ID ClientId) -{ - return(ZwOpenProcess(ProcessHandle, - DesiredAccess, - ObjectAttributes, - ClientId)); -} - -NTSTATUS STDCALL ZwOpenProcess (OUT PHANDLE ProcessHandle, - IN ACCESS_MASK DesiredAccess, - IN POBJECT_ATTRIBUTES ObjectAttributes, - IN PCLIENT_ID ClientId) -{ - UNIMPLEMENTED; -} - -NTSTATUS STDCALL NtQueryInformationProcess(IN HANDLE ProcessHandle, - IN CINT ProcessInformationClass, - OUT PVOID ProcessInformation, - IN ULONG ProcessInformationLength, - OUT PULONG ReturnLength) -{ - return(ZwQueryInformationProcess(ProcessHandle, - ProcessInformationClass, - ProcessInformation, - ProcessInformationLength, - ReturnLength)); -} - -NTSTATUS STDCALL ZwQueryInformationProcess(IN HANDLE ProcessHandle, - IN CINT ProcessInformationClass, - OUT PVOID ProcessInformation, - IN ULONG ProcessInformationLength, - OUT PULONG ReturnLength) -{ - PEPROCESS Process; - NTSTATUS Status; - - Status = ObReferenceObjectByHandle(ProcessHandle, - PROCESS_QUERY_INFORMATION, - PsProcessType, - UserMode, - &ProcessHandle, - NULL); - if (Status != STATUS_SUCCESS) - { - return(Status); - } - - switch (ProcessInformationClass) - { - case ProcessBasicInformation: - case ProcessQuotaLimits: - case ProcessIoCounters: - case ProcessVmCounters: - case ProcessTimes: - case ProcessBasePriority: - case ProcessRaisePriority: - case ProcessDebugPort: - case ProcessExceptionPort: - case ProcessAccessToken: - case ProcessLdtInformation: - case ProcessLdtSize: - case ProcessDefaultHardErrorMode: - case ProcessIoPortHandlers: - case ProcessWorkingSetWatch: - case ProcessUserModeIOPL: - case ProcessEnableAlignmentFaultFixup: - case ProcessPriorityClass: - case ProcessWx86Information: - case ProcessHandleCount: - case ProcessAffinityMask: - default: - Status = STATUS_NOT_IMPLEMENTED; - } - return(Status); -} - -NTSTATUS STDCALL NtSetInformationProcess(IN HANDLE ProcessHandle, - IN CINT ProcessInformationClass, - IN PVOID ProcessInformation, - IN ULONG ProcessInformationLength) -{ - return(ZwSetInformationProcess(ProcessHandle, - ProcessInformationClass, - ProcessInformation, - ProcessInformationLength)); -} - -NTSTATUS STDCALL ZwSetInformationProcess(IN HANDLE ProcessHandle, - IN CINT ProcessInformationClass, - IN PVOID ProcessInformation, - IN ULONG ProcessInformationLength) -{ - UNIMPLEMENTED; -} +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS kernel + * FILE: ntoskrnl/ps/process.c + * PURPOSE: Process managment + * PROGRAMMER: David Welch (welch@mcmail.com) + * REVISION HISTORY: + * 21/07/98: Created + */ + +/* INCLUDES ******************************************************************/ + +#include +#include +#include +#include + +#define NDEBUG +#include + +/* GLOBALS ******************************************************************/ + +PEPROCESS SystemProcess = NULL; +HANDLE SystemProcessHandle = NULL; + +POBJECT_TYPE PsProcessType = NULL; + +/* FUNCTIONS *****************************************************************/ + +VOID PsInitProcessManagment(VOID) +{ + ANSI_STRING AnsiString; + PKPROCESS KProcess; + + /* + * Register the process object type + */ + + PsProcessType = ExAllocatePool(NonPagedPool, sizeof(OBJECT_TYPE)); + + PsProcessType->TotalObjects = 0; + PsProcessType->TotalHandles = 0; + PsProcessType->MaxObjects = ULONG_MAX; + PsProcessType->MaxHandles = ULONG_MAX; + PsProcessType->PagedPoolCharge = 0; + PsProcessType->NonpagedPoolCharge = sizeof(EPROCESS); + PsProcessType->Dump = NULL; + PsProcessType->Open = NULL; + PsProcessType->Close = NULL; + PsProcessType->Delete = NULL; + PsProcessType->Parse = NULL; + PsProcessType->Security = NULL; + PsProcessType->QueryName = NULL; + PsProcessType->OkayToClose = NULL; + + RtlInitAnsiString(&AnsiString,"Process"); + RtlAnsiStringToUnicodeString(&PsProcessType->TypeName,&AnsiString,TRUE); + + /* + * Initialize the system process + */ + SystemProcess = ObGenericCreateObject(NULL,PROCESS_ALL_ACCESS,NULL, + PsProcessType); + KProcess = &SystemProcess->Pcb; + + InitializeListHead(&(KProcess->MemoryAreaList)); + ObInitializeHandleTable(NULL,FALSE,KProcess); + KProcess->PageTableDirectory = get_page_directory(); + + SystemProcessHandle = ObInsertHandle(KProcess,SystemProcess, + PROCESS_ALL_ACCESS,FALSE); +} + +PKPROCESS KeGetCurrentProcess(VOID) +/* + * FUNCTION: Returns a pointer to the current process + */ +{ + return(&(PsGetCurrentProcess()->Pcb)); +} + +struct _EPROCESS* PsGetCurrentProcess(VOID) +/* + * FUNCTION: Returns a pointer to the current process + */ +{ + if (PsGetCurrentThread()==NULL + || PsGetCurrentThread()->ThreadsProcess==NULL) + { + return(SystemProcess); + } + else + { + return(PsGetCurrentThread()->ThreadsProcess); + } +} + +NTSTATUS STDCALL NtCreateProcess( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, + IN HANDLE ParentProcessHandle, + IN BOOLEAN InheritObjectTable, + IN HANDLE SectionHandle OPTIONAL, + IN HANDLE DebugPort OPTIONAL, + IN HANDLE ExceptionPort OPTIONAL) +{ + return(ZwCreateProcess(ProcessHandle, + DesiredAccess, + ObjectAttributes, + ParentProcessHandle, + InheritObjectTable, + SectionHandle, + DebugPort, + ExceptionPort)); +} + +NTSTATUS STDCALL ZwCreateProcess( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, + IN HANDLE ParentProcessHandle, + IN BOOLEAN InheritObjectTable, + IN HANDLE SectionHandle OPTIONAL, + IN HANDLE DebugPort OPTIONAL, + IN HANDLE ExceptionPort OPTIONAL) +/* + * FUNCTION: Creates a process. + * ARGUMENTS: + * ProcessHandle (OUT) = Caller supplied storage for the resulting + * handle + * DesiredAccess = Specifies the allowed or desired access to the + * process can be a combination of + * STANDARD_RIGHTS_REQUIRED| .. + * ObjectAttribute = Initialized attributes for the object, contains + * the rootdirectory and the filename + * ParentProcess = Handle to the parent process. + * InheritObjectTable = Specifies to inherit the objects of the parent + * process if true. + * SectionHandle = Handle to a section object to back the image file + * DebugPort = Handle to a DebugPort if NULL the system default debug + * port will be used. + * ExceptionPort = Handle to a exception port. + * REMARKS: + * This function maps to the win32 CreateProcess. + * RETURNS: Status + */ +{ + PEPROCESS Process; + PEPROCESS ParentProcess; + PULONG PageDirectory; + PULONG CurrentPageDirectory; + ULONG i; + PKPROCESS KProcess; + ULONG Base; + ULONG Length; + LARGE_INTEGER Offset; + NTSTATUS Status; + + DPRINT("ZwCreateProcess(ObjectAttributes %x)\n",ObjectAttributes); + + Status = ObReferenceObjectByHandle(ParentProcessHandle, + PROCESS_CREATE_PROCESS, + PsProcessType, + UserMode, + &ParentProcessHandle, + NULL); + + if (Status != STATUS_SUCCESS) + { + DPRINT("ZwCreateProcess() = %x\n",Status); + return(Status); + } + + Process = ObGenericCreateObject(ProcessHandle, + DesiredAccess, + ObjectAttributes, + PsProcessType); + KeInitializeDispatcherHeader(&Process->Pcb.DispatcherHeader, + 0, + sizeof(EPROCESS), + FALSE); + KProcess = &(Process->Pcb); + + InitializeListHead(&(KProcess->MemoryAreaList)); + ObInitializeHandleTable(KProcess,InheritObjectTable,KProcess); + + PageDirectory = physical_to_linear((ULONG)get_free_page()); + KProcess->PageTableDirectory = PageDirectory; + + CurrentPageDirectory = get_page_directory(); + + memset(PageDirectory,0,PAGESIZE); + for (i=768;i<1024;i++) + { + PageDirectory[i]=CurrentPageDirectory[i]; + } + + /* + * FIXME: I don't what I'm supposed to know with a section handle + */ + if (SectionHandle != NULL) + { + DbgPrint("ZwCreateProcess() non-NULL SectionHandle\n"); + return(STATUS_UNSUCCESSFUL); + } + + Process->Pcb.ProcessState = PROCESS_STATE_ACTIVE; + + return(STATUS_SUCCESS); +} + + +NTSTATUS STDCALL NtOpenProcess (OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN PCLIENT_ID ClientId) +{ + return(ZwOpenProcess(ProcessHandle, + DesiredAccess, + ObjectAttributes, + ClientId)); +} + +NTSTATUS STDCALL ZwOpenProcess (OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN PCLIENT_ID ClientId) +{ + UNIMPLEMENTED; +} + +NTSTATUS STDCALL NtQueryInformationProcess(IN HANDLE ProcessHandle, + IN CINT ProcessInformationClass, + OUT PVOID ProcessInformation, + IN ULONG ProcessInformationLength, + OUT PULONG ReturnLength) +{ + return(ZwQueryInformationProcess(ProcessHandle, + ProcessInformationClass, + ProcessInformation, + ProcessInformationLength, + ReturnLength)); +} + +NTSTATUS STDCALL ZwQueryInformationProcess(IN HANDLE ProcessHandle, + IN CINT ProcessInformationClass, + OUT PVOID ProcessInformation, + IN ULONG ProcessInformationLength, + OUT PULONG ReturnLength) +{ + PEPROCESS Process; + NTSTATUS Status; + + Status = ObReferenceObjectByHandle(ProcessHandle, + PROCESS_QUERY_INFORMATION, + PsProcessType, + UserMode, + &ProcessHandle, + NULL); + if (Status != STATUS_SUCCESS) + { + return(Status); + } + + switch (ProcessInformationClass) + { + case ProcessBasicInformation: + case ProcessQuotaLimits: + case ProcessIoCounters: + case ProcessVmCounters: + case ProcessTimes: + case ProcessBasePriority: + case ProcessRaisePriority: + case ProcessDebugPort: + case ProcessExceptionPort: + case ProcessAccessToken: + case ProcessLdtInformation: + case ProcessLdtSize: + case ProcessDefaultHardErrorMode: + case ProcessIoPortHandlers: + case ProcessWorkingSetWatch: + case ProcessUserModeIOPL: + case ProcessEnableAlignmentFaultFixup: + case ProcessPriorityClass: + case ProcessWx86Information: + case ProcessHandleCount: + case ProcessAffinityMask: + default: + Status = STATUS_NOT_IMPLEMENTED; + } + return(Status); +} + +NTSTATUS STDCALL NtSetInformationProcess(IN HANDLE ProcessHandle, + IN CINT ProcessInformationClass, + IN PVOID ProcessInformation, + IN ULONG ProcessInformationLength) +{ + return(ZwSetInformationProcess(ProcessHandle, + ProcessInformationClass, + ProcessInformation, + ProcessInformationLength)); +} + +NTSTATUS STDCALL ZwSetInformationProcess(IN HANDLE ProcessHandle, + IN CINT ProcessInformationClass, + IN PVOID ProcessInformation, + IN ULONG ProcessInformationLength) +{ + UNIMPLEMENTED; +} + diff --git a/reactos/ntoskrnl/rtl/wstring.c b/reactos/ntoskrnl/rtl/wstring.c index 4dae5b13c80..4925ada4144 100644 --- a/reactos/ntoskrnl/rtl/wstring.c +++ b/reactos/ntoskrnl/rtl/wstring.c @@ -61,17 +61,19 @@ wcschr(const wchar_t *str, wchar_t ch) return NULL; } +#if 0 wchar_t towupper(wchar_t w) { if (w < L'A') { - return(w+'A'); + return(w + 'A'); } else { return(w); } } +#endif int wcsicmp(const wchar_t* cs, const wchar_t* ct) { @@ -521,7 +523,7 @@ UNIMPLEMENTED; #endif -unsigned long wstrlen(PWSTR s) +size_t wstrlen(const wchar_t *s) { return wcslen(s); } diff --git a/reactos/ntoskrnl/tst/test.c b/reactos/ntoskrnl/tst/test.c index 50bfdd4cbbe..f2384face15 100644 --- a/reactos/ntoskrnl/tst/test.c +++ b/reactos/ntoskrnl/tst/test.c @@ -529,35 +529,8 @@ TstTimer(void) } -void TstDriverLoad(void) -{ - NTSTATUS Status; - ANSI_STRING AnsiDriverName; - UNICODE_STRING DriverName; - - RtlInitAnsiString(&AnsiDriverName,"\\??\\C:\\reactos\\system\\keyboard.o"); - RtlAnsiStringToUnicodeString(&DriverName, &AnsiDriverName, TRUE); - Status = LdrLoadDriver(&DriverName); - RtlFreeUnicodeString(&DriverName); - if (!NT_SUCCESS(Status)) - { - DbgPrint("driver load failed, status;%d(%x)\n", Status, Status); - DbgPrintErrorMessage(Status); - } - RtlInitAnsiString(&AnsiDriverName,"\\??\\C:\\reactos\\system\\beep.sys"); - RtlAnsiStringToUnicodeString(&DriverName, &AnsiDriverName, TRUE); - Status = LdrLoadDriver(&DriverName); - RtlFreeUnicodeString(&DriverName); - if (!NT_SUCCESS(Status)) - { - DbgPrint("driver load failed, status;%d(%x)\n", Status, Status); - DbgPrintErrorMessage(Status); - } -} - void TstBegin() { - TstDriverLoad(); ExExecuteShell(); // TstFileRead(); // TstGeneralWrite();