diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..34c8dee
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,388 @@
+## Ignore Visual Studio temporary files, build results, and
+## files generated by popular Visual Studio add-ons.
+##
+## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
+
+# User-specific files
+*.rsuser
+*.suo
+*.user
+*.userosscache
+*.sln.docstates
+
+# User-specific files (MonoDevelop/Xamarin Studio)
+*.userprefs
+
+# Mono auto generated files
+mono_crash.*
+
+# Build results
+[Dd]ebug/
+[Dd]ebugPublic/
+[Rr]elease/
+[Rr]eleases/
+x64/
+x86/
+[Ww][Ii][Nn]32/
+[Aa][Rr][Mm]/
+[Aa][Rr][Mm]64/
+bld/
+[Bb]in/
+[Oo]bj/
+[Ll]og/
+[Ll]ogs/
+
+# Visual Studio 2015/2017 cache/options directory
+.vs/
+# Uncomment if you have tasks that create the project's static files in wwwroot
+#wwwroot/
+
+# Visual Studio 2017 auto generated files
+Generated\ Files/
+
+# MSTest test Results
+[Tt]est[Rr]esult*/
+[Bb]uild[Ll]og.*
+
+# NUnit
+*.VisualState.xml
+TestResult.xml
+nunit-*.xml
+
+# Build Results of an ATL Project
+[Dd]ebugPS/
+[Rr]eleasePS/
+dlldata.c
+
+# Benchmark Results
+BenchmarkDotNet.Artifacts/
+
+# .NET Core
+project.lock.json
+project.fragment.lock.json
+artifacts/
+
+# ASP.NET Scaffolding
+ScaffoldingReadMe.txt
+
+# StyleCop
+StyleCopReport.xml
+
+# Files built by Visual Studio
+*_i.c
+*_p.c
+*_h.h
+*.ilk
+*.meta
+*.obj
+*.iobj
+*.pch
+*.pdb
+*.ipdb
+*.pgc
+*.pgd
+*.rsp
+*.sbr
+*.tlb
+*.tli
+*.tlh
+*.tmp
+*.tmp_proj
+*_wpftmp.csproj
+*.log
+*.tlog
+*.vspscc
+*.vssscc
+.builds
+*.pidb
+*.svclog
+*.scc
+
+# Chutzpah Test files
+_Chutzpah*
+
+# Visual C++ cache files
+ipch/
+*.aps
+*.ncb
+*.opendb
+*.opensdf
+*.sdf
+*.cachefile
+*.VC.db
+*.VC.VC.opendb
+
+# Visual Studio profiler
+*.psess
+*.vsp
+*.vspx
+*.sap
+
+# Visual Studio Trace Files
+*.e2e
+
+# TFS 2012 Local Workspace
+$tf/
+
+# Guidance Automation Toolkit
+*.gpState
+
+# ReSharper is a .NET coding add-in
+_ReSharper*/
+*.[Rr]e[Ss]harper
+*.DotSettings.user
+
+# TeamCity is a build add-in
+_TeamCity*
+
+# DotCover is a Code Coverage Tool
+*.dotCover
+
+# AxoCover is a Code Coverage Tool
+.axoCover/*
+!.axoCover/settings.json
+
+# Coverlet is a free, cross platform Code Coverage Tool
+coverage*.json
+coverage*.xml
+coverage*.info
+
+# Visual Studio code coverage results
+*.coverage
+*.coveragexml
+
+# NCrunch
+_NCrunch_*
+.*crunch*.local.xml
+nCrunchTemp_*
+
+# MightyMoose
+*.mm.*
+AutoTest.Net/
+
+# Web workbench (sass)
+.sass-cache/
+
+# Installshield output folder
+[Ee]xpress/
+
+# DocProject is a documentation generator add-in
+DocProject/buildhelp/
+DocProject/Help/*.HxT
+DocProject/Help/*.HxC
+DocProject/Help/*.hhc
+DocProject/Help/*.hhk
+DocProject/Help/*.hhp
+DocProject/Help/Html2
+DocProject/Help/html
+
+# Click-Once directory
+publish/
+
+# Publish Web Output
+*.[Pp]ublish.xml
+*.azurePubxml
+# Note: Comment the next line if you want to checkin your web deploy settings,
+# but database connection strings (with potential passwords) will be unencrypted
+*.pubxml
+*.publishproj
+
+# Microsoft Azure Web App publish settings. Comment the next line if you want to
+# checkin your Azure Web App publish settings, but sensitive information contained
+# in these scripts will be unencrypted
+PublishScripts/
+
+# NuGet Packages
+*.nupkg
+# NuGet Symbol Packages
+*.snupkg
+# The packages folder can be ignored because of Package Restore
+**/[Pp]ackages/*
+# except build/, which is used as an MSBuild target.
+!**/[Pp]ackages/build/
+# Uncomment if necessary however generally it will be regenerated when needed
+#!**/[Pp]ackages/repositories.config
+# NuGet v3's project.json files produces more ignorable files
+*.nuget.props
+*.nuget.targets
+
+# Nuget personal access tokens and Credentials
+nuget.config
+
+# Microsoft Azure Build Output
+csx/
+*.build.csdef
+
+# Microsoft Azure Emulator
+ecf/
+rcf/
+
+# Windows Store app package directories and files
+AppPackages/
+BundleArtifacts/
+Package.StoreAssociation.xml
+_pkginfo.txt
+*.appx
+*.appxbundle
+*.appxupload
+
+# Visual Studio cache files
+# files ending in .cache can be ignored
+*.[Cc]ache
+# but keep track of directories ending in .cache
+!?*.[Cc]ache/
+
+# Others
+ClientBin/
+~$*
+*~
+*.dbmdl
+*.dbproj.schemaview
+*.jfm
+*.pfx
+*.publishsettings
+orleans.codegen.cs
+
+# Including strong name files can present a security risk
+# (https://github.com/github/gitignore/pull/2483#issue-259490424)
+#*.snk
+
+# Since there are multiple workflows, uncomment next line to ignore bower_components
+# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
+#bower_components/
+
+# RIA/Silverlight projects
+Generated_Code/
+
+# Backup & report files from converting an old project file
+# to a newer Visual Studio version. Backup files are not needed,
+# because we have git ;-)
+_UpgradeReport_Files/
+Backup*/
+UpgradeLog*.XML
+UpgradeLog*.htm
+ServiceFabricBackup/
+*.rptproj.bak
+
+# SQL Server files
+*.mdf
+*.ldf
+*.ndf
+
+# Business Intelligence projects
+*.rdl.data
+*.bim.layout
+*.bim_*.settings
+*.rptproj.rsuser
+*- [Bb]ackup.rdl
+*- [Bb]ackup ([0-9]).rdl
+*- [Bb]ackup ([0-9][0-9]).rdl
+
+# Microsoft Fakes
+FakesAssemblies/
+
+# GhostDoc plugin setting file
+*.GhostDoc.xml
+
+# Node.js Tools for Visual Studio
+.ntvs_analysis.dat
+node_modules/
+
+# Visual Studio 6 build log
+*.plg
+
+# Visual Studio 6 workspace options file
+*.opt
+
+# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
+*.vbw
+
+# Visual Studio LightSwitch build output
+**/*.HTMLClient/GeneratedArtifacts
+**/*.DesktopClient/GeneratedArtifacts
+**/*.DesktopClient/ModelManifest.xml
+**/*.Server/GeneratedArtifacts
+**/*.Server/ModelManifest.xml
+_Pvt_Extensions
+
+# Paket dependency manager
+.paket/paket.exe
+paket-files/
+
+# FAKE - F# Make
+.fake/
+
+# CodeRush personal settings
+.cr/personal
+
+# Python Tools for Visual Studio (PTVS)
+__pycache__/
+*.pyc
+
+# Cake - Uncomment if you are using it
+# tools/**
+# !tools/packages.config
+
+# Tabs Studio
+*.tss
+
+# Telerik's JustMock configuration file
+*.jmconfig
+
+# BizTalk build output
+*.btp.cs
+*.btm.cs
+*.odx.cs
+*.xsd.cs
+
+# OpenCover UI analysis results
+OpenCover/
+
+# Azure Stream Analytics local run output
+ASALocalRun/
+
+# MSBuild Binary and Structured Log
+*.binlog
+
+# NVidia Nsight GPU debugger configuration file
+*.nvuser
+
+# MFractors (Xamarin productivity tool) working folder
+.mfractor/
+
+# Local History for Visual Studio
+.localhistory/
+
+# BeatPulse healthcheck temp database
+healthchecksdb
+
+# Backup folder for Package Reference Convert tool in Visual Studio 2017
+MigrationBackup/
+
+# Ionide (cross platform F# VS Code tools) working folder
+.ionide/
+
+# Fody - auto-generated XML schema
+FodyWeavers.xsd
+
+# VS Code files for those working on multiple tools
+.vscode/*
+!.vscode/settings.json
+!.vscode/tasks.json
+!.vscode/launch.json
+!.vscode/extensions.json
+*.code-workspace
+
+# Local History for Visual Studio Code
+.history/
+
+# Windows Installer files from build outputs
+*.cab
+*.msi
+*.msix
+*.msm
+*.msp
+
+# JetBrains Rider
+.idea/
+*.sln.iml
diff --git a/DarkLoadLibrary/DarkLoadLibrary.vcxproj b/DarkLoadLibrary/DarkLoadLibrary.vcxproj
index 9a3dd50..0f5324b 100644
--- a/DarkLoadLibrary/DarkLoadLibrary.vcxproj
+++ b/DarkLoadLibrary/DarkLoadLibrary.vcxproj
@@ -44,7 +44,7 @@
true
v142
Unicode
- true
+ false
Application
@@ -119,10 +119,12 @@
true
_CRT_SECURE_NO_WARNINGS;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)
true
+ $(ProjectDir)include
Console
true
+ ntdll.lib;kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies)
@@ -134,7 +136,7 @@
_CRT_SECURE_NO_WARNINGS;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)
true
MultiThreadedDLL
- P:\DarkLoadLibrary\DarkLoadLibrary\include;%(AdditionalIncludeDirectories)
+ $(ProjectDir)include
Console
diff --git a/DarkLoadLibrary/include/darkloadlibrary.h b/DarkLoadLibrary/include/darkloadlibrary.h
index a732475..f0806a7 100644
--- a/DarkLoadLibrary/include/darkloadlibrary.h
+++ b/DarkLoadLibrary/include/darkloadlibrary.h
@@ -18,8 +18,9 @@ typedef struct _DARKMODULE {
} DARKMODULE, *PDARKMODULE;
DARKMODULE DarkLoadLibrary(
- DWORD dwFlags,
+ DWORD dwFlags,
LPCWSTR lpwBuffer,
- DWORD dwLen,
+ LPVOID lpFileBuffer,
+ DWORD dwLen,
LPCWSTR lpwName
);
\ No newline at end of file
diff --git a/DarkLoadLibrary/src/darkloadlibrary.c b/DarkLoadLibrary/src/darkloadlibrary.c
index 6fbc0ba..c650bb3 100644
--- a/DarkLoadLibrary/src/darkloadlibrary.c
+++ b/DarkLoadLibrary/src/darkloadlibrary.c
@@ -144,6 +144,7 @@ BOOL ReadFileToBuffer(
DARKMODULE DarkLoadLibrary(
DWORD dwFlags,
LPCWSTR lpwBuffer,
+ LPVOID lpFileBuffer,
DWORD dwLen,
LPCWSTR lpwName
)
@@ -163,8 +164,15 @@ DARKMODULE DarkLoadLibrary(
break;
case LOAD_MEMORY:
- dModule.ErrorMsg = L"Not implemented yet, sorry";
- goto Cleanup;
+ dModule.dwDllDataLen = dwLen;
+ dModule.pbDllData = lpFileBuffer;
+
+ /*
+ This is probably a hack for the greater scheme but lol
+ */
+ dModule.CrackedDLLName = lpwName;
+ dModule.LocalDLLName = lpwName;
+
break;
case NO_LINK:
diff --git a/DarkLoadLibrary/src/main.c b/DarkLoadLibrary/src/main.c
index 948c9c4..a53f7e8 100644
--- a/DarkLoadLibrary/src/main.c
+++ b/DarkLoadLibrary/src/main.c
@@ -10,6 +10,7 @@ VOID main()
DARKMODULE DarkModule = DarkLoadLibrary(
LOAD_LOCAL_FILE,
L"TestDLL.dll",
+ NULL,
0,
NULL
);
diff --git a/DarkLoadLibrary/src/pebutils.c b/DarkLoadLibrary/src/pebutils.c
index 7a1d457..489f49c 100644
--- a/DarkLoadLibrary/src/pebutils.c
+++ b/DarkLoadLibrary/src/pebutils.c
@@ -3,439 +3,442 @@
ULONG LdrHashEntry(UNICODE_STRING UniName, BOOL XorHash) {
ULONG ulRes = 0;
- RtlHashUnicodeString(
- &UniName,
- TRUE,
- 0,
- &ulRes
- );
+ RtlHashUnicodeString(
+ &UniName,
+ TRUE,
+ 0,
+ &ulRes
+ );
- if (XorHash)
- {
- ulRes &= (LDR_HASH_TABLE_ENTRIES - 1);
- }
+ if (XorHash)
+ {
+ ulRes &= (LDR_HASH_TABLE_ENTRIES - 1);
+ }
return ulRes;
}
PLDR_DATA_TABLE_ENTRY2 FindLdrTableEntry(
- PCWSTR BaseName
+ PCWSTR BaseName
)
{
- PPEB2 pPeb;
- PLDR_DATA_TABLE_ENTRY2 pCurEntry;
- PLIST_ENTRY pListHead, pListEntry;
-
- pPeb = (PPEB2)READ_MEMLOC(PEB_OFFSET);
+ PPEB2 pPeb;
+ PLDR_DATA_TABLE_ENTRY2 pCurEntry;
+ PLIST_ENTRY pListHead, pListEntry;
+
+ pPeb = (PPEB2)READ_MEMLOC(PEB_OFFSET);
- if (pPeb == NULL)
- {
- return NULL;
- }
+ if (pPeb == NULL)
+ {
+ return NULL;
+ }
- pListHead = &pPeb->Ldr->InLoadOrderModuleList;
- pListEntry = pListHead->Flink;
+ pListHead = &pPeb->Ldr->InLoadOrderModuleList;
+ pListEntry = pListHead->Flink;
- do
- {
+ do
+ {
- pCurEntry = CONTAINING_RECORD(pListEntry, LDR_DATA_TABLE_ENTRY2, InLoadOrderLinks);
- pListEntry = pListEntry->Flink;
+ pCurEntry = CONTAINING_RECORD(pListEntry, LDR_DATA_TABLE_ENTRY2, InLoadOrderLinks);
+ pListEntry = pListEntry->Flink;
- INT BaseName1 = _wcsnicmp(BaseName, pCurEntry->BaseDllName.Buffer, (pCurEntry->BaseDllName.Length / sizeof(wchar_t)) - 4);
- INT BaseName2 = _wcsnicmp(BaseName, pCurEntry->BaseDllName.Buffer, pCurEntry->BaseDllName.Length / sizeof(wchar_t));
+ INT BaseName1 = _wcsnicmp(BaseName, pCurEntry->BaseDllName.Buffer, (pCurEntry->BaseDllName.Length / sizeof(wchar_t)) - 4);
+ INT BaseName2 = _wcsnicmp(BaseName, pCurEntry->BaseDllName.Buffer, pCurEntry->BaseDllName.Length / sizeof(wchar_t));
- if (!BaseName1 || !BaseName2)
- {
- return pCurEntry;
- }
+ if (!BaseName1 || !BaseName2)
+ {
+ return pCurEntry;
+ }
- } while (pListEntry != pListHead);
+ } while (pListEntry != pListHead);
- return NULL;
+ return NULL;
}
PRTL_RB_TREE FindModuleBaseAddressIndex()
{
- SIZE_T stEnd = NULL;
- PRTL_BALANCED_NODE pNode = NULL;
- PRTL_RB_TREE pModBaseAddrIndex = NULL;
+ SIZE_T stEnd = NULL;
+ PRTL_BALANCED_NODE pNode = NULL;
+ PRTL_RB_TREE pModBaseAddrIndex = NULL;
- PLDR_DATA_TABLE_ENTRY2 pLdrEntry = FindLdrTableEntry(L"ntdll.dll");
+ PLDR_DATA_TABLE_ENTRY2 pLdrEntry = FindLdrTableEntry(L"ntdll.dll");
- pNode = &pLdrEntry->BaseAddressIndexNode;
+ pNode = &pLdrEntry->BaseAddressIndexNode;
- do
- {
- pNode = (PRTL_BALANCED_NODE)(pNode->ParentValue & (~7));
- } while (pNode->ParentValue & (~7));
+ do
+ {
+ pNode = (PRTL_BALANCED_NODE)(pNode->ParentValue & (~7));
+ } while (pNode->ParentValue & (~7));
- if (!pNode->Red)
- {
- DWORD dwLen = NULL;
- SIZE_T stBegin = NULL;
+ if (!pNode->Red)
+ {
+ DWORD dwLen = NULL;
+ SIZE_T stBegin = NULL;
- PIMAGE_NT_HEADERS pNtHeaders = RVA(
- PIMAGE_NT_HEADERS,
- pLdrEntry->DllBase,
- ((PIMAGE_DOS_HEADER)pLdrEntry->DllBase)->e_lfanew
- );
+ PIMAGE_NT_HEADERS pNtHeaders = RVA(
+ PIMAGE_NT_HEADERS,
+ pLdrEntry->DllBase,
+ ((PIMAGE_DOS_HEADER)pLdrEntry->DllBase)->e_lfanew
+ );
- PIMAGE_SECTION_HEADER pSection = IMAGE_FIRST_SECTION(pNtHeaders);
+ PIMAGE_SECTION_HEADER pSection = IMAGE_FIRST_SECTION(pNtHeaders);
- for (INT i = 0; i < pNtHeaders->FileHeader.NumberOfSections; i++)
- {
- if (!strcmp(".data", (LPCSTR)pSection->Name))
- {
- stBegin = (SIZE_T)pLdrEntry->DllBase + pSection->VirtualAddress;
- dwLen = pSection->Misc.VirtualSize;
+ for (INT i = 0; i < pNtHeaders->FileHeader.NumberOfSections; i++)
+ {
+ if (!strcmp(".data", (LPCSTR)pSection->Name))
+ {
+ stBegin = (SIZE_T)pLdrEntry->DllBase + pSection->VirtualAddress;
+ dwLen = pSection->Misc.VirtualSize;
- break;
- }
+ break;
+ }
- ++pSection;
- }
+ ++pSection;
+ }
- for (DWORD i = 0; i < dwLen - sizeof(SIZE_T); ++stBegin, ++i)
- {
+ for (DWORD i = 0; i < dwLen - sizeof(SIZE_T); ++stBegin, ++i)
+ {
- SIZE_T stRet = RtlCompareMemory(
- (PVOID)stBegin,
- (PVOID)&pNode,
- sizeof(SIZE_T)
- );
+ SIZE_T stRet = RtlCompareMemory(
+ (PVOID)stBegin,
+ (PVOID)&pNode,
+ sizeof(SIZE_T)
+ );
- if (stRet == sizeof(SIZE_T))
- {
- stEnd = stBegin;
- break;
- }
- }
+ if (stRet == sizeof(SIZE_T))
+ {
+ stEnd = stBegin;
+ break;
+ }
+ }
- if (stEnd == NULL)
- {
- return NULL;
- }
+ if (stEnd == NULL)
+ {
+ return NULL;
+ }
- PRTL_RB_TREE pTree = (PRTL_RB_TREE)stEnd;
-
- if (pTree && pTree->Root && pTree->Min)
- {
- pModBaseAddrIndex = pTree;
- }
- }
-
- return pModBaseAddrIndex;
+ PRTL_RB_TREE pTree = (PRTL_RB_TREE)stEnd;
+
+ if (pTree && pTree->Root && pTree->Min)
+ {
+ pModBaseAddrIndex = pTree;
+ }
+ }
+
+ return pModBaseAddrIndex;
}
BOOL AddBaseAddressEntry(
- PLDR_DATA_TABLE_ENTRY2 pLdrEntry,
- PVOID lpBaseAddr
+ PLDR_DATA_TABLE_ENTRY2 pLdrEntry,
+ PVOID lpBaseAddr
)
{
- PRTL_RB_TREE pModBaseAddrIndex = FindModuleBaseAddressIndex();
+ PRTL_RB_TREE pModBaseAddrIndex = FindModuleBaseAddressIndex();
- if (!pModBaseAddrIndex)
- {
- return FALSE;
- }
+ if (!pModBaseAddrIndex)
+ {
+ return FALSE;
+ }
- BOOL bRight = FALSE;
- PLDR_DATA_TABLE_ENTRY2 pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pModBaseAddrIndex - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
+ BOOL bRight = FALSE;
+ PLDR_DATA_TABLE_ENTRY2 pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pModBaseAddrIndex - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
- do
- {
+ do
+ {
- if (lpBaseAddr < pLdrNode->DllBase)
- {
- if (!pLdrNode->BaseAddressIndexNode.Left)
- {
- break;
- }
+ if (lpBaseAddr < pLdrNode->DllBase)
+ {
+ if (!pLdrNode->BaseAddressIndexNode.Left)
+ {
+ break;
+ }
- pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pLdrNode->BaseAddressIndexNode.Left - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
- }
+ pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pLdrNode->BaseAddressIndexNode.Left - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
+ }
- else if (lpBaseAddr > pLdrNode->DllBase)
- {
- if (!pLdrNode->BaseAddressIndexNode.Right)
- {
- bRight = TRUE;
- break;
- }
+ else if (lpBaseAddr > pLdrNode->DllBase)
+ {
+ if (!pLdrNode->BaseAddressIndexNode.Right)
+ {
+ bRight = TRUE;
+ break;
+ }
- pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pLdrNode->BaseAddressIndexNode.Right - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
- }
+ pLdrNode = (PLDR_DATA_TABLE_ENTRY2)((size_t)pLdrNode->BaseAddressIndexNode.Right - offsetof(LDR_DATA_TABLE_ENTRY2, BaseAddressIndexNode));
+ }
- else
- {
- pLdrNode->DdagNode->LoadCount++;
- }
+ else
+ {
+ pLdrNode->DdagNode->LoadCount++;
+ }
- } while (TRUE);
+ } while (TRUE);
- RtlRbInsertNodeEx(pModBaseAddrIndex, &pLdrNode->BaseAddressIndexNode, bRight, &pLdrEntry->BaseAddressIndexNode);
+ RtlRbInsertNodeEx(pModBaseAddrIndex, &pLdrNode->BaseAddressIndexNode, bRight, &pLdrEntry->BaseAddressIndexNode);
- return TRUE;
+ return TRUE;
}
PLIST_ENTRY FindHashTable() {
- PLIST_ENTRY pList = NULL;
- PLIST_ENTRY pHead = NULL;
- PLIST_ENTRY pEntry = NULL;
- PLDR_DATA_TABLE_ENTRY2 pCurrentEntry = NULL;
+ PLIST_ENTRY pList = NULL;
+ PLIST_ENTRY pHead = NULL;
+ PLIST_ENTRY pEntry = NULL;
+ PLDR_DATA_TABLE_ENTRY2 pCurrentEntry = NULL;
- PPEB2 pPeb = (PPEB2)READ_MEMLOC(PEB_OFFSET);
+ PPEB2 pPeb = (PPEB2)READ_MEMLOC(PEB_OFFSET);
pHead = &pPeb->Ldr->InInitializationOrderModuleList;
- pEntry = pHead->Flink;
+ pEntry = pHead->Flink;
- do
- {
- pCurrentEntry = CONTAINING_RECORD(
- pEntry,
- LDR_DATA_TABLE_ENTRY2,
- InInitializationOrderLinks
- );
+ do
+ {
+ pCurrentEntry = CONTAINING_RECORD(
+ pEntry,
+ LDR_DATA_TABLE_ENTRY2,
+ InInitializationOrderLinks
+ );
- pEntry = pEntry->Flink;
+ pEntry = pEntry->Flink;
- if (pCurrentEntry->HashLinks.Flink == &pCurrentEntry->HashLinks)
- {
- continue;
- }
+ if (pCurrentEntry->HashLinks.Flink == &pCurrentEntry->HashLinks)
+ {
+ continue;
+ }
- pList = pCurrentEntry->HashLinks.Flink;
+ pList = pCurrentEntry->HashLinks.Flink;
- if (pList->Flink == &pCurrentEntry->HashLinks)
- {
- ULONG ulHash = LdrHashEntry(
- pCurrentEntry->BaseDllName,
- TRUE
- );
+ if (pList->Flink == &pCurrentEntry->HashLinks)
+ {
+ ULONG ulHash = LdrHashEntry(
+ pCurrentEntry->BaseDllName,
+ TRUE
+ );
- pList = (PLIST_ENTRY)(
- (size_t)pCurrentEntry->HashLinks.Flink -
- ulHash *
- sizeof(LIST_ENTRY)
- );
+ pList = (PLIST_ENTRY)(
+ (size_t)pCurrentEntry->HashLinks.Flink -
+ ulHash *
+ sizeof(LIST_ENTRY)
+ );
break;
}
- pList = NULL;
- } while (pHead != pEntry);
+ pList = NULL;
+ } while (pHead != pEntry);
- return pList;
+ return pList;
}
VOID InsertTailList(
- PLIST_ENTRY ListHead,
- PLIST_ENTRY Entry
+ PLIST_ENTRY ListHead,
+ PLIST_ENTRY Entry
)
{
- PLIST_ENTRY Blink;
+ PLIST_ENTRY Blink;
- Blink = ListHead->Blink;
- Entry->Flink = ListHead;
- Entry->Blink = Blink;
- Blink->Flink = Entry;
- ListHead->Blink = Entry;
+ Blink = ListHead->Blink;
+ Entry->Flink = ListHead;
+ Entry->Blink = Blink;
+ Blink->Flink = Entry;
+ ListHead->Blink = Entry;
- return;
+ return;
}
BOOL AddHashTableEntry(
- PLDR_DATA_TABLE_ENTRY2 pLdrEntry
+ PLDR_DATA_TABLE_ENTRY2 pLdrEntry
)
{
- PPEB pPeb;
- PPEB_LDR_DATA2 pPebData;
- PLIST_ENTRY LdrpHashTable;
+ PPEB pPeb;
+ PPEB_LDR_DATA2 pPebData;
+ PLIST_ENTRY LdrpHashTable;
- pPeb = (PPEB)READ_MEMLOC(PEB_OFFSET);
+ pPeb = (PPEB)READ_MEMLOC(PEB_OFFSET);
- RtlInitializeListEntry(
- &pLdrEntry->HashLinks
- );
+ RtlInitializeListEntry(
+ &pLdrEntry->HashLinks
+ );
- LdrpHashTable = FindHashTable();
- if (!LdrpHashTable)
- {
- return FALSE;
- }
+ LdrpHashTable = FindHashTable();
+ if (!LdrpHashTable)
+ {
+ return FALSE;
+ }
- pPebData = (PPEB_LDR_DATA2)pPeb->Ldr;
+ pPebData = (PPEB_LDR_DATA2)pPeb->Ldr;
- // insert into hash table
+ // insert into hash table
ULONG ulHash = LdrHashEntry(
- pLdrEntry->BaseDllName,
- TRUE
- );
+ pLdrEntry->BaseDllName,
+ TRUE
+ );
- InsertTailList(
- &LdrpHashTable[ulHash],
- &pLdrEntry->HashLinks
- );
+ InsertTailList(
+ &LdrpHashTable[ulHash],
+ &pLdrEntry->HashLinks
+ );
// insert into other lists
InsertTailList(
- &pPebData->InLoadOrderModuleList,
- &pLdrEntry->InLoadOrderLinks
- );
+ &pPebData->InLoadOrderModuleList,
+ &pLdrEntry->InLoadOrderLinks
+ );
InsertTailList(
- &pPebData->InMemoryOrderModuleList,
- &pLdrEntry->InMemoryOrderLinks
- );
+ &pPebData->InMemoryOrderModuleList,
+ &pLdrEntry->InMemoryOrderLinks
+ );
InsertTailList(
- &pPebData->InInitializationOrderModuleList,
- &pLdrEntry->InInitializationOrderLinks
- );
+ &pPebData->InInitializationOrderModuleList,
+ &pLdrEntry->InInitializationOrderLinks
+ );
- return TRUE;
+ return TRUE;
}
HMODULE IsModulePresent(
- LPCWSTR lpwName
+ LPCWSTR lpwName
)
{
- PPEB pPeb;
- PUCHAR ucModPtrOff;
- PLDR_DATA_TABLE_ENTRY2 pLdrTbl;
-
- pPeb = (PPEB)READ_MEMLOC(PEB_OFFSET);
+ if (lpwName == NULL)
+ return (HMODULE)NULL;
- PLIST_ENTRY pModListEnd = &pPeb->Ldr->InMemoryOrderModuleList;
- PLIST_ENTRY pModList = pModListEnd->Flink;
+ PPEB pPeb;
+ PUCHAR ucModPtrOff;
+ PLDR_DATA_TABLE_ENTRY2 pLdrTbl;
+
+ pPeb = (PPEB)READ_MEMLOC(PEB_OFFSET);
- do
- {
- ucModPtrOff = (PUCHAR)pModList - (sizeof(LIST_ENTRY));
+ PLIST_ENTRY pModListEnd = &pPeb->Ldr->InMemoryOrderModuleList;
+ PLIST_ENTRY pModList = pModListEnd->Flink;
- pLdrTbl = (PLDR_DATA_TABLE_ENTRY2)ucModPtrOff;
+ do
+ {
+ ucModPtrOff = (PUCHAR)pModList - (sizeof(LIST_ENTRY));
- if (!_wcsicmp(
- pLdrTbl->BaseDllName.Buffer,
- (PWSTR)lpwName)
- )
- {
- // already loaded, so return the base address
- return (ULONG_PTR)pLdrTbl->DllBase;
- }
+ pLdrTbl = (PLDR_DATA_TABLE_ENTRY2)ucModPtrOff;
- pModList = pModList->Flink;
- } while (pModList != pModListEnd);
+ if (!_wcsicmp(
+ pLdrTbl->BaseDllName.Buffer,
+ (PWSTR)lpwName)
+ )
+ {
+ // already loaded, so return the base address
+ return (ULONG_PTR)pLdrTbl->DllBase;
+ }
- return (HMODULE)NULL;
+ pModList = pModList->Flink;
+ } while (pModList != pModListEnd);
+
+ return (HMODULE)NULL;
}
BOOL LinkModuleToPEB(
- PDARKMODULE pdModule
+ PDARKMODULE pdModule
)
{
- PIMAGE_NT_HEADERS pNtHeaders;
- UNICODE_STRING FullDllName, BaseDllName;
- PLDR_DATA_TABLE_ENTRY2 pLdrEntry = NULL;
+ PIMAGE_NT_HEADERS pNtHeaders;
+ UNICODE_STRING FullDllName, BaseDllName;
+ PLDR_DATA_TABLE_ENTRY2 pLdrEntry = NULL;
- pNtHeaders = RVA(
- PIMAGE_NT_HEADERS,
- pdModule->pbDllData,
- ((PIMAGE_DOS_HEADER)pdModule->pbDllData)->e_lfanew
- );
+ pNtHeaders = RVA(
+ PIMAGE_NT_HEADERS,
+ pdModule->pbDllData,
+ ((PIMAGE_DOS_HEADER)pdModule->pbDllData)->e_lfanew
+ );
- // convert the names to unicode
- RtlInitUnicodeString(
- &FullDllName,
- pdModule->LocalDLLName
- );
+ // convert the names to unicode
+ RtlInitUnicodeString(
+ &FullDllName,
+ pdModule->LocalDLLName
+ );
- RtlInitUnicodeString(
- &BaseDllName,
- pdModule->CrackedDLLName
- );
+ RtlInitUnicodeString(
+ &BaseDllName,
+ pdModule->CrackedDLLName
+ );
- // link the entry to the PEB
- pLdrEntry = (PLDR_DATA_TABLE_ENTRY2)HeapAlloc(
- GetProcessHeap(),
- HEAP_ZERO_MEMORY,
- sizeof(LDR_DATA_TABLE_ENTRY2)
- );
+ // link the entry to the PEB
+ pLdrEntry = (PLDR_DATA_TABLE_ENTRY2)HeapAlloc(
+ GetProcessHeap(),
+ HEAP_ZERO_MEMORY,
+ sizeof(LDR_DATA_TABLE_ENTRY2)
+ );
- if (!pLdrEntry)
- {
- return FALSE;
- }
+ if (!pLdrEntry)
+ {
+ return FALSE;
+ }
- // start setting the values in the entry
- NtQuerySystemTime(&pLdrEntry->LoadTime);
+ // start setting the values in the entry
+ NtQuerySystemTime(&pLdrEntry->LoadTime);
- // do the obvious ones
- pLdrEntry->ReferenceCount = 1;
- pLdrEntry->LoadReason = LoadReasonDynamicLoad;
- pLdrEntry->OriginalBase = pNtHeaders->OptionalHeader.ImageBase;
+ // do the obvious ones
+ pLdrEntry->ReferenceCount = 1;
+ pLdrEntry->LoadReason = LoadReasonDynamicLoad;
+ pLdrEntry->OriginalBase = pNtHeaders->OptionalHeader.ImageBase;
- // set the hash value
- pLdrEntry->BaseNameHashValue = LdrHashEntry(
- BaseDllName,
- FALSE
- );
+ // set the hash value
+ pLdrEntry->BaseNameHashValue = LdrHashEntry(
+ BaseDllName,
+ FALSE
+ );
- // correctly add the base address to the entry
- AddBaseAddressEntry(
- pLdrEntry,
- pdModule->ModuleBase
- );
+ // correctly add the base address to the entry
+ AddBaseAddressEntry(
+ pLdrEntry,
+ pdModule->ModuleBase
+ );
- // an the rest
- pLdrEntry->ImageDll = TRUE;
- pLdrEntry->LoadNotificationsSent = TRUE; // lol
- pLdrEntry->EntryProcessed = TRUE;
- pLdrEntry->InLegacyLists = TRUE;
- pLdrEntry->InIndexes = TRUE;
- pLdrEntry->ProcessAttachCalled = TRUE;
- pLdrEntry->InExceptionTable = FALSE;
- pLdrEntry->DllBase = (PVOID)pdModule->ModuleBase;
- pLdrEntry->SizeOfImage = pNtHeaders->OptionalHeader.SizeOfImage;
- pLdrEntry->TimeDateStamp = pNtHeaders->FileHeader.TimeDateStamp;
- pLdrEntry->BaseDllName = BaseDllName;
- pLdrEntry->FullDllName = FullDllName;
- pLdrEntry->ObsoleteLoadCount = 1;
- pLdrEntry->Flags = LDRP_IMAGE_DLL | LDRP_ENTRY_INSERTED | LDRP_ENTRY_PROCESSED | LDRP_PROCESS_ATTACH_CALLED;
+ // an the rest
+ pLdrEntry->ImageDll = TRUE;
+ pLdrEntry->LoadNotificationsSent = TRUE; // lol
+ pLdrEntry->EntryProcessed = TRUE;
+ pLdrEntry->InLegacyLists = TRUE;
+ pLdrEntry->InIndexes = TRUE;
+ pLdrEntry->ProcessAttachCalled = TRUE;
+ pLdrEntry->InExceptionTable = FALSE;
+ pLdrEntry->DllBase = (PVOID)pdModule->ModuleBase;
+ pLdrEntry->SizeOfImage = pNtHeaders->OptionalHeader.SizeOfImage;
+ pLdrEntry->TimeDateStamp = pNtHeaders->FileHeader.TimeDateStamp;
+ pLdrEntry->BaseDllName = BaseDllName;
+ pLdrEntry->FullDllName = FullDllName;
+ pLdrEntry->ObsoleteLoadCount = 1;
+ pLdrEntry->Flags = LDRP_IMAGE_DLL | LDRP_ENTRY_INSERTED | LDRP_ENTRY_PROCESSED | LDRP_PROCESS_ATTACH_CALLED;
- // set the correct values in the Ddag node struct
- pLdrEntry->DdagNode = (PLDR_DDAG_NODE)HeapAlloc(
- GetProcessHeap(),
- HEAP_ZERO_MEMORY,
- sizeof(LDR_DDAG_NODE)
- );
+ // set the correct values in the Ddag node struct
+ pLdrEntry->DdagNode = (PLDR_DDAG_NODE)HeapAlloc(
+ GetProcessHeap(),
+ HEAP_ZERO_MEMORY,
+ sizeof(LDR_DDAG_NODE)
+ );
- if (!pLdrEntry->DdagNode)
- {
- return 0;
- }
+ if (!pLdrEntry->DdagNode)
+ {
+ return 0;
+ }
- pLdrEntry->NodeModuleLink.Flink = &pLdrEntry->DdagNode->Modules;
- pLdrEntry->NodeModuleLink.Blink = &pLdrEntry->DdagNode->Modules;
- pLdrEntry->DdagNode->Modules.Flink = &pLdrEntry->NodeModuleLink;
- pLdrEntry->DdagNode->Modules.Blink = &pLdrEntry->NodeModuleLink;
- pLdrEntry->DdagNode->State = LdrModulesReadyToRun;
- pLdrEntry->DdagNode->LoadCount = 1;
+ pLdrEntry->NodeModuleLink.Flink = &pLdrEntry->DdagNode->Modules;
+ pLdrEntry->NodeModuleLink.Blink = &pLdrEntry->DdagNode->Modules;
+ pLdrEntry->DdagNode->Modules.Flink = &pLdrEntry->NodeModuleLink;
+ pLdrEntry->DdagNode->Modules.Blink = &pLdrEntry->NodeModuleLink;
+ pLdrEntry->DdagNode->State = LdrModulesReadyToRun;
+ pLdrEntry->DdagNode->LoadCount = 1;
- // add the hash to the LdrpHashTable
- AddHashTableEntry(
- pLdrEntry
- );
+ // add the hash to the LdrpHashTable
+ AddHashTableEntry(
+ pLdrEntry
+ );
- // set the entry point
- pLdrEntry->EntryPoint = RVA(
- PVOID,
- pdModule->ModuleBase,
- pNtHeaders->OptionalHeader.AddressOfEntryPoint
- );
+ // set the entry point
+ pLdrEntry->EntryPoint = RVA(
+ PVOID,
+ pdModule->ModuleBase,
+ pNtHeaders->OptionalHeader.AddressOfEntryPoint
+ );
- return TRUE;
+ return TRUE;
}
\ No newline at end of file
diff --git a/README.md b/README.md
index e6a5133..b4829db 100644
--- a/README.md
+++ b/README.md
@@ -12,6 +12,7 @@ https://www.mdsec.co.uk/2021/06/bypassing-image-load-kernel-callbacks/
DARKMODULE DarkModule = DarkLoadLibrary(
LOAD_LOCAL_FILE, // control flags
L"TestDLL.dll", // local dll path, if loading from disk
+ NULL, // DLL Buffer to load from if loading from memory
0, // dll size if loading from memory
NULL // dll name if loaded from memory
);
@@ -26,6 +27,10 @@ DARKMODULE DarkModule = DarkLoadLibrary(
This can be any path that `CreateFileW` will open.
+### DLL Buffer:
+
+This argument is only needed when `LOAD_MEMORY` is set. In that case this argument should be the buffer containing the DLL.
+
#### DLL Size:
This argument is only needed when `LOAD_MEMORY` is set. In that case this argument should be the size of the buffer containing the DLL.