This project aims to enhance the working environment on Windows
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

420 lines
12 KiB

#ifndef _H_UTILITY_H_
#define _H_UTILITY_H_
#if __has_include("ep_private.h")
//#define USE_PRIVATE_INTERFACES
#endif
#include <Windows.h>
#include <tchar.h>
#include <windows.data.xml.dom.h>
#include <accctrl.h>
#include <aclapi.h>
#include <sddl.h>
#include <Shlobj_core.h>
#include <restartmanager.h>
#pragma comment(lib, "Rstrtmgr.lib")
#define _LIBVALINET_INCLUDE_UNIVERSAL
#include <valinet/universal/toast/toast.h>
#include "queryversion.h"
#define APPID L"Microsoft.Windows.Explorer"
#define REGPATH "SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Explorer\\ExplorerPatcher"
#define SPECIAL_FOLDER CSIDL_APPDATA
#define APP_RELATIVE_PATH "\\ExplorerPatcher"
// This allows compiling with older Windows SDKs as well
#ifndef DWMWA_USE_HOSTBACKDROPBRUSH
#define DWMWA_USE_HOSTBACKDROPBRUSH 17 // [set] BOOL, Allows the use of host backdrop brushes for the window.
#endif
#ifndef DWMWA_USE_IMMERSIVE_DARK_MODE
#define DWMWA_USE_IMMERSIVE_DARK_MODE 20 // [set] BOOL, Allows a window to either use the accent color, or dark, according to the user Color Mode preferences.
#endif
#ifndef DWMWCP_DEFAULT
#define DWMWCP_DEFAULT 0
#endif
#ifndef DWMWCP_DONOTROUND
#define DWMWCP_DONOTROUND 1
#endif
#ifndef DWMWCP_ROUND
#define DWMWCP_ROUND 2
#endif
#ifndef DWMWCP_ROUNDSMALL
#define DWMWCP_ROUNDSMALL 3
#endif
#ifndef DWMWA_WINDOW_CORNER_PREFERENCE
#define DWMWA_WINDOW_CORNER_PREFERENCE 33 // [set] WINDOW_CORNER_PREFERENCE, Controls the policy that rounds top-level window corners
#endif
#ifndef DWMWA_BORDER_COLOR
#define DWMWA_BORDER_COLOR 34 // [set] COLORREF, The color of the thin border around a top-level window
#endif
#ifndef DWMWA_CAPTION_COLOR
#define DWMWA_CAPTION_COLOR 35 // [set] COLORREF, The color of the caption
#endif
#ifndef DWMWA_TEXT_COLOR
#define DWMWA_TEXT_COLOR 36 // [set] COLORREF, The color of the caption text
#endif
#ifndef DWMWA_VISIBLE_FRAME_BORDER_THICKNESS
#define DWMWA_VISIBLE_FRAME_BORDER_THICKNESS 37 // [get] UINT, width of the visible border around a thick frame window
#endif
#ifndef DWMWA_MICA_EFFFECT
#define DWMWA_MICA_EFFFECT 1029
#endif
#pragma region "Weird stuff"
INT64 nimpl4_1(INT64 a1, DWORD* a2);
INT64 nimpl4_0(INT64 a1, DWORD* a2);
__int64 __fastcall nimpl2(__int64 a1, uintptr_t* a2);
ULONG nimpl3();
HRESULT nimpl();
HRESULT nimpl1(__int64 a1, uintptr_t* a2, uintptr_t* a3);
HRESULT nimpl1_2(__int64 a1, uintptr_t* a2, uintptr_t* a3);
HRESULT nimpl1_3(__int64 a1, uintptr_t* a2, uintptr_t* a3);
__int64 nimpl4(__int64 a1, __int64 a2, __int64 a3, BYTE* a4);
typedef struct _IActivationFactoryAA
{
CONST_VTBL struct IActivationFactoryVtbl* lpVtbl;
struct IActivationFactoryVtbl* lpVtbl2;
struct IActivationFactoryVtbl* lpVtbl3;
} IActivationFactoryAA;
extern const IActivationFactoryAA XamlExtensionsFactory;
#pragma endregion
inline int FileExistsW(wchar_t* file)
{
WIN32_FIND_DATAW FindFileData;
HANDLE handle = FindFirstFileW(file, &FindFileData);
int found = handle != INVALID_HANDLE_VALUE;
if (found)
{
FindClose(handle);
}
return found;
}
// https://stackoverflow.com/questions/1672677/print-a-guid-variable
void printf_guid(GUID guid);
LRESULT CALLBACK BalloonWndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
__declspec(dllexport) CALLBACK ZZTestBalloon(HWND hWnd, HINSTANCE hInstance, LPSTR lpszCmdLine, int nCmdShow);
__declspec(dllexport) CALLBACK ZZTestToast(HWND hWnd, HINSTANCE hInstance, LPSTR lpszCmdLine, int nCmdShow);
__declspec(dllexport) CALLBACK ZZLaunchExplorer(HWND hWnd, HINSTANCE hInstance, LPSTR lpszCmdLine, int nCmdShow);
__declspec(dllexport) CALLBACK ZZLaunchExplorerDelayed(HWND hWnd, HINSTANCE hInstance, LPSTR lpszCmdLine, int nCmdShow);
POINT GetDefaultWinXPosition(BOOL bUseRcWork, BOOL* lpBottom, BOOL* lpRight, BOOL bAdjust);
#define MIN(X, Y) (((X) < (Y)) ? (X) : (Y))
#define MAX(X, Y) (((X) > (Y)) ? (X) : (Y))
FARPROC SHRegGetValueFromHKCUHKLMFunc;
inline LSTATUS SHRegGetValueFromHKCUHKLMWithOpt(
PCWSTR pwszKey,
PCWSTR pwszValue,
REGSAM samDesired,
void* pvData,
DWORD* pcbData
)
{
LSTATUS lRes = ERROR_FILE_NOT_FOUND;
HKEY hKey = NULL;
RegOpenKeyExW(
HKEY_CURRENT_USER,
pwszKey,
0,
samDesired,
&hKey
);
if (hKey == NULL || hKey == INVALID_HANDLE_VALUE)
{
hKey = NULL;
}
if (hKey)
{
lRes = RegQueryValueExW(
hKey,
pwszValue,
0,
NULL,
pvData,
pcbData
);
RegCloseKey(hKey);
if (lRes == ERROR_SUCCESS || lRes == ERROR_MORE_DATA)
{
return lRes;
}
}
RegOpenKeyExW(
HKEY_LOCAL_MACHINE,
pwszKey,
0,
samDesired,
&hKey
);
if (hKey == NULL || hKey == INVALID_HANDLE_VALUE)
{
hKey = NULL;
}
if (hKey)
{
lRes = RegQueryValueExW(
hKey,
pwszValue,
0,
NULL,
pvData,
pcbData
);
RegCloseKey(hKey);
if (lRes == ERROR_SUCCESS || lRes == ERROR_MORE_DATA)
{
return lRes;
}
}
return lRes;
}
static HWND(WINAPI* CreateWindowInBand)(
_In_ DWORD dwExStyle,
_In_opt_ ATOM atom,
_In_opt_ LPCWSTR lpWindowName,
_In_ DWORD dwStyle,
_In_ int X,
_In_ int Y,
_In_ int nWidth,
_In_ int nHeight,
_In_opt_ HWND hWndParent,
_In_opt_ HMENU hMenu,
_In_opt_ HINSTANCE hInstance,
_In_opt_ LPVOID lpParam,
DWORD band
);
BOOL(WINAPI* GetWindowBand)(HWND hWnd, PDWORD pdwBand);
BOOL(WINAPI* SetWindowBand)(HWND hWnd, HWND hwndInsertAfter, DWORD dwBand);
INT64(*SetWindowCompositionAttribute)(HWND, void*);
static void(*SetPreferredAppMode)(INT64 bAllowDark);
static void(*AllowDarkModeForWindow)(HWND hWnd, INT64 bAllowDark);
static BOOL(*ShouldAppsUseDarkMode)();
static void(*GetThemeName)(void*, void*, void*);
static BOOL AppsShouldUseDarkMode() { return TRUE; }
void* ReadFromFile(wchar_t* wszFileName, DWORD* dwSize);
inline long long milliseconds_now() {
LARGE_INTEGER s_frequency;
BOOL s_use_qpc = QueryPerformanceFrequency(&s_frequency);
if (s_use_qpc) {
LARGE_INTEGER now;
QueryPerformanceCounter(&now);
return (1000LL * now.QuadPart) / s_frequency.QuadPart;
}
else {
return GetTickCount();
}
}
inline BOOL IsAppRunningAsAdminMode()
{
BOOL fIsRunAsAdmin = FALSE;
DWORD dwError = ERROR_SUCCESS;
PSID pAdministratorsGroup = NULL;
// Allocate and initialize a SID of the administrators group.
SID_IDENTIFIER_AUTHORITY NtAuthority = SECURITY_NT_AUTHORITY;
if (!AllocateAndInitializeSid(
&NtAuthority,
2,
SECURITY_BUILTIN_DOMAIN_RID,
DOMAIN_ALIAS_RID_ADMINS,
0, 0, 0, 0, 0, 0,
&pAdministratorsGroup))
{
dwError = GetLastError();
goto Cleanup;
}
// Determine whether the SID of administrators group is enabled in
// the primary access token of the process.
if (!CheckTokenMembership(NULL, pAdministratorsGroup, &fIsRunAsAdmin))
{
dwError = GetLastError();
goto Cleanup;
}
Cleanup:
// Centralized cleanup for all allocated resources.
if (pAdministratorsGroup)
{
FreeSid(pAdministratorsGroup);
pAdministratorsGroup = NULL;
}
// Throw the error if something failed in the function.
if (ERROR_SUCCESS != dwError)
{
return FALSE;
}
return fIsRunAsAdmin;
}
inline BOOL IsDesktopWindowAlreadyPresent()
{
return (FindWindowExW(NULL, NULL, L"Progman", NULL) || FindWindowExW(NULL, NULL, L"Proxy Desktop", NULL));
}
// https://jiangsheng.net/2013/01/22/how-to-restart-windows-explorer-programmatically-using-restart-manager/
inline RM_UNIQUE_PROCESS GetExplorerApplication()
{
HWND hwnd = FindWindow(L"Shell_TrayWnd", NULL);
DWORD pid = 0;
GetWindowThreadProcessId(hwnd, &pid);
RM_UNIQUE_PROCESS out = { 0, { -1, -1 } };
DWORD bytesReturned;
WCHAR imageName[MAX_PATH]; // process image name buffer
DWORD processIds[2048]; // max 2048 processes (more than enough)
// enumerate all running processes (usually around 60-70)
EnumProcesses(processIds, sizeof(processIds), &bytesReturned);
int count = bytesReturned / sizeof(DWORD); // number of processIds returned
for (int i = 0; i < count; ++i)
{
DWORD processId = processIds[i];
HANDLE hProc;
if (processId == pid && (hProc = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, processId)))
{
GetProcessImageFileNameW(hProc, imageName, MAX_PATH);
FILETIME ftStart, ftExit, ftKernel, ftUser;
GetProcessTimes(hProc, &ftStart, &ftExit, &ftKernel, &ftUser);
if (ftStart.dwLowDateTime < out.ProcessStartTime.dwLowDateTime)
{
out.dwProcessId = processId;
out.ProcessStartTime = ftStart;
}
CloseHandle(hProc);
}
}
return out; // return count in pResults
}
static DWORD RmSession = -1;
static wchar_t RmSessionKey[CCH_RM_SESSION_KEY + 1];
// shuts down the explorer and is ready for explorer restart
inline void BeginExplorerRestart()
{
if (RmStartSession(&RmSession, 0, RmSessionKey) == ERROR_SUCCESS)
{
RM_UNIQUE_PROCESS rgApplications[] = { GetExplorerApplication() };
RmRegisterResources(RmSession, 0, 0, 1, rgApplications, 0, 0);
DWORD rebootReason;
UINT nProcInfoNeeded, nProcInfo = 16;
RM_PROCESS_INFO affectedApps[16];
RmGetList(RmSession, &nProcInfoNeeded, &nProcInfo, affectedApps, &rebootReason);
if (rebootReason == RmRebootReasonNone) // no need for reboot?
{
// shutdown explorer
RmShutdown(RmSession, RmForceShutdown, 0);
}
}
}
// restarts the explorer
inline void FinishExplorerRestart()
{
DWORD dwError;
if (dwError = RmRestart(RmSession, 0, NULL))
printf("\n RmRestart error: %d\n\n", dwError);
RmEndSession(RmSession);
RmSession = -1;
RmSessionKey[0] = 0;
}
// https://stackoverflow.com/questions/5689904/gracefully-exit-explorer-programmatically
inline BOOL ExitExplorer()
{
HWND hWndTray = FindWindowW(L"Shell_TrayWnd", NULL);
return PostMessageW(hWndTray, 0x5B4, 0, 0);
}
inline void StartExplorer()
{
/*PROCESSENTRY32 pe32 = {0};
pe32.dwSize = sizeof(PROCESSENTRY32);
HANDLE hSnapshot = CreateToolhelp32Snapshot(
TH32CS_SNAPPROCESS,
0
);
if (Process32First(hSnapshot, &pe32) == TRUE)
{
do
{
if (!wcscmp(pe32.szExeFile, TEXT("explorer.exe")))
{
HANDLE hSihost = OpenProcess(
PROCESS_TERMINATE,
FALSE,
pe32.th32ProcessID
);
TerminateProcess(hSihost, 1);
CloseHandle(hSihost);
}
} while (Process32Next(hSnapshot, &pe32) == TRUE);
}
CloseHandle(hSnapshot);
*/
wchar_t wszPath[MAX_PATH];
ZeroMemory(
wszPath,
(MAX_PATH) * sizeof(wchar_t)
);
GetWindowsDirectoryW(
wszPath,
MAX_PATH
);
wcscat_s(
wszPath,
MAX_PATH,
L"\\explorer.exe"
);
STARTUPINFO si;
ZeroMemory(&si, sizeof(STARTUPINFO));
si.cb = sizeof(si);
PROCESS_INFORMATION pi;
ZeroMemory(&pi, sizeof(PROCESS_INFORMATION));
if (CreateProcessW(
NULL,
wszPath,
NULL,
NULL,
TRUE,
CREATE_UNICODE_ENVIRONMENT,
NULL,
NULL,
&si,
&pi
))
{
CloseHandle(pi.hThread);
CloseHandle(pi.hProcess);
}
}
#endif