Self-contained .NET (#22217)

* dotnet sc

* MD preview - C# app

 - working self-contained

* Gcode preview - C# app

* DevFiles preview - C# app

* Fix passing path with spaces as cmd arg and monacocpp proj file

* Pdf preview - C# app

* Svg preview - C# app

* Fix comment

* Gcode thumbnail - C# app

TODO:
	- installer
	- why IThumbnailProvider and IIntializeWithFile doesn't work?

* Pdf thumbnail - C# app

TODO:
        - installer
        - why IThumbnailProvider and IIntializeWithFile doesn't work?

* Pdf thumbnail - C# app

TODO:
        - installer
        - why IThumbnailProvider and IIntializeWithFile doesn't work?

* Fix GcodeThumbnailProviderCpp.vcxproj

* Svg thumbnail - C# app

TODO:
        - installer
        - why IThumbnailProvider and IIntializeWithFile doesn't work?

* Fix Svg tests

* Thumbnail providers - installer

* Self-contained Hosts and FileLocksmith

* Fix hardcoded <RuntimeIdentifier>

* Remove unneeded files

* Try to fix Nuget in PR CI

* Prefix new dlls with PowerToys.
Sign new dlls and exes

* Add new .exe files to ProcessList

* ci: debug by listing all env vars

* ci: try setting variable in the right ci file

* Bring back hardcoded RuntimeIdentifier

* ci: Add comment and remove debug action

* Remove unneeded lib

* [WIP] Platform conditional dotnet files & hardlinks

* Cleanup

* Update expect.txt

* Test fix - ARM installer

* Fix uninstall bug

* Update docs

* Fix failing test

* Add dll details

* Minor cleanup

* Improve resizing

* Add some logs

* Test fix - release build

* Remove InvokeOnControlThread

* Test fix: logger initialization

* Fix arm64 installer

Co-authored-by: Jaime Bernardo <jaime@janeasystems.com>
Co-authored-by: Dustin L. Howett <dustin@howett.net>
This commit is contained in:
Stefan Markovic
2022-12-14 13:37:23 +01:00
committed by GitHub
parent a2c0febccc
commit 6ac508fb93
215 changed files with 9060 additions and 2328 deletions

View File

@@ -0,0 +1,84 @@
#include "pch.h"
#include "ClassFactory.h"
#include "SvgThumbnailProvider.h"
#include <new>
#include <Shlwapi.h>
extern long g_cDllRef;
ClassFactory::ClassFactory() :
m_cRef(1)
{
InterlockedIncrement(&g_cDllRef);
}
ClassFactory::~ClassFactory()
{
InterlockedDecrement(&g_cDllRef);
}
//
// IUnknown
//
IFACEMETHODIMP ClassFactory::QueryInterface(REFIID riid, void **ppv)
{
static const QITAB qit[] = {
QITABENT(ClassFactory, IClassFactory),
{ 0 },
};
return QISearch(this, qit, riid, ppv);
}
IFACEMETHODIMP_(ULONG) ClassFactory::AddRef()
{
return InterlockedIncrement(&m_cRef);
}
IFACEMETHODIMP_(ULONG) ClassFactory::Release()
{
ULONG cRef = InterlockedDecrement(&m_cRef);
if (0 == cRef)
{
delete this;
}
return cRef;
}
//
// IClassFactory
//
IFACEMETHODIMP ClassFactory::CreateInstance(IUnknown *pUnkOuter, REFIID riid, void **ppv)
{
HRESULT hr = CLASS_E_NOAGGREGATION;
if (pUnkOuter == NULL)
{
hr = E_OUTOFMEMORY;
SvgThumbnailProvider* pExt = new (std::nothrow) SvgThumbnailProvider();
if (pExt)
{
hr = pExt->QueryInterface(riid, ppv);
pExt->Release();
}
}
return hr;
}
IFACEMETHODIMP ClassFactory::LockServer(BOOL fLock)
{
if (fLock)
{
InterlockedIncrement(&g_cDllRef);
}
else
{
InterlockedDecrement(&g_cDllRef);
}
return S_OK;
}

View File

@@ -0,0 +1,24 @@
#pragma once
#include <Unknwn.h>
class ClassFactory : public IClassFactory
{
public:
// IUnknown
IFACEMETHODIMP QueryInterface(REFIID riid, void** ppv);
IFACEMETHODIMP_(ULONG) AddRef();
IFACEMETHODIMP_(ULONG) Release();
// IClassFactory
IFACEMETHODIMP CreateInstance(IUnknown* pUnkOuter, REFIID riid, void** ppv);
IFACEMETHODIMP LockServer(BOOL fLock);
ClassFactory();
protected:
~ClassFactory();
private:
long m_cRef;
};

View File

@@ -0,0 +1,3 @@
EXPORTS
DllGetClassObject PRIVATE
DllCanUnloadNow PRIVATE

View File

@@ -0,0 +1,181 @@
#include "pch.h"
#include "SvgThumbnailProvider.h"
#include <filesystem>
#include <fstream>
#include <shellapi.h>
#include <Shlwapi.h>
#include <string>
#include <wil/com.h>
#include <common/interop/shared_constants.h>
#include <common/logger/logger.h>
#include <common/SettingsAPI/settings_helpers.h>
#include <common/utils/process_path.h>
extern HINSTANCE g_hInst;
extern long g_cDllRef;
SvgThumbnailProvider::SvgThumbnailProvider() :
m_cRef(1), m_pStream(NULL), m_process(NULL)
{
std::filesystem::path logFilePath(PTSettingsHelper::get_local_low_folder_location());
logFilePath.append(LogSettings::svgThumbLogPath);
Logger::init(LogSettings::svgThumbLoggerName, logFilePath.wstring(), PTSettingsHelper::get_log_settings_file_location());
InterlockedIncrement(&g_cDllRef);
}
SvgThumbnailProvider::~SvgThumbnailProvider()
{
InterlockedDecrement(&g_cDllRef);
}
#pragma region IUnknown
IFACEMETHODIMP SvgThumbnailProvider::QueryInterface(REFIID riid, void** ppv)
{
static const QITAB qit[] = {
QITABENT(SvgThumbnailProvider, IThumbnailProvider),
QITABENT(SvgThumbnailProvider, IInitializeWithStream),
{ 0 },
};
return QISearch(this, qit, riid, ppv);
}
IFACEMETHODIMP_(ULONG)
SvgThumbnailProvider::AddRef()
{
return InterlockedIncrement(&m_cRef);
}
IFACEMETHODIMP_(ULONG)
SvgThumbnailProvider::Release()
{
ULONG cRef = InterlockedDecrement(&m_cRef);
if (0 == cRef)
{
delete this;
}
return cRef;
}
#pragma endregion
#pragma region IInitializationWithStream
IFACEMETHODIMP SvgThumbnailProvider::Initialize(IStream* pStream, DWORD grfMode)
{
HRESULT hr = E_INVALIDARG;
if (pStream)
{
// Initialize can be called more than once, so release existing valid
// m_pStream.
if (m_pStream)
{
m_pStream->Release();
m_pStream = NULL;
}
m_pStream = pStream;
m_pStream->AddRef();
hr = S_OK;
}
return hr;
}
#pragma endregion
#pragma region IThumbnailProvider
IFACEMETHODIMP SvgThumbnailProvider::GetThumbnail(UINT cx, HBITMAP* phbmp, WTS_ALPHATYPE* pdwAlpha)
{
// Read stream into the buffer
char buffer[4096];
ULONG cbRead;
Logger::trace(L"Begin");
GUID guid;
if (CoCreateGuid(&guid) == S_OK)
{
wil::unique_cotaskmem_string guidString;
if (SUCCEEDED(StringFromCLSID(guid, &guidString)))
{
Logger::info(L"Read stream and save to tmp file.");
// {CLSID} -> CLSID
std::wstring guid = std::wstring(guidString.get()).substr(1, std::wstring(guidString.get()).size() - 2);
std::wstring filePath = PTSettingsHelper::get_local_low_folder_location() + L"\\SvgThumbnailPreview-Temp\\";
if (!std::filesystem::exists(filePath))
{
std::filesystem::create_directories(filePath);
}
std::wstring fileName = filePath + guid + L".svg";
// Write data to tmp file
std::fstream file;
file.open(fileName, std::ios_base::out | std::ios_base::binary);
if (!file.is_open())
{
return 0;
}
while (true)
{
auto result = m_pStream->Read(buffer, 4096, &cbRead);
file.write(buffer, cbRead);
if (result == S_FALSE)
{
break;
}
}
file.close();
try
{
Logger::info(L"Start SvgThumbnailProvider.exe");
STARTUPINFO info = { sizeof(info) };
std::wstring cmdLine{ L"\"" + fileName + L"\"" };
cmdLine += L" ";
cmdLine += std::to_wstring(cx);
std::wstring appPath = get_module_folderpath(g_hInst) + L"\\PowerToys.SvgThumbnailProvider.exe";
SHELLEXECUTEINFO sei{ sizeof(sei) };
sei.fMask = { SEE_MASK_NOCLOSEPROCESS | SEE_MASK_FLAG_NO_UI };
sei.lpFile = appPath.c_str();
sei.lpParameters = cmdLine.c_str();
sei.nShow = SW_SHOWDEFAULT;
ShellExecuteEx(&sei);
m_process = sei.hProcess;
WaitForSingleObject(m_process, INFINITE);
std::filesystem::remove(fileName);
std::wstring fileNameBmp = filePath + guid + L".bmp";
*phbmp = (HBITMAP)LoadImage(NULL, fileNameBmp.c_str(), IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE);
*pdwAlpha = WTS_ALPHATYPE::WTSAT_ARGB;
std::filesystem::remove(fileNameBmp);
}
catch (std::exception& e)
{
std::wstring errorMessage = std::wstring{ winrt::to_hstring(e.what()) };
Logger::error(L"Failed to start SvgThumbnailProvider.exe. Error: {}", errorMessage);
}
}
}
return S_OK;
}
#pragma endregion
#pragma region Helper Functions
#pragma endregion

View File

@@ -0,0 +1,37 @@
#pragma once
#include "pch.h"
#include <ShlObj.h>
#include <string>
#include <thumbcache.h>
class SvgThumbnailProvider :
public IInitializeWithStream,
public IThumbnailProvider
{
public:
// IUnknown
IFACEMETHODIMP QueryInterface(REFIID riid, void** ppv);
IFACEMETHODIMP_(ULONG) AddRef();
IFACEMETHODIMP_(ULONG) Release();
// IInitializeWithStream
IFACEMETHODIMP Initialize(IStream* pstream, DWORD grfMode);
// IPreviewHandler
IFACEMETHODIMP GetThumbnail(UINT cx, HBITMAP* phbmp, WTS_ALPHATYPE* pdwAlpha);
SvgThumbnailProvider();
protected:
~SvgThumbnailProvider();
private:
// Reference count of component.
long m_cRef;
// Provided during initialization.
IStream* m_pStream;
HANDLE m_process;
};

View File

@@ -0,0 +1,40 @@
#include <windows.h>
#include "resource.h"
#include "../../../common/version/version.h"
#define APSTUDIO_READONLY_SYMBOLS
#include "winres.h"
#undef APSTUDIO_READONLY_SYMBOLS
1 VERSIONINFO
FILEVERSION FILE_VERSION
PRODUCTVERSION PRODUCT_VERSION
FILEFLAGSMASK VS_FFI_FILEFLAGSMASK
#ifdef _DEBUG
FILEFLAGS VS_FF_DEBUG
#else
FILEFLAGS 0x0L
#endif
FILEOS VOS_NT_WINDOWS32
FILETYPE VFT_DLL
FILESUBTYPE VFT2_UNKNOWN
BEGIN
BLOCK "StringFileInfo"
BEGIN
BLOCK "040904b0" // US English (0x0409), Unicode (0x04B0) charset
BEGIN
VALUE "CompanyName", COMPANY_NAME
VALUE "FileDescription", FILE_DESCRIPTION
VALUE "FileVersion", FILE_VERSION_STRING
VALUE "InternalName", INTERNAL_NAME
VALUE "LegalCopyright", COPYRIGHT_NOTE
VALUE "OriginalFilename", ORIGINAL_FILENAME
VALUE "ProductName", PRODUCT_NAME
VALUE "ProductVersion", PRODUCT_VERSION_STRING
END
END
BLOCK "VarFileInfo"
BEGIN
VALUE "Translation", 0x409, 1200 // US English (0x0409), Unicode (1200) charset
END
END

View File

@@ -0,0 +1,121 @@
<?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.props" Condition="Exists('..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.props')" />
<PropertyGroup Label="Globals">
<VCProjectVersion>16.0</VCProjectVersion>
<Keyword>Win32Proj</Keyword>
<ProjectGuid>{2bbc9e33-21ec-401c-84da-bb6590a9b2aa}</ProjectGuid>
<RootNamespace>SvgThumbnailProviderCpp</RootNamespace>
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)'=='Debug'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)'=='Release'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v143</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet>
</PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings">
</ImportGroup>
<ImportGroup Label="Shared">
</ImportGroup>
<ImportGroup Label="PropertySheets">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup>
<PropertyGroup Label="UserMacros" />
<PropertyGroup>
<OutDir>$(SolutionDir)$(Platform)\$(Configuration)\modules\FileExplorerPreview\</OutDir>
</PropertyGroup>
<PropertyGroup>
<TargetName>PowerToys.$(ProjectName)</TargetName>
</PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)'=='Debug'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>_DEBUG;MARKDOWNPREVIEWHANDLERCPP_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
<PrecompiledHeader>Use</PrecompiledHeader>
<AdditionalIncludeDirectories>../../..</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableUAC>false</EnableUAC>
<ModuleDefinitionFile>GlobalExportFunctions.def</ModuleDefinitionFile>
<AdditionalDependencies>Shlwapi.lib;$(CoreLibraryDependencies);%(AdditionalDependencies)</AdditionalDependencies>
</Link>
</ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)'=='Release'">
<ClCompile>
<WarningLevel>Level3</WarningLevel>
<FunctionLevelLinking>true</FunctionLevelLinking>
<IntrinsicFunctions>true</IntrinsicFunctions>
<SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>NDEBUG;MARKDOWNPREVIEWHANDLERCPP_EXPORTS;_WINDOWS;_USRDLL;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<ConformanceMode>true</ConformanceMode>
<PrecompiledHeader>Use</PrecompiledHeader>
<AdditionalIncludeDirectories>../../..</AdditionalIncludeDirectories>
</ClCompile>
<Link>
<SubSystem>Windows</SubSystem>
<EnableCOMDATFolding>true</EnableCOMDATFolding>
<OptimizeReferences>true</OptimizeReferences>
<GenerateDebugInformation>true</GenerateDebugInformation>
<EnableUAC>false</EnableUAC>
<ModuleDefinitionFile>GlobalExportFunctions.def</ModuleDefinitionFile>
<AdditionalDependencies>Shlwapi.lib;$(CoreLibraryDependencies);%(AdditionalDependencies)</AdditionalDependencies>
</Link>
</ItemDefinitionGroup>
<ItemGroup>
<ClInclude Include="ClassFactory.h" />
<ClInclude Include="pch.h" />
<ClInclude Include="resource.h" />
<ClInclude Include="SvgThumbnailProvider.h" />
</ItemGroup>
<ItemGroup>
<ClCompile Include="ClassFactory.cpp" />
<ClCompile Include="dllmain.cpp" />
<ClCompile Include="pch.cpp">
<PrecompiledHeader>Create</PrecompiledHeader>
</ClCompile>
<ClCompile Include="SvgThumbnailProvider.cpp" />
</ItemGroup>
<ItemGroup>
<None Include="GlobalExportFunctions.def" />
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\..\..\common\logger\logger.vcxproj">
<Project>{d9b8fc84-322a-4f9f-bbb9-20915c47ddfd}</Project>
</ProjectReference>
<ProjectReference Include="..\..\..\common\SettingsAPI\SettingsAPI.vcxproj">
<Project>{6955446d-23f7-4023-9bb3-8657f904af99}</Project>
</ProjectReference>
</ItemGroup>
<ItemGroup>
<ResourceCompile Include="SvgThumbnailProviderCpp.rc" />
</ItemGroup>
<Import Project="..\..\..\..\deps\spdlog.props" />
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
<Import Project="..\..\..\..\packages\Microsoft.Windows.ImplementationLibrary.1.0.220914.1\build\native\Microsoft.Windows.ImplementationLibrary.targets" Condition="Exists('..\..\..\..\packages\Microsoft.Windows.ImplementationLibrary.1.0.220914.1\build\native\Microsoft.Windows.ImplementationLibrary.targets')" />
<Import Project="..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.targets" Condition="Exists('..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.targets')" />
</ImportGroup>
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\..\..\..\packages\Microsoft.Windows.ImplementationLibrary.1.0.220914.1\build\native\Microsoft.Windows.ImplementationLibrary.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\..\..\..\packages\Microsoft.Windows.ImplementationLibrary.1.0.220914.1\build\native\Microsoft.Windows.ImplementationLibrary.targets'))" />
<Error Condition="!Exists('..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.props')" Text="$([System.String]::Format('$(ErrorText)', '..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.props'))" />
<Error Condition="!Exists('..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\..\..\..\packages\Microsoft.Windows.CppWinRT.2.0.220929.3\build\native\Microsoft.Windows.CppWinRT.targets'))" />
</Target>
</Project>

