Page Menu
Home
GnuPG
Search
Configure Global Search
Log In
Files
F34123787
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Size
22 KB
Subscribers
None
View Options
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index abe8f96..385b302 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -1,16 +1,19 @@
# Copyright (C) 2018 Intevation GmbH <info@intevation.de>
#
# This file is Free Software under the GNU GPL (v>=2)
# and comes with ABSOLUTELY NO WARRANTY!
# See LICENSE.txt for details.
include_directories(${Qt5Core_INCLUDE_DIRS})
include_directories(${CMAKE_CURRENT_SOURCE_DIR})
include_directories(util)
add_subdirectory(resolver)
add_subdirectory(overlayer)
add_subdirectory(gpgolconfig)
add_subdirectory(gpgolkeyadder)
+if (WIN32)
+ add_subdirectory(gpga)
+endif ()
diff --git a/src/gpga/CMakeLists.txt b/src/gpga/CMakeLists.txt
new file mode 100644
index 0000000..1e8e8c3
--- /dev/null
+++ b/src/gpga/CMakeLists.txt
@@ -0,0 +1,28 @@
+# Copyright (C) 2018 Andre Heinecke <aheinecke@gnupg.com>
+#
+# This file is Free Software under the GNU GPL (v>=2)
+# and comes with ABSOLUTELY NO WARRANTY!
+# See LICENSE.txt for details.
+
+set(EXECUTABLE_NAME "gpga")
+
+set(EXECUTABLE_SRC
+ flange.cpp
+ ../util/debug.cpp
+ ../util/w32-util.cpp
+ gpga.def
+)
+
+add_library (${EXECUTABLE_NAME}
+ ${EXECUTABLE_SRC}
+)
+
+target_link_libraries(${EXECUTABLE_NAME}
+ PRIVATE Gpgmepp
+)
+
+set_target_properties(${EXECUTABLE_NAME} PROPERTIES LINK_FLAGS "-municode")
+
+set_target_properties(${EXECUTABLE_NAME} PROPERTIES PREFIX "")
+
+install(TARGETS ${EXECUTABLE_NAME} DESTINATION bin)
diff --git a/src/gpga/comhelp.h b/src/gpga/comhelp.h
new file mode 100644
index 0000000..bafe203
--- /dev/null
+++ b/src/gpga/comhelp.h
@@ -0,0 +1,19 @@
+#ifndef COMHELP_H
+#define COMHELP_H
+/* Copyright (C) 2018 by Andre Heinecke <aheinecke@gnupg.com>
+ *
+ * This file is Free Software under the GNU GPL (v>=2)
+ * and comes with ABSOLUTELY NO WARRANTY!
+ * See LICENSE.txt for details.
+ */
+
+#define DECLARE_IUNKNOWN \
+
+#define SFGAO_FOLDER 0x20000000
+#define SFGAO_HASSUBFOLDER 0x80000000
+#define SFGAO_CANDELETE 0x00000020
+#define SFGAO_CANRENAME 0x00000010
+#define SFGAO_HASPROPSHEET 0x00000040
+
+
+#endif // COMHELP_H
diff --git a/src/gpga/flange.cpp b/src/gpga/flange.cpp
new file mode 100644
index 0000000..b77d6e5
--- /dev/null
+++ b/src/gpga/flange.cpp
@@ -0,0 +1,271 @@
+/* Copyright (C) 2018 by Andre Heinecke <aheinecke@gnupg.com>
+ *
+ * This file is Free Software under the GNU GPL (v>=2)
+ * and comes with ABSOLUTELY NO WARRANTY!
+ * See LICENSE.txt for details.
+ */
+
+#include "flange.h"
+#include "debug.h"
+#include "comhelp.h"
+#include "w32-util.h"
+
+#include "shlobj.h"
+
+/** @file Code to flange to the Windows explorer.
+ *
+ * This file contains the Windows and COM API requirements
+ * to properly work as an explorer extension.
+ */
+
+#ifndef INITGUID
+/* Include every header that defines a GUID below this
+ macro. Otherwise the GUID's will only be declared and
+ not defined. */
+#define INITGUID
+#endif
+#include <initguid.h>
+
+#define MY_CLSID_STR "CCD955E4-5C16-4A33-AFDA-A8947A94946C"
+DEFINE_GUID(MY_CLSID, 0xCCD955E4, 0x5C16, 0x4A33,
+ 0xAF, 0xDA, 0xA8, 0x94, 0x7A, 0x94, 0x94, 0x6C);
+#define MY_PROGID "GpgArchive"
+
+static HINSTANCE s_hinst;
+static FlangeFactory *s_factory;
+
+static void init_logging()
+{
+ static bool wasDone;
+ if (!wasDone) {
+ gpgrt_log_set_sink("c:\\tmp\\gpga.txt", nullptr, -1);
+ wasDone = true;
+ }
+}
+
+/* Here we go */
+STDAPI DllGetClassObject (REFCLSID rclsid, REFIID riid, LPVOID* ppv)
+{
+ init_logging ();
+
+ log_debug ("Get class object for clsid'" GUID_FMT "'",
+ GUID_ARG(riid));
+ if (!ppv) {
+ return E_POINTER;
+ }
+ *ppv = nullptr;
+
+ if (rclsid == MY_CLSID) {
+ return FlangeFactory::instance()->QueryInterface(riid, ppv);
+ }
+
+ return CLASS_E_CLASSNOTAVAILABLE;
+}
+
+STDMETHODIMP FlangeFactory::LockServer (BOOL lock)
+{
+ if (lock) {
+ AddRef();
+ } else {
+ Release();
+ }
+ return S_OK;
+}
+
+STDMETHODIMP FlangeFactory::CreateInstance (LPUNKNOWN unknown,
+ REFIID riid,
+ LPVOID* ppvObj)
+{
+ log_debug ("CreateInstance with id '" GUID_FMT "'",
+ GUID_ARG(riid));
+
+ return E_NOINTERFACE;
+}
+
+STDMETHODIMP FlangeFactory::QueryInterface (REFIID riid, void **ppv)
+{
+ log_debug ("QueryInterface:'" GUID_FMT "'",
+ GUID_ARG(riid));
+
+ if (!ppv) {
+ return E_POINTER;
+ }
+
+ *ppv = nullptr;
+
+ /* The static casts ensure that the virtual function table
+ layout of the returned object is correct. */
+ if (riid == IID_IUnknown)
+ *ppv = static_cast<IUnknown *> (this);
+ else if (riid == IID_IClassFactory)
+ *ppv = static_cast<IClassFactory *> (this);
+ else
+ return E_NOINTERFACE;
+
+ reinterpret_cast<IUnknown *>(*ppv)->AddRef ();
+
+ return S_OK;
+}
+
+FlangeFactory *FlangeFactory::instance()
+{
+ if (!s_factory) {
+ s_factory = new FlangeFactory();
+ }
+ return s_factory;
+}
+
+STDMETHODIMP_(ULONG) FlangeFactory::Release()
+{
+ ULONG lCount = --m_lRef;
+ if (!lCount) {
+ delete this;
+ }
+ return lCount;
+}
+
+FlangeFactory::~FlangeFactory()
+{
+ s_factory = nullptr;
+}
+
+STDAPI DllCanUnloadNow()
+{
+ return s_factory == nullptr;
+}
+
+STDAPI DllUnregisterServer()
+{
+ HKEY root_key;
+
+ if (W32::isElevated()) {
+ root_key = HKEY_LOCAL_MACHINE;
+ } else {
+ root_key = HKEY_CURRENT_USER;
+ }
+
+ log_debug("Un Registering shell extension.");
+
+ RegDeleteKeyA(root_key, "Software\\Classes\\.gpga");
+ RegDeleteKeyA(root_key, "Software\\Classes\\GPGArchive");
+ RegDeleteKeyA(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}");
+}
+
+STDAPI DllRegisterServer()
+{
+ const char *root_key;
+
+ const auto gpg4windir = W32::getGpg4winDir();
+
+ init_logging ();
+
+ log_debug ("Debug");
+
+ if (gpg4windir.empty()) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+
+ char module_path[MAX_PATH + 1];
+ if (!s_hinst || GetModuleFileNameA (s_hinst, module_path,
+ MAX_PATH) == MAX_PATH) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+
+ if (W32::isElevated()) {
+ root_key = "HKEY_LOCAL_MACHINE";
+ } else {
+ root_key = "HKEY_CURRENT_USER";
+ }
+
+ log_debug("Registering shell extension.");
+
+ /* Tar file is: {2B3256E4-49AA-11D3-8229-0050AE509054} */
+
+ /* Register File extension */
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\.gpga",
+ nullptr, MY_PROGID)) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\GPGArchive",
+ nullptr, "GnuPG Archive Extension")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\GPGArchive",
+ "FriendlyTypeName", "GnuPG Archive")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\GPGArchive\\ShellEx",
+ nullptr, "")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\GPGArchive\\CLSID",
+ nullptr, "{" MY_CLSID_STR "}")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\GPGArchive\\CLSID",
+ nullptr, "{" MY_CLSID_STR "}")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}",
+ nullptr, "GnuPG Archive Extension")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ std::string iconPath = gpg4windir + "\\share\\gpg4win\\file-ext.ico";
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}",
+ "Default Icon", iconPath.c_str())) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}\\InprocServer32",
+ nullptr, module_path)) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}\\InprocServer32",
+ "ThreadingModel", "Apartment")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}\\ProgID",
+ nullptr, MY_PROGID)) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ if (!W32::writeRegStr(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}\\Implemented Categories\\"
+ "{00021490-0000-0000-C000-000000000046}",
+ nullptr, "Browsable Shell Extension")) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+ /* See: https://msdn.microsoft.com/en-us/library/windows/desktop/cc144093(v=vs.85).aspx */
+ if (!W32::writeRegDword(root_key, "Software\\Classes\\CLSID\\{" MY_CLSID_STR "}\\ShellFolder",
+ "Attributes", SFGAO_FOLDER | SFGAO_CANRENAME | SFGAO_CANDELETE)) {
+ STRANGEPOINT;
+ return FALSE;
+ }
+
+ /* Notify the shell about the change. */
+ SHChangeNotify (SHCNE_ASSOCCHANGED, SHCNF_IDLIST, NULL, NULL);
+}
+
+STDAPI DllMain (HINSTANCE hinst, DWORD reason, LPVOID)
+{
+ if (reason == DLL_PROCESS_ATTACH) {
+ s_hinst = hinst;
+ // Do init of GPGME
+ init_logging ();
+ } else if (reason == DLL_PROCESS_DETACH) {
+ log_debug ("Detached");
+ }
+
+ return TRUE;
+}
diff --git a/src/gpga/flange.h b/src/gpga/flange.h
new file mode 100644
index 0000000..7801824
--- /dev/null
+++ b/src/gpga/flange.h
@@ -0,0 +1,36 @@
+#ifndef FLANGE_H
+#define FLANGE_H
+/* Copyright (C) 2018 by Andre Heinecke <aheinecke@gnupg.com>
+ *
+ * This file is Free Software under the GNU GPL (v>=2)
+ * and comes with ABSOLUTELY NO WARRANTY!
+ * See LICENSE.txt for details.
+ */
+
+#include <windows.h>
+
+class FlangeFactory: public IClassFactory
+{
+protected:
+ FlangeFactory(): m_lRef(0) {}
+
+public:
+ virtual ~FlangeFactory();
+
+ STDMETHODIMP QueryInterface (REFIID riid, LPVOID* ppvObj);
+ STDMETHODIMP_(ULONG) AddRef() { ++m_lRef; return m_lRef; };
+ STDMETHODIMP_(ULONG) Release();
+
+ /* IClassFactory */
+ STDMETHODIMP CreateInstance (LPUNKNOWN unknown, REFIID riid,
+ LPVOID* ppvObj);
+ STDMETHODIMP LockServer (BOOL lock);
+
+ /* Custom */
+ static FlangeFactory *instance();
+
+private:
+ ULONG m_lRef;
+};
+
+#endif // FLANGE_H
diff --git a/src/gpga/gpga.def b/src/gpga/gpga.def
new file mode 100644
index 0000000..da453f3
--- /dev/null
+++ b/src/gpga/gpga.def
@@ -0,0 +1,7 @@
+LIBRARY "gpga"
+DESCRIPTION 'GnuPG Archive Extension'
+
+EXPORTS
+ DllRegisterServer = DllRegisterServer@0 @1 PRIVATE
+ DllUnregisterServer = DllUnregisterServer@0 @2 PRIVATE
+ DllGetClassObject = DllGetClassObject@12 @3 PRIVATE
diff --git a/src/util/debug.cpp b/src/util/debug.cpp
new file mode 100644
index 0000000..1fec4cd
--- /dev/null
+++ b/src/util/debug.cpp
@@ -0,0 +1,16 @@
+/* Copyright (C) 2018 by Andre Heinecke <aheinecke@gnupg.com>
+ *
+ * This file is Free Software under the GNU GPL (v>=2)
+ * and comes with ABSOLUTELY NO WARRANTY!
+ * See LICENSE.txt for details.
+ */
+
+#include <string.h>
+
+const char *
+log_srcname (const char *file)
+{
+ const char *s = strrchr (file, '/');
+ return s? s+1:file;
+}
+
diff --git a/src/util/debug.h b/src/util/debug.h
new file mode 100644
index 0000000..e68fca4
--- /dev/null
+++ b/src/util/debug.h
@@ -0,0 +1,29 @@
+#ifndef GPG4WIN_DEBUG_H
+#define GPG4WIN_DEBUG_H
+/* Copyright (C) 2018 by Andre Heinecke <aheinecke@gnupg.com>
+ *
+ * This file is Free Software under the GNU GPL (v>=2)
+ * and comes with ABSOLUTELY NO WARRANTY!
+ * See LICENSE.txt for details.
+ */
+
+
+#include <gpg-error.h>
+
+const char *log_srcname (const char *s);
+
+#define SRCNAME log_srcname (__FILE__)
+
+#define log_debug(format, ...) \
+ gpgrt_log_debug("%s:%s: " format, SRCNAME, __func__, ##__VA_ARGS__)
+
+
+#define STRANGEPOINT log_debug ("%s:%s:%d:UNEXPECTED", \
+ __LINE__);
+
+#define GUID_FMT "{%08lX-%04hX-%04hX-%02hX%02hX-%02hX%02hX%02hX%02hX%02hX%02hX}"
+#define GUID_ARG(x) (x).Data1, (x).Data2, (x).Data3, (x).Data4[0], \
+ (x).Data4[1], (x).Data4[2], (x).Data4[3], (x).Data4[4], \
+ (x).Data4[5], (x).Data4[6], (x).Data4[7]
+
+#endif // GPG4WIN_DEBUG_H
diff --git a/src/util/w32-util.cpp b/src/util/w32-util.cpp
index cdb962a..884dafb 100644
--- a/src/util/w32-util.cpp
+++ b/src/util/w32-util.cpp
@@ -1,288 +1,320 @@
/* Copyright (C) 2018 by Intevation GmbH <info@intevation.de>
*
* This file is Free Software under the GNU GPL (v>=2)
* and comes with ABSOLUTELY NO WARRANTY!
* See LICENSE.txt for details.
*/
#include <stdio.h>
#include "w32-util.h"
#include <unistd.h>
#ifdef _WIN32
# include <windows.h>
#endif
-#include <QWindow>
-#include <QDebug>
-
#define SLDIR "\\share\\locale"
namespace W32 {
std::string getGpg4winLocaleDir()
{
const auto instdir = getGpg4winDir();
if (instdir.empty()) {
return std::string();
}
return instdir + SLDIR;
}
std::string getGpg4winDir()
{
const auto tmp = readRegStr(nullptr, GPG4WIN_REGKEY_3,
"Install Directory");
if (tmp.empty()) {
return std::string();
}
if (!access(tmp.c_str(), R_OK)) {
return tmp;
} else {
fprintf (stderr, "Failed to access: %s\n", tmp.c_str());
}
return std::string();
}
/* Helper for read_w32_registry_string(). */
#ifdef _WIN32
static HKEY
get_root_key(const char *root)
{
HKEY root_key;
if( !root )
root_key = HKEY_CURRENT_USER;
else if( !strcmp( root, "HKEY_CLASSES_ROOT" ) )
root_key = HKEY_CLASSES_ROOT;
else if( !strcmp( root, "HKEY_CURRENT_USER" ) )
root_key = HKEY_CURRENT_USER;
else if( !strcmp( root, "HKEY_LOCAL_MACHINE" ) )
root_key = HKEY_LOCAL_MACHINE;
else if( !strcmp( root, "HKEY_USERS" ) )
root_key = HKEY_USERS;
else if( !strcmp( root, "HKEY_PERFORMANCE_DATA" ) )
root_key = HKEY_PERFORMANCE_DATA;
else if( !strcmp( root, "HKEY_CURRENT_CONFIG" ) )
root_key = HKEY_CURRENT_CONFIG;
else
return nullptr;
return root_key;
}
#endif
#if defined(_WIN64)
#define CROSS_ACCESS KEY_WOW64_32KEY
#else
#define CROSS_ACCESS KEY_WOW64_64KEY
#endif
#ifdef _WIN32
std::string
_readRegStr (HKEY root_key, const char *dir,
const char *name, bool alternate)
{
HKEY key_handle;
DWORD n1, nbytes, type;
std::string ret;
DWORD flags = KEY_READ;
if (alternate) {
flags |= CROSS_ACCESS;
}
if (RegOpenKeyExA(root_key, dir, 0, flags, &key_handle)) {
return ret;
}
nbytes = 1;
if (RegQueryValueExA(key_handle, name, 0, nullptr, nullptr, &nbytes)) {
RegCloseKey (key_handle);
return ret;
}
n1 = nbytes+1;
char result[n1];
if (RegQueryValueExA(key_handle, name, 0, &type, (LPBYTE)result, &n1)) {
RegCloseKey(key_handle);
return ret;
}
RegCloseKey(key_handle);
result[nbytes] = 0; /* make sure it is really a string */
ret = result;
if (type == REG_EXPAND_SZ && strchr (result, '%')) {
n1 += 1000;
char tmp[n1 +1];
nbytes = ExpandEnvironmentStringsA(ret.c_str(), tmp, n1);
if (nbytes && nbytes > n1) {
n1 = nbytes;
char tmp2[n1 +1];
nbytes = ExpandEnvironmentStringsA(result, tmp2, n1);
if (nbytes && nbytes > n1) {
/* oops - truncated, better don't expand at all */
return ret;
}
tmp2[nbytes] = 0;
ret = tmp2;
} else if (nbytes) { /* okay, reduce the length */
tmp[nbytes] = 0;
ret = tmp;
}
}
return ret;
}
#endif
std::string
readRegStr (const char *root, const char *dir, const char *name)
{
#ifndef _WIN32
(void)root; (void)dir; (void)name;
return std::string();
#else
HKEY root_key;
std::string ret;
if (!(root_key = get_root_key(root))) {
return ret;
}
ret = _readRegStr (root_key, dir, name, false);
if (ret.empty()) {
// Try local machine as fallback.
- qDebug() << "Fallback to HKLM for" << dir << name;
ret = _readRegStr (HKEY_LOCAL_MACHINE, dir, name, false);
if (ret.empty()) {
// Try alternative registry view as fallback
- qDebug() << "Fallback to HKLM alternative for" << dir << name;
ret = _readRegStr (HKEY_LOCAL_MACHINE, dir, name, true);
}
}
- qDebug() << "Returning:" << (ret.empty() ? "empty" : ret.c_str());
return ret;
#endif
}
bool writeRegStr(const char *root, const char *path, const char *key,
const char *val)
{
#ifndef _WIN32
(void) root; (void) path; (void) key; (void) val;
return false;
#else
HKEY h, hk;
int type;
int ec;
hk = get_root_key (root);
if (!hk) {
fprintf(stderr, "Failed to find root key.\n");
}
DWORD flags = KEY_ALL_ACCESS;
ec = RegCreateKeyExA(hk, path, 0, NULL, REG_OPTION_NON_VOLATILE,
flags, NULL, &h, NULL);
if (ec != ERROR_SUCCESS)
{
fprintf (stderr, "creating/opening registry key `%s' failed\n", path);
return false;
}
type = strchr (val, '%')? REG_EXPAND_SZ : REG_SZ;
ec = RegSetValueExA(h, key, 0, type, (const BYTE*)val, strlen (val));
if (ec != ERROR_SUCCESS)
{
fprintf (stderr, "saving registry key `%s'->`%s' failed\n", path, key);
RegCloseKey(h);
return false;
}
RegCloseKey(h);
return true;
#endif
}
+bool writeRegDword (const char *root, const char *path, const char *key,
+ unsigned long val)
+{
+#ifndef _WIN32
+ (void) root; (void) path; (void) key; (void) val;
+ return false;
+#else
+ HKEY h, hk;
+ int ec;
+
+ hk = get_root_key (root);
+
+ if (!hk) {
+ fprintf(stderr, "Failed to find root key.\n");
+ }
+
+ DWORD flags = KEY_ALL_ACCESS;
+
+ ec = RegCreateKeyExA(hk, path, 0, NULL, REG_OPTION_NON_VOLATILE,
+ flags, NULL, &h, NULL);
+ if (ec != ERROR_SUCCESS)
+ {
+ fprintf (stderr, "creating/opening registry key `%s' failed\n", path);
+ return false;
+ }
+ ec = RegSetValueExA(h, key, 0, REG_DWORD, (const BYTE*)&val, sizeof(val));
+ if (ec != ERROR_SUCCESS)
+ {
+ fprintf (stderr, "saving registry key `%s'->`%s' failed\n", path, key);
+ RegCloseKey(h);
+ return false;
+ }
+ RegCloseKey(h);
+ return true;
+#endif
+}
+
+
#ifdef _WIN32
static int
has_high_integrity(HANDLE hToken)
{
PTOKEN_MANDATORY_LABEL integrity_label = NULL;
DWORD integrity_level = 0,
size = 0;
if (hToken == NULL || hToken == INVALID_HANDLE_VALUE)
{
return 0;
}
/* Get the required size */
if (!GetTokenInformation (hToken, TokenIntegrityLevel,
NULL, 0, &size))
{
if (GetLastError() != ERROR_INSUFFICIENT_BUFFER)
{
return 0;
}
}
integrity_label = (PTOKEN_MANDATORY_LABEL) LocalAlloc(0, size);
if (integrity_label == NULL)
{
return 0;
}
if (!GetTokenInformation (hToken, TokenIntegrityLevel,
integrity_label, size, &size))
{
LocalFree(integrity_label);
return 0;
}
/* Get the last integrity level */
integrity_level = *GetSidSubAuthority(integrity_label->Label.Sid,
(DWORD)(UCHAR)(*GetSidSubAuthorityCount(
integrity_label->Label.Sid) - 1));
LocalFree (integrity_label);
return integrity_level >= SECURITY_MANDATORY_HIGH_RID;
}
#endif
bool isElevated()
{
#ifdef _WIN32
int ret = 0;
HANDLE hToken = NULL;
if (OpenProcessToken (GetCurrentProcess(), TOKEN_QUERY, &hToken))
{
DWORD elevation;
DWORD cbSize = sizeof (DWORD);
if (GetTokenInformation (hToken, TokenElevation, &elevation,
sizeof (TokenElevation), &cbSize))
{
ret = elevation;
}
}
/* Elevation will be true and ElevationType TokenElevationTypeFull even
if the token is a user token created by SAFER so we additionally
check the integrity level of the token which will only be high in
the real elevated process and medium otherwise. */
ret = ret && has_high_integrity (hToken);
if (hToken)
CloseHandle (hToken);
return ret;
#else
return false;
#endif
}
}// namespace
diff --git a/src/util/w32-util.h b/src/util/w32-util.h
index 998ae95..c358462 100644
--- a/src/util/w32-util.h
+++ b/src/util/w32-util.h
@@ -1,56 +1,62 @@
/* Copyright (C) 2018 by Intevation GmbH <info@intevation.de>
*
* This file is Free Software under the GNU GPL (v>=2)
* and comes with ABSOLUTELY NO WARRANTY!
* See LICENSE.txt for details.
*/
#include <string>
/* The Registry key used by Gpg4win. */
#ifdef _WIN64
# define GPG4WIN_REGKEY_2 "Software\\Wow6432Node\\GNU\\GnuPG"
#else
# define GPG4WIN_REGKEY_2 "Software\\GNU\\GnuPG"
#endif
#ifdef _WIN64
# define GPG4WIN_REGKEY_3 "Software\\Wow6432Node\\Gpg4win"
#else
# define GPG4WIN_REGKEY_3 "Software\\Gpg4win"
#endif
#define GPGOL_REG_PATH "Software\\GNU\\GpgOL"
namespace W32
{
/* Get the locale dir of Gpg4win. */
std::string getGpg4winLocaleDir();
/** Get the Gpg4win Install directory.
*
* Looks for the Gpg4win 3.x registry key.
* And checks that the directory can be read.
*
* @returns an empty string if no dir could be found.
*
**/
std::string getGpg4winDir();
/** Read a registry string value. If root is null first
* HKEY_CURRENT_USER is searched and then it falls back
* to HKEY_LOCAL_MACHINE . */
std::string readRegStr(const char *root,
const char *path,
const char *key);
bool writeRegStr(const char *root,
const char *path,
const char *key,
const char *val);
+bool writeRegDword(const char *root,
+ const char *path,
+ const char *key,
+ unsigned long value);
+
+
/** Call this to switch to the W64 registry. */
void setW64RegistryMode(bool value);
bool isElevated();
} // namespace W32
File Metadata
Details
Attached
Mime Type
text/x-diff
Expires
Sat, Dec 6, 11:49 PM (1 d, 6 h)
Storage Engine
local-disk
Storage Format
Raw Data
Storage Handle
e0/ea/93cdcfa379dc154ae0b5139a023e
Attached To
rGTO Gpg4win-Tools
Event Timeline
Log In to Comment