Page Menu
Home
GnuPG
Search
Configure Global Search
Log In
Files
F34307101
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Size
26 KB
Subscribers
None
View Options
diff --git a/src/gpga/CMakeLists.txt b/src/gpga/CMakeLists.txt
index 3502ad1..075a854 100644
--- a/src/gpga/CMakeLists.txt
+++ b/src/gpga/CMakeLists.txt
@@ -1,29 +1,30 @@
# 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
gpgshellfolder.cpp
+ gpgpersistfolder.cpp
)
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/flange.cpp b/src/gpga/flange.cpp
index 15c5144..94b55b8 100644
--- a/src/gpga/flange.cpp
+++ b/src/gpga/flange.cpp
@@ -1,277 +1,283 @@
/* 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 "gpgshellfolder.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;
}
}
+CLSID getFlangeCLSID ()
+{
+ return MY_CLSID;
+}
+
/* Here we go */
STDAPI DllGetClassObject (REFCLSID rclsid, REFIID riid, LPVOID* ppv)
{
init_logging ();
+ log_debug ("\nGetClassObject");
if (!ppv) {
return E_POINTER;
}
*ppv = nullptr;
if (rclsid == MY_CLSID) {
return FlangeFactory::instance()->QueryInterface(riid, ppv);
}
log_debug ("Get class object for nonimp clsid'" GUID_FMT "'",
GUID_ARG(riid));
return CLASS_E_CLASSNOTAVAILABLE;
}
STDMETHODIMP FlangeFactory::LockServer (BOOL lock)
{
if (lock) {
AddRef();
} else {
Release();
}
return S_OK;
}
STDMETHODIMP FlangeFactory::CreateInstance (LPUNKNOWN,
REFIID riid,
LPVOID* ppvObj)
{
if (riid == IID_IShellFolder) {
auto folder = new GpgShellFolder();
return folder->QueryInterface (riid, ppvObj);
}
log_debug ("CreateInstance with unimplemented id '" GUID_FMT "'",
GUID_ARG(riid));
return E_NOINTERFACE;
}
STDMETHODIMP FlangeFactory::QueryInterface (REFIID riid, void **ppv)
{
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 {
log_debug("QueryInterface with unknwon interface: '" GUID_FMT "'",
GUID_ARG(riid));
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
index 7801824..d291106 100644
--- a/src/gpga/flange.h
+++ b/src/gpga/flange.h
@@ -1,36 +1,38 @@
#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;
};
+CLSID getFlangeCLSID();
+
#endif // FLANGE_H
diff --git a/src/gpga/gpgpersistfolder.cpp b/src/gpga/gpgpersistfolder.cpp
new file mode 100644
index 0000000..452c0cb
--- /dev/null
+++ b/src/gpga/gpgpersistfolder.cpp
@@ -0,0 +1,111 @@
+/* Copyright (C) 2019 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 "gpgpersistfolder.h"
+#include "debug.h"
+
+#include "flange.h"
+
+STDMETHODIMP GpgPersistFolder::QueryInterface (REFIID riid, void **ppv)
+{
+ TRACEPOINT;
+ if (!ppv) {
+ return E_POINTER;
+ }
+
+ *ppv = nullptr;
+ log_debug("QueryInterface for: '" GUID_FMT "'",
+ GUID_ARG(riid));
+
+ /* The static casts ensure that the virtual function table
+ layout of the returned object is correct. */
+ if (riid == IID_IUnknown) {
+ TRACEPOINT;
+ *ppv = static_cast<IUnknown *> (this);
+ } else if (riid == IID_IPersistFolder) {
+ TRACEPOINT;
+ *ppv = static_cast<IPersistFolder*> (this);
+ } else if (riid == IID_IPersistFolder2) {
+ TRACEPOINT;
+ *ppv = static_cast<IPersistFolder2*> (this);
+ } else if (riid == IID_IPersistFolder3) {
+ TRACEPOINT;
+ *ppv = static_cast<IPersistFolder3*> (this);
+ } else if (riid == IID_IPersist) {
+ TRACEPOINT;
+ *ppv = static_cast<IPersist*> (this);
+ } else {
+ log_debug("QueryInterface with unknown interface: '" GUID_FMT "'",
+ GUID_ARG(riid));
+ return E_NOINTERFACE;
+ }
+
+ reinterpret_cast<IUnknown *>(*ppv)->AddRef ();
+
+ return S_OK;
+}
+
+ULONG STDMETHODCALLTYPE GpgPersistFolder::Release()
+{
+ TRACEPOINT;
+ ULONG lCount = --m_lRef;
+ if (!lCount) {
+ delete this;
+ }
+ return lCount;
+}
+
+GpgPersistFolder::GpgPersistFolder():
+ m_lRef(0),
+ m_pidl(nullptr)
+{
+
+}
+
+GpgPersistFolder::~GpgPersistFolder()
+{
+ TRACEPOINT;
+ if (m_pidl) {
+ CoTaskMemFree(m_pidl);
+ }
+}
+
+HRESULT STDMETHODCALLTYPE GpgPersistFolder::GetFolderTargetInfo(PERSIST_FOLDER_TARGET_INFO *ppfti)
+{
+ TRACEPOINT;
+ return S_OK;
+}
+
+HRESULT STDMETHODCALLTYPE GpgPersistFolder::InitializeEx(IBindCtx *pbc,
+ PCIDLIST_ABSOLUTE pidlRoot,
+ const PERSIST_FOLDER_TARGET_INFO *ppfti)
+{
+ TRACEPOINT;
+ Initialize (pidlRoot);
+ return S_OK;
+}
+
+HRESULT STDMETHODCALLTYPE GpgPersistFolder::GetCurFolder(PIDLIST_ABSOLUTE *ppidl)
+{
+ TRACEPOINT;
+ return S_OK;
+}
+
+HRESULT STDMETHODCALLTYPE GpgPersistFolder::Initialize(PCIDLIST_ABSOLUTE pidl)
+{
+ TRACEPOINT;
+ m_pidl = ILCloneFull(pidl);
+ return m_pidl ? S_OK : E_FAIL;
+}
+
+HRESULT STDMETHODCALLTYPE GpgPersistFolder::GetClassID(CLSID *pClassID)
+{
+ TRACEPOINT;
+ *pClassID = getFlangeCLSID();
+
+ return S_OK;
+}
diff --git a/src/gpga/gpgpersistfolder.h b/src/gpga/gpgpersistfolder.h
new file mode 100644
index 0000000..8ae172e
--- /dev/null
+++ b/src/gpga/gpgpersistfolder.h
@@ -0,0 +1,43 @@
+#ifndef GPGA_GPGPERSISTFOLDER_H
+#define GPGA_GPGPERSISTFOLDER_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>
+#include <shlobj.h>
+
+class GpgPersistFolder: public IPersistFolder3
+{
+public:
+ GpgPersistFolder();
+
+ virtual ~GpgPersistFolder();
+
+ /* IUnknown */
+ STDMETHODIMP QueryInterface (REFIID riid, LPVOID* ppvObj);
+ STDMETHODIMP_(ULONG) AddRef() { ++m_lRef; return m_lRef; };
+ STDMETHODIMP_(ULONG) Release();
+
+ /* IPersist */
+ HRESULT STDMETHODCALLTYPE GetClassID(CLSID *pClassID);
+
+ /* IPersistFolder3 */
+ HRESULT STDMETHODCALLTYPE GetFolderTargetInfo(PERSIST_FOLDER_TARGET_INFO *ppfti);
+ HRESULT STDMETHODCALLTYPE InitializeEx(IBindCtx *pbc, PCIDLIST_ABSOLUTE pidlRoot,
+ const PERSIST_FOLDER_TARGET_INFO *ppfti);
+ /* IPersistFolder2 */
+ HRESULT STDMETHODCALLTYPE GetCurFolder(PIDLIST_ABSOLUTE *ppidl);
+
+ /* IPersistFolder */
+ HRESULT STDMETHODCALLTYPE Initialize(PCIDLIST_ABSOLUTE pidl);
+
+ /* custom */
+ PIDLIST_ABSOLUTE pidl() {return m_pidl;}
+private:
+ ULONG m_lRef;
+ PIDLIST_ABSOLUTE m_pidl;
+};
+#endif // GPGA_GPGPERSISTFOLDER_H
diff --git a/src/gpga/gpgshellfolder.cpp b/src/gpga/gpgshellfolder.cpp
index 17caeb7..9a1daae 100644
--- a/src/gpga/gpgshellfolder.cpp
+++ b/src/gpga/gpgshellfolder.cpp
@@ -1,146 +1,209 @@
/* 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 "gpgshellfolder.h"
+#include "gpgpersistfolder.h"
#include "debug.h"
+GpgShellFolder::GpgShellFolder() :
+ m_lRef(0),
+ m_persistFolder(new GpgPersistFolder())
+{
+ m_persistFolder->AddRef();
+}
+
GpgShellFolder::~GpgShellFolder()
{
+ m_persistFolder->Release();
}
STDMETHODIMP GpgShellFolder::QueryInterface (REFIID riid, void **ppv)
{
- 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_IShellFolder) {
- *ppv = static_cast<IShellFolder*> (this);
- } else {
- log_debug("QueryInterface with unknwon interface: '" GUID_FMT "'",
- GUID_ARG(riid));
- return E_NOINTERFACE;
- }
-
- reinterpret_cast<IUnknown *>(*ppv)->AddRef ();
-
- return S_OK;
+ if (!ppv) {
+ return E_POINTER;
+ }
+
+ log_debug ("Get class object for clsid'" GUID_FMT "'",
+ GUID_ARG(riid));
+ *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_IShellFolder) {
+ *ppv = static_cast<IShellFolder*> (this);
+ } else if (riid == IID_IPersistFolder ||
+ riid == IID_IPersistFolder2 ||
+ riid == IID_IPersistFolder3 ||
+ riid == IID_IPersist) {
+ return m_persistFolder->QueryInterface (riid, ppv);
+ } else {
+ log_debug("QueryInterface with unknown interface: '" GUID_FMT "'",
+ GUID_ARG(riid));
+ return E_NOINTERFACE;
+ }
+
+ reinterpret_cast<IUnknown *>(*ppv)->AddRef ();
+
+ return S_OK;
}
ULONG STDMETHODCALLTYPE GpgShellFolder::Release()
{
- ULONG lCount = --m_lRef;
- if (!lCount) {
- delete this;
- }
- return lCount;
+ ULONG lCount = --m_lRef;
+ log_debug ("Folder release %i", lCount);
+ if (!lCount) {
+ delete this;
+ }
+ return lCount;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::ParseDisplayName(HWND hwnd,
IBindCtx *pbc,
LPWSTR pszDisplayName,
ULONG *pchEaten,
PIDLIST_RELATIVE *ppidl,
ULONG *pdwAttributes)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::EnumObjects(HWND hwnd,
SHCONTF grfFlags,
IEnumIDList **ppenumIDList)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::BindToObject(PCUIDLIST_RELATIVE pidl,
IBindCtx *pbc,
REFIID riid,
void **ppv)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::BindToStorage(PCUIDLIST_RELATIVE pidl,
IBindCtx *pbc,
REFIID riid,
void **ppv)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::CompareIDs(LPARAM lParam,
PCUIDLIST_RELATIVE pidl1,
PCUIDLIST_RELATIVE pidl2)
{
TRACEPOINT;
return S_OK;
}
-HRESULT STDMETHODCALLTYPE GpgShellFolder::CreateViewObject(HWND hwndOwner,
+HRESULT STDMETHODCALLTYPE GpgShellFolder::CreateViewObject(HWND hwnd,
REFIID riid,
void **ppv)
{
TRACEPOINT;
- return S_OK;
+ *ppv = NULL;
+
+ TRACEPOINT;
+ HRESULT hr = E_NOINTERFACE;
+ if (riid == IID_IShellView) {
+ SFV_CREATE csfv = { sizeof(csfv), 0 };
+ hr = QueryInterface(IID_IShellFolder, (void**)&csfv.pshf);
+ if (SUCCEEDED(hr)) {
+ if (SUCCEEDED(hr)) {
+ hr = SHCreateShellFolderView(&csfv, (IShellView**)ppv);
+ csfv.psfvcb->Release();
+ }
+ csfv.pshf->Release();
+ }
+ } else if (riid == IID_ICategoryProvider) {
+ /*
+ CFolderViewImplCategoryProvider* pCatProvider = new (std::nothrow) CFolderViewImplCategoryProvider(this);
+ hr = pCatProvider ? S_OK : E_OUTOFMEMORY;
+ if (SUCCEEDED(hr))
+ {
+ hr = pCatProvider->QueryInterface(riid, ppv);
+ pCatProvider->Release();
+ }
+ */
+ log_debug ("CategoryProvider requested but not implemented.");
+ } else if (riid == IID_IContextMenu){
+ // This is the background context menu for the folder itself, not the context menu on items within it.
+ DEFCONTEXTMENU dcm = { hwnd, NULL, m_persistFolder->pidl(),
+ static_cast<IShellFolder *>(this), // Replace with IShellFolder2
+ 0, NULL, NULL, 0, NULL };
+ hr = SHCreateDefaultContextMenu(&dcm, riid, ppv);
+ } else if (riid == IID_IExplorerCommandProvider) {
+ /*
+ CFolderViewCommandProvider *pProvider = new (std::nothrow) CFolderViewCommandProvider();
+ hr = pProvider ? S_OK : E_OUTOFMEMORY;
+ if (SUCCEEDED(hr))
+ {
+ hr = pProvider->QueryInterface(riid, ppv);
+ pProvider->Release();
+ }
+ */
+ log_debug ("ExplorerCommandProvider requested but not implemented.");
+ } else {
+ log_debug ("nonimp clsid'" GUID_FMT "'",
+ GUID_ARG(riid));
+ }
+ return hr;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::GetAttributesOf(UINT cidl,
PCUITEMID_CHILD_ARRAY apidl,
SFGAOF *rgfInOut)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::GetUIObjectOf(HWND hwndOwner,
UINT cidl,
PCUITEMID_CHILD_ARRAY apidl,
REFIID riid,
UINT *rgfReserved,
void **ppv)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::GetDisplayNameOf(PCUITEMID_CHILD pidl,
SHGDNF uFlags,
STRRET *pName)
{
TRACEPOINT;
return S_OK;
}
HRESULT STDMETHODCALLTYPE GpgShellFolder::SetNameOf(HWND hwnd,
PCUITEMID_CHILD pidl,
LPCWSTR pszName,
SHGDNF uFlags,
PITEMID_CHILD *ppidlOut)
{
- TRACEPOINT;
- return S_OK;
+ TRACEPOINT;
+ return S_OK;
}
diff --git a/src/gpga/gpgshellfolder.h b/src/gpga/gpgshellfolder.h
index 4e3ad22..0382b37 100644
--- a/src/gpga/gpgshellfolder.h
+++ b/src/gpga/gpgshellfolder.h
@@ -1,77 +1,80 @@
#ifndef GPGSHELLFOLDER_H
#define GPGSHELLFOLDER_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>
#include <shlobj.h>
+class GpgPersistFolder;
+
class GpgShellFolder: public IShellFolder
{
public:
- GpgShellFolder(): m_lRef(0) {}
+ GpgShellFolder();
virtual ~GpgShellFolder();
/* IUnknown */
STDMETHODIMP QueryInterface (REFIID riid, LPVOID* ppvObj);
STDMETHODIMP_(ULONG) AddRef() { ++m_lRef; return m_lRef; };
STDMETHODIMP_(ULONG) Release();
/* IShellFolder*/
HRESULT STDMETHODCALLTYPE ParseDisplayName(HWND hwnd,
IBindCtx *pbc,
LPWSTR pszDisplayName,
ULONG *pchEaten,
PIDLIST_RELATIVE *ppidl,
ULONG *pdwAttributes);
HRESULT STDMETHODCALLTYPE EnumObjects(HWND hwnd,
SHCONTF grfFlags,
IEnumIDList **ppenumIDList);
HRESULT STDMETHODCALLTYPE BindToObject(PCUIDLIST_RELATIVE pidl,
IBindCtx *pbc,
REFIID riid,
void **ppv);
HRESULT STDMETHODCALLTYPE BindToStorage(PCUIDLIST_RELATIVE pidl,
IBindCtx *pbc,
REFIID riid,
void **ppv);
HRESULT STDMETHODCALLTYPE CompareIDs(LPARAM lParam,
PCUIDLIST_RELATIVE pidl1,
PCUIDLIST_RELATIVE pidl2);
HRESULT STDMETHODCALLTYPE CreateViewObject(HWND hwndOwner,
REFIID riid,
void **ppv);
HRESULT STDMETHODCALLTYPE GetAttributesOf(UINT cidl,
PCUITEMID_CHILD_ARRAY apidl,
SFGAOF *rgfInOut);
HRESULT STDMETHODCALLTYPE GetUIObjectOf(HWND hwndOwner,
UINT cidl,
PCUITEMID_CHILD_ARRAY apidl,
REFIID riid,
UINT *rgfReserved,
void **ppv);
HRESULT STDMETHODCALLTYPE GetDisplayNameOf(PCUITEMID_CHILD pidl,
SHGDNF uFlags,
STRRET *pName);
HRESULT STDMETHODCALLTYPE SetNameOf(HWND hwnd,
PCUITEMID_CHILD pidl,
LPCWSTR pszName,
SHGDNF uFlags,
PITEMID_CHILD *ppidlOut);
private:
ULONG m_lRef;
+ GpgPersistFolder *m_persistFolder;
};
#endif // GPGSHELLFOLDER_H
diff --git a/src/util/debug.h b/src/util/debug.h
index 5d6257a..92571c3 100644
--- a/src/util/debug.h
+++ b/src/util/debug.h
@@ -1,31 +1,33 @@
#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__)
+ gpgrt_log_debug("%s:%s: " format, SRCNAME, __func__, ##__VA_ARGS__); \
+ gpgrt_log_debug("");
-#define STRANGEPOINT log_debug ("%s:%s:%d:UNEXPECTED", \
+#define STRANGEPOINT log_debug ("%d:UNEXPECTED", \
__LINE__);
-#define TRACEPOINT log_debug ("%s:%s:%d:TRACE");
+#define TRACEPOINT log_debug ("%d:TRACE", \
+ __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
File Metadata
Details
Attached
Mime Type
text/x-diff
Expires
Sun, Dec 28, 10:16 PM (6 h, 13 m)
Storage Engine
local-disk
Storage Format
Raw Data
Storage Handle
2c/64/61cc9c4b2a305ccf0eab4a1c0251
Attached To
rGTO Gpg4win-Tools
Event Timeline
Log In to Comment