View File

@@ -0,0 +1,59 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup>
<Filter Include="Source Files">
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
<Extensions>cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
</Filter>
<Filter Include="Header Files">
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
<Extensions>h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd</Extensions>
</Filter>
<Filter Include="Resource Files">
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
</Filter>
</ItemGroup>
<ItemGroup>
<ClInclude Include="pch.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="ClassFactory.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="SvgThumbnailProvider.h">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="resource.h">
<Filter>Resource Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="dllmain.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="pch.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="ClassFactory.cpp">
<Filter>Source Files</Filter>
</ClCompile>
<ClCompile Include="SvgThumbnailProvider.cpp">
<Filter>Source Files</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<None Include="GlobalExportFunctions.def">
<Filter>Source Files</Filter>
</None>
<None Include="packages.config" />
</ItemGroup>
<ItemGroup>
<Natvis Include="$(MSBuildThisFileDirectory)..\..\natvis\wil.natvis" />
</ItemGroup>
<ItemGroup>
<ResourceCompile Include="SvgThumbnailProviderCpp.rc">
<Filter>Resource Files</Filter>
</ResourceCompile>
</ItemGroup>
</Project>

View File

@@ -0,0 +1,73 @@
// dllmain.cpp : Defines the entry point for the DLL application.
#include "pch.h"
#include "ClassFactory.h"
HINSTANCE g_hInst = NULL;
long g_cDllRef = 0;
// {10144713-1526-46C9-88DA-1FB52807A9FF}
static const GUID CLSID_SvgThumbnailProvider = { 0x10144713, 0x1526, 0x46c9, { 0x88, 0xda, 0x1f, 0xb5, 0x28, 0x7, 0xa9, 0xff } };
BOOL APIENTRY DllMain(HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
g_hInst = hModule;
DisableThreadLibraryCalls(hModule);
break;
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
//
// FUNCTION: DllGetClassObject
//
// PURPOSE: Create the class factory and query to the specific interface.
//
// PARAMETERS:
// * rclsid - The CLSID that will associate the correct data and code.
// * riid - A reference to the identifier of the interface that the caller
// is to use to communicate with the class object.
// * ppv - The address of a pointer variable that receives the interface
// pointer requested in riid. Upon successful return, *ppv contains the
// requested interface pointer. If an error occurs, the interface pointer
// is NULL.
//
STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, void** ppv)
{
HRESULT hr = CLASS_E_CLASSNOTAVAILABLE;
if (IsEqualCLSID(CLSID_SvgThumbnailProvider, rclsid))
{
hr = E_OUTOFMEMORY;
ClassFactory* pClassFactory = new ClassFactory();
if (pClassFactory)
{
hr = pClassFactory->QueryInterface(riid, ppv);
pClassFactory->Release();
}
}
return hr;
}
//
// FUNCTION: DllCanUnloadNow
//
// PURPOSE: Check if we can unload the component from the memory.
//
// NOTE: The component can be unloaded from the memory when its reference
// count is zero (i.e. nobody is still using the component).
//
STDAPI DllCanUnloadNow(void)
{
return g_cDllRef > 0 ? S_FALSE : S_OK;
}

