summary refs log tree commit diff stats
path: root/lib/windows/winlean.nim
diff options
context:
space:
mode:
Diffstat (limited to 'lib/windows/winlean.nim')
-rw-r--r--lib/windows/winlean.nim570
1 files changed, 264 insertions, 306 deletions
diff --git a/lib/windows/winlean.nim b/lib/windows/winlean.nim
index 3263f1d37..79681376b 100644
--- a/lib/windows/winlean.nim
+++ b/lib/windows/winlean.nim
@@ -10,29 +10,29 @@
 ## This module implements a small wrapper for some needed Win API procedures,
 ## so that the Nim compiler does not depend on the huge Windows module.
 
-{.deadCodeElim: on.}  # dce option deprecated
+import std/dynlib
 
-import dynlib
+when defined(nimHasStyleChecks):
+  {.push styleChecks: off.}
 
+{.passc: "-DWIN32_LEAN_AND_MEAN".}
 
-{.passC: "-DWIN32_LEAN_AND_MEAN".}
+when defined(nimPreviewSlimSystem):
+  from std/syncio import FileHandle
+  import std/widestrs
 
-const
-  useWinUnicode* = not defined(useWinAnsi)
-
-when useWinUnicode:
-  type WinChar* = Utf16Char
-  {.deprecated: [TWinChar: WinChar].}
-else:
-  type WinChar* = char
-  {.deprecated: [TWinChar: WinChar].}
+type WinChar* = Utf16Char
 
+# See https://docs.microsoft.com/en-us/windows/win32/winprog/windows-data-types
 type
   Handle* = int
   LONG* = int32
   ULONG* = int32
   PULONG* = ptr int
   WINBOOL* = int32
+    ## `WINBOOL` uses opposite convention as posix, !=0 meaning success.
+    # xxx this should be distinct int32, distinct would make code less error prone
+  PBOOL* = ptr WINBOOL
   DWORD* = int32
   PDWORD* = ptr DWORD
   LPINT* = ptr int32
@@ -40,13 +40,14 @@ type
   PULONG_PTR* = ptr uint
   HDC* = Handle
   HGLRC* = Handle
+  BYTE* = uint8
 
-  SECURITY_ATTRIBUTES* {.final, pure.} = object
+  SECURITY_ATTRIBUTES* = object
     nLength*: int32
     lpSecurityDescriptor*: pointer
     bInheritHandle*: WINBOOL
 
-  STARTUPINFO* {.final, pure.} = object
+  STARTUPINFO* = object
     cb*: int32
     lpReserved*: cstring
     lpDesktop*: cstring
@@ -66,17 +67,17 @@ type
     hStdOutput*: Handle
     hStdError*: Handle
 
-  PROCESS_INFORMATION* {.final, pure.} = object
+  PROCESS_INFORMATION* = object
     hProcess*: Handle
     hThread*: Handle
     dwProcessId*: int32
     dwThreadId*: int32
 
-  FILETIME* {.final, pure.} = object ## CANNOT BE int64 BECAUSE OF ALIGNMENT
+  FILETIME* = object ## CANNOT BE int64 BECAUSE OF ALIGNMENT
     dwLowDateTime*: DWORD
     dwHighDateTime*: DWORD
 
-  BY_HANDLE_FILE_INFORMATION* {.final, pure.} = object
+  BY_HANDLE_FILE_INFORMATION* = object
     dwFileAttributes*: DWORD
     ftCreationTime*: FILETIME
     ftLastAccessTime*: FILETIME
@@ -88,7 +89,7 @@ type
     nFileIndexHigh*: DWORD
     nFileIndexLow*: DWORD
 
-  OSVERSIONINFO* {.final, pure.} = object
+  OSVERSIONINFO* = object
     dwOSVersionInfoSize*: DWORD
     dwMajorVersion*: DWORD
     dwMinorVersion*: DWORD
@@ -96,9 +97,11 @@ type
     dwPlatformId*: DWORD
     szCSDVersion*: array[0..127, WinChar]
 
-{.deprecated: [THandle: Handle, TSECURITY_ATTRIBUTES: SECURITY_ATTRIBUTES,
-    TSTARTUPINFO: STARTUPINFO, TPROCESS_INFORMATION: PROCESS_INFORMATION,
-    TFILETIME: FILETIME, TBY_HANDLE_FILE_INFORMATION: BY_HANDLE_FILE_INFORMATION].}
+  Protoent* = object
+    p_name*: cstring
+    p_aliases*: cstringArray
+    p_proto*: cshort
+
 
 const
   STARTF_USESHOWWINDOW* = 1'i32
@@ -132,35 +135,41 @@ const
 
   CREATE_NO_WINDOW* = 0x08000000'i32
 
-when useWinUnicode:
-  proc getVersionExW*(lpVersionInfo: ptr OSVERSIONINFO): WINBOOL {.stdcall, dynlib: "kernel32", importc: "GetVersionExW".}
-else:
-  proc getVersionExA*(lpVersionInfo: ptr OSVERSIONINFO): WINBOOL {.stdcall, dynlib: "kernel32", importc: "GetVersionExA".}
+  HANDLE_FLAG_INHERIT* = 0x00000001'i32
+
+proc isSuccess*(a: WINBOOL): bool {.inline.} =
+  ## Returns true if `a != 0`. Windows uses a different convention than POSIX,
+  ## where `a == 0` is commonly used on success.
+  a != 0
+proc getVersionExW*(lpVersionInfo: ptr OSVERSIONINFO): WINBOOL {.
+    stdcall, dynlib: "kernel32", importc: "GetVersionExW", sideEffect.}
+proc getVersionExA*(lpVersionInfo: ptr OSVERSIONINFO): WINBOOL {.
+    stdcall, dynlib: "kernel32", importc: "GetVersionExA", sideEffect.}
 
-proc getVersion*(): DWORD {.stdcall, dynlib: "kernel32", importc: "GetVersion".}
+proc getVersion*(): DWORD {.stdcall, dynlib: "kernel32", importc: "GetVersion", sideEffect.}
 
 proc closeHandle*(hObject: Handle): WINBOOL {.stdcall, dynlib: "kernel32",
     importc: "CloseHandle".}
 
-proc readFile*(hFile: Handle, Buffer: pointer, nNumberOfBytesToRead: int32,
+proc readFile*(hFile: Handle, buffer: pointer, nNumberOfBytesToRead: int32,
                lpNumberOfBytesRead: ptr int32, lpOverlapped: pointer): WINBOOL{.
-    stdcall, dynlib: "kernel32", importc: "ReadFile".}
+    stdcall, dynlib: "kernel32", importc: "ReadFile", sideEffect.}
 
