#
#
# Nim's Runtime Library
# (c) Copyright 2016 Andreas Rumpf
#
# See the file "copying.txt", included in this
# distribution, for details about the copyright.
#
## This module is experimental and its interface may change.
import std/oserrors
when defined(nimPreviewSlimSystem):
import std/widestrs
type
HKEY* = uint
const
HKEY_LOCAL_MACHINE* = HKEY(0x80000002u)
HKEY_CURRENT_USER* = HKEY(2147483649)
RRF_RT_ANY = 0x0000ffff
KEY_WOW64_64KEY = 0x0100
KEY_WOW64_32KEY = 0x0200
KEY_READ = 0x00020019
REG_SZ = 1
proc regOpenKeyEx(hKey: HKEY, lpSubKey: WideCString, ulOptions: int32,
samDesired: int32,
phkResult: var HKEY): int32 {.
importc: "RegOpenKeyExW", dynlib: "Advapi32.dll", stdcall.}
proc regCloseKey(hkey: HKEY): int32 {.
importc: "RegCloseKey", dynlib: "Advapi32.dll", stdcall.}
proc regGetValue(key: HKEY, lpSubKey, lpValue: WideCString;
dwFlags: int32 = RRF_RT_ANY, pdwType: ptr int32,
pvData: pointer,
pcbData: ptr int32): int32 {.
importc: "RegGetValueW", dynlib: "Advapi32.dll", stdcall.}
template call(f) =
let err = f
if err != 0:
raiseOSError(err.OSErrorCode, astToStr(f))
proc getUnicodeValue*(path, key: string; handle: HKEY): string =
let hh = newWideCString path
let kk = newWideCString key
var bufSize: int32
# try a couple of different flag settings:
var flags: int32 = RRF_RT_ANY
let err = regGetValue(handle, hh, kk, flags, nil, nil, addr bufSize)
if err != 0:
var newHandle: HKEY
call regOpenKeyEx(handle, hh, 0, KEY_READ or KEY_WOW64_64KEY, newHandle)
call regGetValue(newHandle, nil, kk, flags, nil, nil, addr bufSize)
if bufSize > 0:
var res = newWideCString(bufSize)
call regGetValue(newHandle, nil, kk, flags, nil, addr res[0],
addr bufSize)
result = res $ bufSize
call regCloseKey(newHandle)
else:
if bufSize > 0:
var res = newWideCString(bufSize)
call regGetValue(handle, hh, kk, flags, nil, addr res[0],
addr bufSize)
result = res $ bufSize
proc regSetValue(key: HKEY, lpSubKey, lpValueName: WideCString,
dwType: int32; lpData: WideCString; cbData: int32): int32 {.
importc: "RegSetKeyValueW", dynlib: "Advapi32.dll", stdcall.}
proc setUnicodeValue*(path, key, val: string; handle: HKEY) =
let hh = newWideCString path
let kk = newWideCString key
let vv = newWideCString val
call regSetValue(handle, hh, kk, REG_SZ, vv, (vv.len.int32+1)*2)