View File

@@ -0,0 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="Microsoft.Windows.CppWinRT" version="2.0.220929.3" targetFramework="native" />
<package id="Microsoft.Windows.ImplementationLibrary" version="1.0.220914.1" targetFramework="native" />
</packages>

View File

@@ -0,0 +1,5 @@
// pch.cpp: source file corresponding to the pre-compiled header
#include "pch.h"
// When you are using pre-compiled headers, this source file is necessary for compilation to succeed.

View File

@@ -0,0 +1,14 @@
// pch.h: This is a precompiled header file.
// Files listed below are compiled only once, improving build performance for future builds.
// This also affects IntelliSense performance, including code completion and many code browsing features.
// However, files listed here are ALL re-compiled if any one of them is updated between builds.
// Do not add files here that you will be updating frequently as this negates the performance advantage.
#ifndef PCH_H
#define PCH_H
#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers
// Windows Header Files
#include <windows.h>
#endif //PCH_H

View File

@@ -0,0 +1,13 @@
//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file.
// Used by AlwaysOnTopModuleInterface.rc
//////////////////////////////
// Non-localizable
#define FILE_DESCRIPTION "PowerToys Svg Thumbnail Provider Module"
#define INTERNAL_NAME "PowerToys.SvgThumbnailProviderCpp"
#define ORIGINAL_FILENAME "PowerToys.SvgThumbnailProviderCpp.dll"
// Non-localizable
//////////////////////////////