-proc writeFile*(hFile: Handle, Buffer: pointer, nNumberOfBytesToWrite: int32,
+proc writeFile*(hFile: Handle, buffer: pointer, nNumberOfBytesToWrite: int32,
                 lpNumberOfBytesWritten: ptr int32,
                 lpOverlapped: pointer): WINBOOL{.
-    stdcall, dynlib: "kernel32", importc: "WriteFile".}
+    stdcall, dynlib: "kernel32", importc: "WriteFile", sideEffect.}
 
 proc createPipe*(hReadPipe, hWritePipe: var Handle,
                  lpPipeAttributes: var SECURITY_ATTRIBUTES,
                  nSize: int32): WINBOOL{.
-    stdcall, dynlib: "kernel32", importc: "CreatePipe".}
+    stdcall, dynlib: "kernel32", importc: "CreatePipe", sideEffect.}
 
 proc createNamedPipe*(lpName: WideCString,
                      dwOpenMode, dwPipeMode, nMaxInstances, nOutBufferSize,
                      nInBufferSize, nDefaultTimeOut: int32,
                      lpSecurityAttributes: ptr SECURITY_ATTRIBUTES): Handle {.
-    stdcall, dynlib: "kernel32", importc: "CreateNamedPipeW".}
+    stdcall, dynlib: "kernel32", importc: "CreateNamedPipeW", sideEffect.}
 
 proc peekNamedPipe*(hNamedPipe: Handle, lpBuffer: pointer=nil,
                     nBufferSize: int32 = 0,
@@ -169,37 +178,25 @@ proc peekNamedPipe*(hNamedPipe: Handle, lpBuffer: pointer=nil,
                     lpBytesLeftThisMessage: ptr int32 = nil): bool {.
     stdcall, dynlib: "kernel32", importc: "PeekNamedPipe".}
 
-when useWinUnicode:
-  proc createProcessW*(lpApplicationName, lpCommandLine: WideCString,
-                     lpProcessAttributes: ptr SECURITY_ATTRIBUTES,
-                     lpThreadAttributes: ptr SECURITY_ATTRIBUTES,
-                     bInheritHandles: WINBOOL, dwCreationFlags: int32,
-                     lpEnvironment, lpCurrentDirectory: WideCString,
-                     lpStartupInfo: var STARTUPINFO,
-                     lpProcessInformation: var PROCESS_INFORMATION): WINBOOL{.
-    stdcall, dynlib: "kernel32", importc: "CreateProcessW".}
-
-else:
-  proc createProcessA*(lpApplicationName, lpCommandLine: cstring,
-                       lpProcessAttributes: ptr SECURITY_ATTRIBUTES,
-                       lpThreadAttributes: ptr SECURITY_ATTRIBUTES,
-                       bInheritHandles: WINBOOL, dwCreationFlags: int32,
-                       lpEnvironment: pointer, lpCurrentDirectory: cstring,
-                       lpStartupInfo: var STARTUPINFO,
-                       lpProcessInformation: var PROCESS_INFORMATION): WINBOOL{.
-      stdcall, dynlib: "kernel32", importc: "CreateProcessA".}
-
+proc createProcessW*(lpApplicationName, lpCommandLine: WideCString,
+                   lpProcessAttributes: ptr SECURITY_ATTRIBUTES,
+                   lpThreadAttributes: ptr SECURITY_ATTRIBUTES,
+                   bInheritHandles: WINBOOL, dwCreationFlags: int32,
+                   lpEnvironment, lpCurrentDirectory: WideCString,
+                   lpStartupInfo: var STARTUPINFO,
+                   lpProcessInformation: var PROCESS_INFORMATION): WINBOOL{.
+  stdcall, dynlib: "kernel32", importc: "CreateProcessW", sideEffect.}
 
 proc suspendThread*(hThread: Handle): int32 {.stdcall, dynlib: "kernel32",
-    importc: "SuspendThread".}
+    importc: "SuspendThread", sideEffect.}
 proc resumeThread*(hThread: Handle): int32 {.stdcall, dynlib: "kernel32",
-    importc: "ResumeThread".}
+    importc: "ResumeThread", sideEffect.}
 
 proc waitForSingleObject*(hHandle: Handle, dwMilliseconds: int32): int32 {.
-    stdcall, dynlib: "kernel32", importc: "WaitForSingleObject".}
+    stdcall, dynlib: "kernel32", importc: "WaitForSingleObject", sideEffect.}
 
 proc terminateProcess*(hProcess: Handle, uExitCode: int): WINBOOL {.stdcall,
-    dynlib: "kernel32", importc: "TerminateProcess".}
+    dynlib: "kernel32", importc: "TerminateProcess", sideEffect.}
 
 proc getExitCodeProcess*(hProcess: Handle, lpExitCode: var int32): WINBOOL {.
     stdcall, dynlib: "kernel32", importc: "GetExitCodeProcess".}
@@ -207,77 +204,47 @@ proc getExitCodeProcess*(hProcess: Handle, lpExitCode: var int32): WINBOOL {.
 proc getStdHandle*(nStdHandle: int32): Handle {.stdcall, dynlib: "kernel32",
     importc: "GetStdHandle".}
 proc setStdHandle*(nStdHandle: int32, hHandle: Handle): WINBOOL {.stdcall,
-    dynlib: "kernel32", importc: "SetStdHandle".}
+    dynlib: "kernel32", importc: "SetStdHandle", sideEffect.}
 proc flushFileBuffers*(hFile: Handle): WINBOOL {.stdcall, dynlib: "kernel32",
-    importc: "FlushFileBuffers".}
+    importc: "FlushFileBuffers", sideEffect.}
 
 proc getLastError*(): int32 {.importc: "GetLastError",
-    stdcall, dynlib: "kernel32".}
+    stdcall, dynlib: "kernel32", sideEffect.}
 
 proc setLastError*(error: int32) {.importc: "SetLastError",
-    stdcall, dynlib: "kernel32".}
-
-when useWinUnicode:
-  proc formatMessageW*(dwFlags: int32, lpSource: pointer,
-                      dwMessageId, dwLanguageId: int32,
-                      lpBuffer: pointer, nSize: int32,
-                      Arguments: pointer): int32 {.
-                      importc: "FormatMessageW", stdcall, dynlib: "kernel32".}
-else:
-  proc formatMessageA*(dwFlags: int32, lpSource: pointer,
+    stdcall, dynlib: "kernel32", sideEffect.}
+
+proc formatMessageW*(dwFlags: int32, lpSource: pointer,
                     dwMessageId, dwLanguageId: int32,
                     lpBuffer: pointer, nSize: int32,
-                    Arguments: pointer): int32 {.
-                    importc: "FormatMessageA", stdcall, dynlib: "kernel32".}
+                    arguments: pointer): int32 {.
+                    importc: "FormatMessageW", stdcall, dynlib: "kernel32".}
 
 proc localFree*(p: pointer) {.
   importc: "LocalFree", stdcall, dynlib: "kernel32".}
 
-when useWinUnicode:
-  proc getCurrentDirectoryW*(nBufferLength: int32,
-                             lpBuffer: WideCString): int32 {.
-    importc: "GetCurrentDirectoryW", dynlib: "kernel32", stdcall.}
-  proc setCurrentDirectoryW*(lpPathName: WideCString): int32 {.
-    importc: "SetCurrentDirectoryW", dynlib: "kernel32", stdcall.}
-  proc createDirectoryW*(pathName: WideCString, security: pointer=nil): int32 {.
-    importc: "CreateDirectoryW", dynlib: "kernel32", stdcall.}
-  proc removeDirectoryW*(lpPathName: WideCString): int32 {.
-    importc: "RemoveDirectoryW", dynlib: "kernel32", stdcall.}
-  proc setEnvironmentVariableW*(lpName, lpValue: WideCString): int32 {.
-    stdcall, dynlib: "kernel32", importc: "SetEnvironmentVariableW".}
-
-  proc getModuleFileNameW*(handle: Handle, buf: WideCString,
-                           size: int32): int32 {.importc: "GetModuleFileNameW",
-    dynlib: "kernel32", stdcall.}
-else:
-  proc getCurrentDirectoryA*(nBufferLength: int32, lpBuffer: cstring): int32 {.
-    importc: "GetCurrentDirectoryA", dynlib: "kernel32", stdcall.}
-  proc setCurrentDirectoryA*(lpPathName: cstring): int32 {.
-    importc: "SetCurrentDirectoryA", dynlib: "kernel32", stdcall.}
-  proc createDirectoryA*(pathName: cstring, security: pointer=nil): int32 {.
-    importc: "CreateDirectoryA", dynlib: "kernel32", stdcall.}
-  proc removeDirectoryA*(lpPathName: cstring): int32 {.
-    importc: "RemoveDirectoryA", dynlib: "kernel32", stdcall.}
-  proc setEnvironmentVariableA*(lpName, lpValue: cstring): int32 {.
-    stdcall, dynlib: "kernel32", importc: "SetEnvironmentVariableA".}
-
-  proc getModuleFileNameA*(handle: Handle, buf: cstring, size: int32): int32 {.
-    importc: "GetModuleFileNameA", dynlib: "kernel32", stdcall.}
-
-when useWinUnicode:
-  proc createSymbolicLinkW*(lpSymlinkFileName, lpTargetFileName: WideCString,
-                         flags: DWORD): int32 {.
-    importc:"CreateSymbolicLinkW", dynlib: "kernel32", stdcall.}
-  proc createHardLinkW*(lpFileName, lpExistingFileName: WideCString,
-                         security: pointer=nil): int32 {.
-    importc:"CreateHardLinkW", dynlib: "kernel32", stdcall.}
-else:
-  proc createSymbolicLinkA*(lpSymlinkFileName, lpTargetFileName: cstring,
-                           flags: DWORD): int32 {.
-    importc:"CreateSymbolicLinkA", dynlib: "kernel32", stdcall.}
-  proc createHardLinkA*(lpFileName, lpExistingFileName: cstring,
-                           security: pointer=nil): int32 {.
-    importc:"CreateHardLinkA", dynlib: "kernel32", stdcall.}
+proc getCurrentDirectoryW*(nBufferLength: int32,
+                           lpBuffer: WideCString): int32 {.
+  importc: "GetCurrentDirectoryW", dynlib: "kernel32", stdcall, sideEffect.}
+proc setCurrentDirectoryW*(lpPathName: WideCString): int32 {.
+  importc: "SetCurrentDirectoryW", dynlib: "kernel32", stdcall, sideEffect.}
+proc createDirectoryW*(pathName: WideCString, security: pointer=nil): int32 {.
+  importc: "CreateDirectoryW", dynlib: "kernel32", stdcall, sideEffect.}
+proc removeDirectoryW*(lpPathName: WideCString): int32 {.
+  importc: "RemoveDirectoryW", dynlib: "kernel32", stdcall, sideEffect.}
+proc setEnvironmentVariableW*(lpName, lpValue: WideCString): int32 {.
+  stdcall, dynlib: "kernel32", importc: "SetEnvironmentVariableW", sideEffect.}
+
+proc getModuleFileNameW*(handle: Handle, buf: WideCString,
+                         size: int32): int32 {.importc: "GetModuleFileNameW",
+  dynlib: "kernel32", stdcall.}
+
+proc createSymbolicLinkW*(lpSymlinkFileName, lpTargetFileName: WideCString,
+                       flags: DWORD): int32 {.
+  importc:"CreateSymbolicLinkW", dynlib: "kernel32", stdcall, sideEffect.}
+proc createHardLinkW*(lpFileName, lpExistingFileName: WideCString,
+                       security: pointer=nil): int32 {.
+  importc:"CreateHardLinkW", dynlib: "kernel32", stdcall, sideEffect.}
 
 const
   FILE_ATTRIBUTE_READONLY* = 0x00000001'i32
@@ -327,114 +294,67 @@ type
     dwReserved1: int32
     cFileName*: array[0..(MAX_PATH) - 1, WinChar]
     cAlternateFileName*: array[0..13, WinChar]
-{.deprecated: [TWIN32_FIND_DATA: WIN32_FIND_DATA].}
-
-when useWinUnicode:
-  proc findFirstFileW*(lpFileName: WideCString,
-                      lpFindFileData: var WIN32_FIND_DATA): Handle {.
-      stdcall, dynlib: "kernel32", importc: "FindFirstFileW".}
-  proc findNextFileW*(hFindFile: Handle,
-                     lpFindFileData: var WIN32_FIND_DATA): int32 {.
-      stdcall, dynlib: "kernel32", importc: "FindNextFileW".}
-else:
-  proc findFirstFileA*(lpFileName: cstring,
-                      lpFindFileData: var WIN32_FIND_DATA): Handle {.
-      stdcall, dynlib: "kernel32", importc: "FindFirstFileA".}
-  proc findNextFileA*(hFindFile: Handle,
-                     lpFindFileData: var WIN32_FIND_DATA): int32 {.
-      stdcall, dynlib: "kernel32", importc: "FindNextFileA".}
+
+proc findFirstFileW*(lpFileName: WideCString,
+                    lpFindFileData: var WIN32_FIND_DATA): Handle {.
+    stdcall, dynlib: "kernel32", importc: "FindFirstFileW", sideEffect.}
+proc findNextFileW*(hFindFile: Handle,
+                   lpFindFileData: var WIN32_FIND_DATA): int32 {.
+    stdcall, dynlib: "kernel32", importc: "FindNextFileW", sideEffect.}
 
 proc findClose*(hFindFile: Handle) {.stdcall, dynlib: "kernel32",
   importc: "FindClose".}
 
-when useWinUnicode:
-  proc getFullPathNameW*(lpFileName: WideCString, nBufferLength: int32,
-                        lpBuffer: WideCString,
-                        lpFilePart: var WideCString): int32 {.
+proc getFullPathNameW*(lpFileName: WideCString, nBufferLength: int32,
+                      lpBuffer: WideCString,
+                      lpFilePart: var WideCString): int32 {.
+                      stdcall, dynlib: "kernel32",
+                      importc: "GetFullPathNameW", sideEffect.}
+proc getFileAttributesW*(lpFileName: WideCString): int32 {.
                         stdcall, dynlib: "kernel32",
-                        importc: "GetFullPathNameW".}
-  proc getFileAttributesW*(lpFileName: WideCString): int32 {.
-                          stdcall, dynlib: "kernel32",
-                          importc: "GetFileAttributesW".}
-  proc setFileAttributesW*(lpFileName: WideCString,
-                           dwFileAttributes: int32): WINBOOL {.
-      stdcall, dynlib: "kernel32", importc: "SetFileAttributesW".}
-
-  proc copyFileW*(lpExistingFileName, lpNewFileName: WideCString,
-                 bFailIfExists: WINBOOL): WINBOOL {.
-    importc: "CopyFileW", stdcall, dynlib: "kernel32".}
-
-  proc moveFileW*(lpExistingFileName, lpNewFileName: WideCString): WINBOOL {.
-    importc: "MoveFileW", stdcall, dynlib: "kernel32".}
-  proc moveFileExW*(lpExistingFileName, lpNewFileName: WideCString,
-                    flags: DWORD): WINBOOL {.
-    importc: "MoveFileExW", stdcall, dynlib: "kernel32".}
-
-  proc getEnvironmentStringsW*(): WideCString {.
-    stdcall, dynlib: "kernel32", importc: "GetEnvironmentStringsW".}
-  proc freeEnvironmentStringsW*(para1: WideCString): int32 {.
-    stdcall, dynlib: "kernel32", importc: "FreeEnvironmentStringsW".}
-
-  proc getCommandLineW*(): WideCString {.importc: "GetCommandLineW",
-    stdcall, dynlib: "kernel32".}
+                        importc: "GetFileAttributesW", sideEffect.}
+proc setFileAttributesW*(lpFileName: WideCString,
+                         dwFileAttributes: int32): WINBOOL {.
+    stdcall, dynlib: "kernel32", importc: "SetFileAttributesW", sideEffect.}
 
-else:
-  proc getFullPathNameA*(lpFileName: cstring, nBufferLength: int32,
-                        lpBuffer: cstring, lpFilePart: var cstring): int32 {.
-                        stdcall, dynlib: "kernel32",
-                        importc: "GetFullPathNameA".}
-  proc getFileAttributesA*(lpFileName: cstring): int32 {.
-                          stdcall, dynlib: "kernel32",
-                          importc: "GetFileAttributesA".}
-  proc setFileAttributesA*(lpFileName: cstring,
-                           dwFileAttributes: int32): WINBOOL {.
-      stdcall, dynlib: "kernel32", importc: "SetFileAttributesA".}
-
-  proc copyFileA*(lpExistingFileName, lpNewFileName: cstring,
-                 bFailIfExists: cint): cint {.
-    importc: "CopyFileA", stdcall, dynlib: "kernel32".}
-
-  proc moveFileA*(lpExistingFileName, lpNewFileName: cstring): WINBOOL {.
-    importc: "MoveFileA", stdcall, dynlib: "kernel32".}
-  proc moveFileExA*(lpExistingFileName, lpNewFileName: WideCString,
-                    flags: DWORD): WINBOOL {.
-    importc: "MoveFileExA", stdcall, dynlib: "kernel32".}
-
-  proc getEnvironmentStringsA*(): cstring {.
-    stdcall, dynlib: "kernel32", importc: "GetEnvironmentStringsA".}
-  proc freeEnvironmentStringsA*(para1: cstring): int32 {.
-    stdcall, dynlib: "kernel32", importc: "FreeEnvironmentStringsA".}
-
-  proc getCommandLineA*(): cstring {.
-    importc: "GetCommandLineA", stdcall, dynlib: "kernel32".}
+proc copyFileW*(lpExistingFileName, lpNewFileName: WideCString,
+               bFailIfExists: WINBOOL): WINBOOL {.
+  importc: "CopyFileW", stdcall, dynlib: "kernel32", sideEffect.}
+
+proc moveFileW*(lpExistingFileName, lpNewFileName: WideCString): WINBOOL {.
+  importc: "MoveFileW", stdcall, dynlib: "kernel32", sideEffect.}
+proc moveFileExW*(lpExistingFileName, lpNewFileName: WideCString,
+                  flags: DWORD): WINBOOL {.
+  importc: "MoveFileExW", stdcall, dynlib: "kernel32", sideEffect.}
+
+proc getEnvironmentStringsW*(): WideCString {.
+  stdcall, dynlib: "kernel32", importc: "GetEnvironmentStringsW", sideEffect.}
+proc freeEnvironmentStringsW*(para1: WideCString): int32 {.
+  stdcall, dynlib: "kernel32", importc: "FreeEnvironmentStringsW", sideEffect.}
+
+proc getCommandLineW*(): WideCString {.importc: "GetCommandLineW",
+  stdcall, dynlib: "kernel32", sideEffect.}
 
 proc rdFileTime*(f: FILETIME): int64 =
-  result = ze64(f.dwLowDateTime) or (ze64(f.dwHighDateTime) shl 32)
+  result = int64(cast[uint32](f.dwLowDateTime)) or (int64(cast[uint32](f.dwHighDateTime)) shl 32)
 
 proc rdFileSize*(f: WIN32_FIND_DATA): int64 =
-  result = ze64(f.nFileSizeLow) or (ze64(f.nFileSizeHigh) shl 32)
+  result = int64(cast[uint32](f.nFileSizeLow)) or (int64(cast[uint32](f.nFileSizeHigh)) shl 32)
 
 proc getSystemTimeAsFileTime*(lpSystemTimeAsFileTime: var FILETIME) {.
-  importc: "GetSystemTimeAsFileTime", dynlib: "kernel32", stdcall.}
+  importc: "GetSystemTimeAsFileTime", dynlib: "kernel32", stdcall, sideEffect.}
 
 proc sleep*(dwMilliseconds: int32){.stdcall, dynlib: "kernel32",
-                                    importc: "Sleep".}
+                                    importc: "Sleep", sideEffect.}
 
-when useWinUnicode:
-  proc shellExecuteW*(HWND: Handle, lpOperation, lpFile,
-                     lpParameters, lpDirectory: WideCString,
-                     nShowCmd: int32): Handle{.
-      stdcall, dynlib: "shell32.dll", importc: "ShellExecuteW".}
-
-else:
-  proc shellExecuteA*(HWND: Handle, lpOperation, lpFile,
-                     lpParameters, lpDirectory: cstring,
-                     nShowCmd: int32): Handle{.
-      stdcall, dynlib: "shell32.dll", importc: "ShellExecuteA".}
+proc shellExecuteW*(hwnd: Handle, lpOperation, lpFile,
+                   lpParameters, lpDirectory: WideCString,
+                   nShowCmd: int32): Handle{.
+    stdcall, dynlib: "shell32.dll", importc: "ShellExecuteW", sideEffect.}
 
 proc getFileInformationByHandle*(hFile: Handle,
   lpFileInformation: ptr BY_HANDLE_FILE_INFORMATION): WINBOOL{.
-    stdcall, dynlib: "kernel32", importc: "GetFileInformationByHandle".}
+    stdcall, dynlib: "kernel32", importc: "GetFileInformationByHandle", sideEffect.}
 
 const
   WSADESCRIPTION_LEN* = 256
@@ -449,11 +369,10 @@ const
 
   ws2dll = "Ws2_32.dll"
 
-proc wsaGetLastError*(): cint {.importc: "WSAGetLastError", dynlib: ws2dll.}
+proc wsaGetLastError*(): cint {.importc: "WSAGetLastError", dynlib: ws2dll, sideEffect.}
 
 type
   SocketHandle* = distinct int
-{.deprecated: [TSocketHandle: SocketHandle].}
 
 type
   WSAData* {.importc: "WSADATA", header: "winsock2.h".} = object
@@ -464,17 +383,17 @@ type
     lpVendorInfo: cstring
 
   SockAddr* {.importc: "SOCKADDR", header: "winsock2.h".} = object
-    sa_family*: int16 # unsigned
+    sa_family*: uint16
     sa_data*: array[0..13, char]
 
   PSockAddr = ptr SockAddr
 
-  InAddr* {.importc: "IN_ADDR", header: "winsock2.h".} = object
+  InAddr* {.importc: "IN_ADDR", header: "winsock2.h", union.} = object
     s_addr*: uint32  # IP address
 
   Sockaddr_in* {.importc: "SOCKADDR_IN",
                   header: "winsock2.h".} = object
-    sin_family*: int16
+    sin_family*: uint16
     sin_port*: uint16
     sin_addr*: InAddr
     sin_zero*: array[0..7, char]
@@ -484,24 +403,18 @@ type
 
   Sockaddr_in6* {.importc: "SOCKADDR_IN6",
                    header: "ws2tcpip.h".} = object
-    sin6_family*: int16
+    sin6_family*: uint16
     sin6_port*: uint16
     sin6_flowinfo*: int32 # unsigned
     sin6_addr*: In6_addr
     sin6_scope_id*: int32 # unsigned
 
-  Sockaddr_in6_old* = object
-    sin6_family*: int16
-    sin6_port*: int16 # unsigned
-    sin6_flowinfo*: int32 # unsigned
-    sin6_addr*: In6_addr
-
   Sockaddr_storage* {.importc: "SOCKADDR_STORAGE",
                       header: "winsock2.h".} = object
-    ss_family*: int16
-    ss_pad1: array[6, byte]
-    ss_align: int64
-    ss_pad2: array[112, byte]
+    ss_family*: uint16
+    ss_pad1 {.importc: "__ss_pad1".}: array[6, byte]
+    ss_align {.importc: "__ss_align".}: int64
+    ss_pad2 {.importc: "__ss_pad2".}: array[112, byte]
 
   Servent* = object
     s_name*: cstring
@@ -524,26 +437,26 @@ type
     fd_count*: cint # unsigned
     fd_array*: array[0..FD_SETSIZE-1, SocketHandle]
 
-  Timeval* = object
-    tv_sec*, tv_usec*: int32
-
   AddrInfo* = object
     ai_flags*: cint         ## Input flags.
     ai_family*: cint        ## Address family of socket.
     ai_socktype*: cint      ## Socket type.
     ai_protocol*: cint      ## Protocol of socket.
-    ai_addrlen*: csize        ## Length of socket address.
+    ai_addrlen*: csize_t        ## Length of socket address.
     ai_canonname*: cstring  ## Canonical name of service location.
     ai_addr*: ptr SockAddr ## Socket address of socket.
     ai_next*: ptr AddrInfo ## Pointer to next in list.
 
   SockLen* = cuint
-{.deprecated: [TSockaddr_in: Sockaddr_in, TAddrinfo: AddrInfo,
-    TSockAddr: SockAddr, TSockLen: SockLen, TTimeval: Timeval,
-    TWSADATA: WSADATA, Thostent: Hostent, TServent: Servent,
-    TInAddr: InAddr, Tin6_addr: In6_addr, Tsockaddr_in6: Sockaddr_in6,
-    Tsockaddr_in6_old: Sockaddr_in6_old].}
 
+when defined(cpp):
+  type
+    Timeval* {.importc: "timeval", header: "<time.h>".} = object
+      tv_sec*, tv_usec*: int32
+else:
+  type
+    Timeval* = object
+      tv_sec*, tv_usec*: int32
 
 var
   SOMAXCONN* {.importc, header: "winsock2.h".}: cint
@@ -569,19 +482,27 @@ var
 proc `==`*(x, y: SocketHandle): bool {.borrow.}
 
 proc getservbyname*(name, proto: cstring): ptr Servent {.
-  stdcall, importc: "getservbyname", dynlib: ws2dll.}
+  stdcall, importc: "getservbyname", dynlib: ws2dll, sideEffect.}
 
 proc getservbyport*(port: cint, proto: cstring): ptr Servent {.
-  stdcall, importc: "getservbyport", dynlib: ws2dll.}
+  stdcall, importc: "getservbyport", dynlib: ws2dll, sideEffect.}
 
 proc gethostbyaddr*(ip: ptr InAddr, len: cuint, theType: cint): ptr Hostent {.
-  stdcall, importc: "gethostbyaddr", dynlib: ws2dll.}
+  stdcall, importc: "gethostbyaddr", dynlib: ws2dll, sideEffect.}
 
 proc gethostbyname*(name: cstring): ptr Hostent {.
-  stdcall, importc: "gethostbyname", dynlib: ws2dll.}
+  stdcall, importc: "gethostbyname", dynlib: ws2dll, sideEffect.}
 
 proc gethostname*(hostname: cstring, len: cint): cint {.
-  stdcall, importc: "gethostname", dynlib: ws2dll.}
+  stdcall, importc: "gethostname", dynlib: ws2dll, sideEffect.}
+
+proc getprotobyname*(
+  name: cstring
+): ptr Protoent {.stdcall, importc: "getprotobyname", dynlib: ws2dll, sideEffect.}
+
+proc getprotobynumber*(
+  proto: cint
+): ptr Protoent {.stdcall, importc: "getprotobynumber", dynlib: ws2dll, sideEffect.}
 
 proc socket*(af, typ, protocol: cint): SocketHandle {.
   stdcall, importc: "socket", dynlib: ws2dll.}
@@ -656,7 +577,7 @@ proc getaddrinfo*(nodename, servname: cstring, hints: ptr AddrInfo,
                   res: var ptr AddrInfo): cint {.
   stdcall, importc: "getaddrinfo", dynlib: ws2dll.}
 
-proc freeaddrinfo*(ai: ptr AddrInfo) {.
+proc freeAddrInfo*(ai: ptr AddrInfo) {.
   stdcall, importc: "freeaddrinfo", dynlib: ws2dll.}
 
 proc inet_ntoa*(i: InAddr): cstring {.
@@ -668,7 +589,6 @@ const
 type
   WOHandleArray* = array[0..MAXIMUM_WAIT_OBJECTS - 1, Handle]
   PWOHandleArray* = ptr WOHandleArray
-{.deprecated: [TWOHandleArray: WOHandleArray].}
 
 proc waitForMultipleObjects*(nCount: DWORD, lpHandles: PWOHandleArray,
                              bWaitAll: WINBOOL, dwMilliseconds: DWORD): DWORD{.
@@ -692,6 +612,10 @@ const
   FILE_BEGIN* = 0'i32
   INVALID_SET_FILE_POINTER* = -1'i32
   NO_ERROR* = 0'i32
+  PAGE_NOACCESS* = 0x01'i32
+  PAGE_EXECUTE* = 0x10'i32
+  PAGE_EXECUTE_READ* = 0x20'i32
+  PAGE_EXECUTE_READWRITE* = 0x40'i32
   PAGE_READONLY* = 2'i32
   PAGE_READWRITE* = 4'i32
   FILE_MAP_READ* = 4'i32
@@ -704,44 +628,46 @@ const
 
 # Error Constants
 const
-  ERROR_FILE_NOT_FOUND* = 2
+  ERROR_FILE_NOT_FOUND* = 2 ## https://docs.microsoft.com/en-us/windows/win32/debug/system-error-codes--0-499-
   ERROR_PATH_NOT_FOUND* = 3
   ERROR_ACCESS_DENIED* = 5
   ERROR_NO_MORE_FILES* = 18
   ERROR_LOCK_VIOLATION* = 33
   ERROR_HANDLE_EOF* = 38
+  ERROR_FILE_EXISTS* = 80
   ERROR_BAD_ARGUMENTS* = 165
 
-proc duplicateHandle*(hSourceProcessHandle: HANDLE, hSourceHandle: HANDLE,
-                      hTargetProcessHandle: HANDLE,
-                      lpTargetHandle: ptr HANDLE,
+proc duplicateHandle*(hSourceProcessHandle: Handle, hSourceHandle: Handle,
+                      hTargetProcessHandle: Handle,
+                      lpTargetHandle: ptr Handle,
                       dwDesiredAccess: DWORD, bInheritHandle: WINBOOL,
                       dwOptions: DWORD): WINBOOL{.stdcall, dynlib: "kernel32",
     importc: "DuplicateHandle".}
 
-proc setHandleInformation*(hObject: HANDLE, dwMask: DWORD,
+proc getHandleInformation*(hObject: Handle, lpdwFlags: ptr DWORD): WINBOOL {.
+    stdcall, dynlib: "kernel32", importc: "GetHandleInformation".}
+
+proc setHandleInformation*(hObject: Handle, dwMask: DWORD,
                            dwFlags: DWORD): WINBOOL {.stdcall,
     dynlib: "kernel32", importc: "SetHandleInformation".}
 
-proc getCurrentProcess*(): HANDLE{.stdcall, dynlib: "kernel32",
+proc getCurrentProcess*(): Handle{.stdcall, dynlib: "kernel32",
                                    importc: "GetCurrentProcess".}
 
-when useWinUnicode:
-  proc createFileW*(lpFileName: WideCString, dwDesiredAccess, dwShareMode: DWORD,
-                    lpSecurityAttributes: pointer,
-                    dwCreationDisposition, dwFlagsAndAttributes: DWORD,
-                    hTemplateFile: Handle): Handle {.
-      stdcall, dynlib: "kernel32", importc: "CreateFileW".}
-  proc deleteFileW*(pathName: WideCString): int32 {.
-    importc: "DeleteFileW", dynlib: "kernel32", stdcall.}
-else:
-  proc createFileA*(lpFileName: cstring, dwDesiredAccess, dwShareMode: DWORD,
-                    lpSecurityAttributes: pointer,
-                    dwCreationDisposition, dwFlagsAndAttributes: DWORD,
-                    hTemplateFile: Handle): Handle {.
-      stdcall, dynlib: "kernel32", importc: "CreateFileA".}
-  proc deleteFileA*(pathName: cstring): int32 {.
-    importc: "DeleteFileA", dynlib: "kernel32", stdcall.}
+proc createFileW*(lpFileName: WideCString, dwDesiredAccess, dwShareMode: DWORD,
+                  lpSecurityAttributes: pointer,
+                  dwCreationDisposition, dwFlagsAndAttributes: DWORD,
+                  hTemplateFile: Handle): Handle {.
+    stdcall, dynlib: "kernel32", importc: "CreateFileW".}
+proc deleteFileW*(pathName: WideCString): int32 {.
+  importc: "DeleteFileW", dynlib: "kernel32", stdcall.}
+proc createFileA*(lpFileName: cstring, dwDesiredAccess, dwShareMode: DWORD,
+                  lpSecurityAttributes: pointer,
+                  dwCreationDisposition, dwFlagsAndAttributes: DWORD,
+                  hTemplateFile: Handle): Handle {.
+    stdcall, dynlib: "kernel32", importc: "CreateFileA".}
+proc deleteFileA*(pathName: cstring): int32 {.
+  importc: "DeleteFileA", dynlib: "kernel32", stdcall.}
 
 proc setEndOfFile*(hFile: Handle): WINBOOL {.stdcall, dynlib: "kernel32",
     importc: "SetEndOfFile".}
@@ -754,9 +680,16 @@ proc setFilePointer*(hFile: Handle, lDistanceToMove: LONG,
 proc getFileSize*(hFile: Handle, lpFileSizeHigh: ptr DWORD): DWORD{.stdcall,
     dynlib: "kernel32", importc: "GetFileSize".}
 
+when defined(cpu32):
+  type
+    WinSizeT* = uint32
+else:
+  type
+    WinSizeT* = uint64
+
 proc mapViewOfFileEx*(hFileMappingObject: Handle, dwDesiredAccess: DWORD,
                       dwFileOffsetHigh, dwFileOffsetLow: DWORD,
-                      dwNumberOfBytesToMap: DWORD,
+                      dwNumberOfBytesToMap: WinSizeT,
                       lpBaseAddress: pointer): pointer{.
     stdcall, dynlib: "kernel32", importc: "MapViewOfFileEx".}
 
@@ -767,13 +700,6 @@ proc createFileMappingW*(hFile: Handle,
                        lpName: pointer): Handle {.
   stdcall, dynlib: "kernel32", importc: "CreateFileMappingW".}
 
-when not useWinUnicode:
-  proc createFileMappingA*(hFile: Handle,
-                           lpFileMappingAttributes: pointer,
-                           flProtect, dwMaximumSizeHigh: DWORD,
-                           dwMaximumSizeLow: DWORD, lpName: cstring): Handle {.
-      stdcall, dynlib: "kernel32", importc: "CreateFileMappingA".}
-
 proc unmapViewOfFile*(lpBaseAddress: pointer): WINBOOL {.stdcall,
     dynlib: "kernel32", importc: "UnmapViewOfFile".}
 
@@ -793,12 +719,11 @@ type
   POVERLAPPED_COMPLETION_ROUTINE* = proc (para1: DWORD, para2: DWORD,
       para3: POVERLAPPED){.stdcall.}
 
-  GUID* {.final, pure.} = object
+  GUID* = object
     D1*: int32
     D2*: int16
     D3*: int16
     D4*: array[0..7, int8]
-{.deprecated: [TOVERLAPPED: OVERLAPPED, TGUID: GUID].}
 
 const
   ERROR_IO_PENDING* = 997 # a.k.a WSA_IO_PENDING
@@ -813,6 +738,7 @@ const
   WSAEINPROGRESS* = 10036
   WSAEINTR* = 10004
   WSAEWOULDBLOCK* = 10035
+  WSAESHUTDOWN* = 10058
   ERROR_NETNAME_DELETED* = 64
   STATUS_PENDING* = 0x103
 
@@ -838,9 +764,9 @@ template hasOverlappedIoCompleted*(lpOverlapped): bool =
   (cast[uint](lpOverlapped.internal) != STATUS_PENDING)
 
 const
- IOC_OUT* = 0x40000000
- IOC_IN*  = 0x80000000
- IOC_WS2* = 0x08000000
+ IOC_OUT* = 0x40000000'i32
+ IOC_IN*  = 0x80000000'i32
+ IOC_WS2* = 0x08000000'i32
  IOC_INOUT* = IOC_IN or IOC_OUT
 
 template WSAIORW*(x,y): untyped = (IOC_INOUT or x or y)
@@ -905,8 +831,11 @@ proc getProcessTimes*(hProcess: Handle; lpCreationTime, lpExitTime,
   lpKernelTime, lpUserTime: var FILETIME): WINBOOL {.stdcall,
   dynlib: "kernel32", importc: "GetProcessTimes".}
 
+proc getSystemTimePreciseAsFileTime*(lpSystemTimeAsFileTime: var FILETIME) {.
+  importc: "GetSystemTimePreciseAsFileTime", dynlib: "kernel32", stdcall, sideEffect.}
+
 type inet_ntop_proc = proc(family: cint, paddr: pointer, pStringBuffer: cstring,
-                      stringBufSize: int32): cstring {.gcsafe, stdcall.}
+                      stringBufSize: int32): cstring {.gcsafe, stdcall, tags: [].}
 
 var inet_ntop_real: inet_ntop_proc = nil
 
@@ -946,7 +875,7 @@ proc inet_ntop*(family: cint, paddr: pointer, pStringBuffer: cstring,
                   stringBufSize: int32): cstring {.stdcall.} =
   var ver: OSVERSIONINFO
   ver.dwOSVersionInfoSize = sizeof(ver).DWORD
-  let res = when useWinUnicode: getVersionExW(ver.addr) else: getVersionExA(ver.addr)
+  let res = getVersionExW(ver.addr)
   if res == 0:
     result = nil
   elif ver.dwMajorVersion >= 6:
@@ -964,13 +893,13 @@ type
                             dwRemoteAddressLength: DWORD,
                             lpdwBytesReceived: ptr DWORD,
                             lpOverlapped: POVERLAPPED): bool {.
-                            stdcall,gcsafe.}
+                            stdcall, gcsafe, raises: [].}
 
   WSAPROC_CONNECTEX* = proc (s: SocketHandle, name: ptr SockAddr, namelen: cint,
                              lpSendBuffer: pointer, dwSendDataLength: DWORD,
                              lpdwBytesSent: ptr DWORD,
                              lpOverlapped: POVERLAPPED): bool {.
-                             stdcall,gcsafe.}
+                             stdcall, gcsafe, raises: [].}
 
   WSAPROC_GETACCEPTEXSOCKADDRS* = proc(lpOutputBuffer: pointer,
                                        dwReceiveDataLength: DWORD,
@@ -980,7 +909,7 @@ type
                                        LocalSockaddrLength: ptr cint,
                                        RemoteSockaddr: ptr PSockAddr,
                                        RemoteSockaddrLength: ptr cint) {.
-                                       stdcall,gcsafe.}
+                                       stdcall, gcsafe, raises: [].}
 
 const
   WT_EXECUTEDEFAULT* = 0x00000000'i32
@@ -1008,9 +937,9 @@ const
   PROCESS_QUERY_LIMITED_INFORMATION* = 0x00001000'i32
   PROCESS_SET_LIMITED_INFORMATION* = 0x00002000'i32
 type
-  WAITORTIMERCALLBACK* = proc(para1: pointer, para2: int32): void {.stdcall.}
+  WAITORTIMERCALLBACK* = proc(para1: pointer, para2: int32) {.stdcall.}
 
-proc postQueuedCompletionStatus*(CompletionPort: HANDLE,
+proc postQueuedCompletionStatus*(CompletionPort: Handle,
                                 dwNumberOfBytesTransferred: DWORD,
                                 dwCompletionKey: ULONG_PTR,
                                 lpOverlapped: pointer): bool
@@ -1023,23 +952,17 @@ proc registerWaitForSingleObject*(phNewWaitObject: ptr Handle, hObject: Handle,
                                  dwFlags: ULONG): bool
      {.stdcall, dynlib: "kernel32", importc: "RegisterWaitForSingleObject".}
 
-proc unregisterWait*(WaitHandle: HANDLE): DWORD
+proc unregisterWait*(WaitHandle: Handle): DWORD
      {.stdcall, dynlib: "kernel32", importc: "UnregisterWait".}
 
 proc openProcess*(dwDesiredAccess: DWORD, bInheritHandle: WINBOOL,
                     dwProcessId: DWORD): Handle
      {.stdcall, dynlib: "kernel32", importc: "OpenProcess".}
 
-when defined(useWinAnsi):
-  proc createEvent*(lpEventAttributes: ptr SECURITY_ATTRIBUTES,
-                    bManualReset: DWORD, bInitialState: DWORD,
-                    lpName: cstring): Handle
-       {.stdcall, dynlib: "kernel32", importc: "CreateEventA".}
-else:
-  proc createEvent*(lpEventAttributes: ptr SECURITY_ATTRIBUTES,
-                    bManualReset: DWORD, bInitialState: DWORD,
-                    lpName: ptr Utf16Char): Handle
-       {.stdcall, dynlib: "kernel32", importc: "CreateEventW".}
+proc createEvent*(lpEventAttributes: ptr SECURITY_ATTRIBUTES,
+                  bManualReset: DWORD, bInitialState: DWORD,
+                  lpName: ptr Utf16Char): Handle
+     {.stdcall, dynlib: "kernel32", importc: "CreateEventW".}
 
 proc setEvent*(hEvent: Handle): cint
      {.stdcall, dynlib: "kernel32", importc: "SetEvent".}
@@ -1071,7 +994,7 @@ proc wsaResetEvent*(hEvent: Handle): bool
      {.stdcall, importc: "WSAResetEvent", dynlib: "ws2_32.dll".}
 
 type
-  KEY_EVENT_RECORD* {.final, pure.} = object
+  KEY_EVENT_RECORD* = object
     eventType*: int16
     bKeyDown*: WINBOOL
     wRepeatCount*: int16
@@ -1080,17 +1003,12 @@ type
     uChar*: int16
     dwControlKeyState*: DWORD
 
-when defined(useWinAnsi):
-  proc readConsoleInput*(hConsoleInput: Handle, lpBuffer: pointer, nLength: cint,
-                        lpNumberOfEventsRead: ptr cint): cint
-       {.stdcall, dynlib: "kernel32", importc: "ReadConsoleInputA".}
-else:
-  proc readConsoleInput*(hConsoleInput: Handle, lpBuffer: pointer, nLength: cint,
-                        lpNumberOfEventsRead: ptr cint): cint
-       {.stdcall, dynlib: "kernel32", importc: "ReadConsoleInputW".}
+proc readConsoleInput*(hConsoleInput: Handle, lpBuffer: pointer, nLength: cint,
+                      lpNumberOfEventsRead: ptr cint): cint
+     {.stdcall, dynlib: "kernel32", importc: "ReadConsoleInputW".}
 
 type
-  LPFIBER_START_ROUTINE* = proc (param: pointer): void {.stdcall.}
+  LPFIBER_START_ROUTINE* = proc (param: pointer) {.stdcall.}
 
 const
   FIBER_FLAG_FLOAT_SWITCH* = 0x01
@@ -1099,17 +1017,57 @@ proc CreateFiber*(stackSize: int, fn: LPFIBER_START_ROUTINE, param: pointer): po
 proc CreateFiberEx*(stkCommit: int, stkReserve: int, flags: int32, fn: LPFIBER_START_ROUTINE, param: pointer): pointer {.stdcall, discardable, dynlib: "kernel32", importc.}
 proc ConvertThreadToFiber*(param: pointer): pointer {.stdcall, discardable, dynlib: "kernel32", importc.}
 proc ConvertThreadToFiberEx*(param: pointer, flags: int32): pointer {.stdcall, discardable, dynlib: "kernel32", importc.}
-proc DeleteFiber*(fiber: pointer): void {.stdcall, discardable, dynlib: "kernel32", importc.}
-proc SwitchToFiber*(fiber: pointer): void {.stdcall, discardable, dynlib: "kernel32", importc.}
-proc GetCurrentFiber*(): pointer {.stdcall, importc, header: "Windows.h".}
+proc DeleteFiber*(fiber: pointer) {.stdcall, discardable, dynlib: "kernel32", importc.}
+proc SwitchToFiber*(fiber: pointer) {.stdcall, discardable, dynlib: "kernel32", importc.}
+proc GetCurrentFiber*(): pointer {.stdcall, importc, header: "windows.h".}
 
 proc toFILETIME*(t: int64): FILETIME =
-  ## Convert the Windows file time timestamp ``t`` to ``FILETIME``.
+  ## Convert the Windows file time timestamp `t` to `FILETIME`.
   result = FILETIME(dwLowDateTime: cast[DWORD](t), dwHighDateTime: DWORD(t shr 32))
 
 type
   LPFILETIME* = ptr FILETIME
 
-proc setFileTime*(hFile: HANDLE, lpCreationTime: LPFILETIME,
+proc setFileTime*(hFile: Handle, lpCreationTime: LPFILETIME,
                  lpLastAccessTime: LPFILETIME, lpLastWriteTime: LPFILETIME): WINBOOL
      {.stdcall, dynlib: "kernel32", importc: "SetFileTime".}
+
+type
+  # https://docs.microsoft.com/en-us/windows/win32/api/winnt/ns-winnt-sid_identifier_authority
+  SID_IDENTIFIER_AUTHORITY* {.importc, header: "<windows.h>".} = object
+    value* {.importc: "Value".}: array[6, BYTE]
+  # https://docs.microsoft.com/en-us/windows/win32/api/winnt/ns-winnt-sid
+  SID* {.importc, header: "<windows.h>".} = object
+    Revision: BYTE
+    SubAuthorityCount: BYTE
+    IdentifierAuthority: SID_IDENTIFIER_AUTHORITY
+    SubAuthority: ptr ptr DWORD
+  PSID* = ptr SID
+
+const
+  # https://docs.microsoft.com/en-us/windows/win32/secauthz/sid-components
+  # https://github.com/mirror/mingw-w64/blob/84c950bdab7c999ace49fe8383856be77f88c4a8/mingw-w64-headers/include/winnt.h#L2994
+  SECURITY_NT_AUTHORITY* = [BYTE(0), BYTE(0), BYTE(0), BYTE(0), BYTE(0), BYTE(5)]
+  SECURITY_BUILTIN_DOMAIN_RID* = 32
+  DOMAIN_ALIAS_RID_ADMINS* = 544
+
+proc allocateAndInitializeSid*(pIdentifierAuthority: ptr SID_IDENTIFIER_AUTHORITY,
+                               nSubAuthorityCount: BYTE,
+                               nSubAuthority0: DWORD,
+                               nSubAuthority1: DWORD,
+                               nSubAuthority2: DWORD,
+                               nSubAuthority3: DWORD,
+                               nSubAuthority4: DWORD,
+                               nSubAuthority5: DWORD,
+                               nSubAuthority6: DWORD,
+                               nSubAuthority7: DWORD,
+                               pSid: ptr PSID): WINBOOL
+     {.stdcall, dynlib: "Advapi32", importc: "AllocateAndInitializeSid".}
+proc checkTokenMembership*(tokenHandle: Handle, sidToCheck: PSID,
+                           isMember: PBOOL): WINBOOL
+     {.stdcall, dynlib: "Advapi32", importc: "CheckTokenMembership".}
+proc freeSid*(pSid: PSID): PSID
+     {.stdcall, dynlib: "Advapi32", importc: "FreeSid".}
+
+when defined(nimHasStyleChecks):
+  {.pop.} # {.push styleChecks: off.}