{
	"id": "10135f9d-bb63-4f21-9cdd-a0d30b5b7db3",
	"created_at": "2026-04-06T00:19:41.627123Z",
	"updated_at": "2026-04-10T13:12:15.578082Z",
	"deleted_at": null,
	"sha1_hash": "691983778ba51eb4067d35d2c9cad7a4c583dc0f",
	"title": "Inexorable PowerShell - A Red Teamer's Tale of Overcoming Simple AppLocker Policies",
	"llm_title": "",
	"authors": "",
	"file_creation_date": "0001-01-01T00:00:00Z",
	"file_modification_date": "0001-01-01T00:00:00Z",
	"file_size": 153602,
	"plain_text": "Inexorable PowerShell - A Red Teamer's Tale of Overcoming\r\nSimple AppLocker Policies\r\nBy sixdub\r\nPublished: 2014-12-02 · Archived: 2026-04-05 23:15:49 UTC\r\n*EDIT* This repo has been renamed to PowerPick and added to the Veil-Framework’s PowerTools. Find it\r\nHERE! See below for more edits. *EDIT*\r\nAttackers have evolved to love PowerShell more than most defenders or system administrators. Tools like\r\nPowersploit’, Veil Power*, and Nishang have become routine capabilities used by Red Teams, Pentesters, Evil\r\nattackers, and skiddies alike. With this evolution and overall consolidation of techniques into a single scripting\r\nlanguage, surely defenders have found a proven method to prevent PowerShell execution? Surely Software\r\nRestriction Policies (SRP) or AppLocker can save the day? Don’t be so sure…\r\nAssessment after Assessment, I find that we can compromise a domain user, elevate local privileges, steal\r\ncredentials, inject payloads, and escalate in the domain all using PowerShell. I have nightmares of the day\r\nsomeone effectively restricts PowerShell and some of the old school tactics must return. From my conversations\r\nwith defenders or infosec junkies, awareness of these techniques is on the rise and people are finally starting to\r\npay attention to the routine release of PowerShell tools to aid in offense. With that being said, until disabling\r\nPowerShell on unneeded systems becomes common practice in the trenches of commercial enterprise, attackers\r\nwill still have an easy[ier] win. At this point, the restriction of PowerShell is unlikely to happen until the time/cost\r\nrequired to implement such defensives are minimized to a point where it can be realistically accomplished natively\r\nat scale.\r\nFor some previous research attackers’ use of PowerShell:\r\nFireEye WhitePaper from Blackhat – Includes discussion of incident response with PowerShell. Awesome\r\nwriteup! Props to these guys for taking a stab at defensive conversation in this arena. I hope to see some of\r\nthis work recreated on an engagement some time.\r\nCrowdstrike Report on DeepPanda – Example of threat actor using PowerShell\r\nWeaponizing PowerShell – harmj0ys post on weaponizing PowerShell. Good write up on bypassing\r\nexecution restrictions\r\nPowerShell Basics – Carlos Perez tutorials on PowerShell. Definitely worth the read\r\nPowersploit’ Github – Essential for Offensive PowerShell users\r\nIn The Words of The Defenders – “Use Applocker”\r\nDisclaimer: This is not intended to be a guide on AppLocker. Later you will see, this is a guide of what not to do!\r\nAlso, I am not a Microsoft Certified Systems Engineer (MSCE) or any sort of Microsoft professional. There might\r\nbe ways to properly configure AppLocker to prevent PowerShell… but they are not publicized enough if they\r\nexist! I googled as much as the average network defender would.\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 1 of 7\n\nAppLocker is the Microsoft solution for “application control in the enterprise”. It is built to restrict unwanted\r\nsoftware from being executed and provides a variety of methods to accomplish this. It allows you to specify\r\npolicies that limit executables, DLLs, installers or scripts by path, hash, or publisher. The resulting policies are\r\nthen pushed out by Group Policy and managed centrally.\r\nObviously there is the regularly preached balance between usability and security but I find it important here to\r\nmention that the best setup possible with AppLocker would utilize a whitelist approach. Organizations could\r\nanalyze their standard images and build policies to match this image. With that being said, the CEO wouldn’t be\r\nable to install their P2P software, the user wouldn’t be able to run World of Warcraft, and tech support would have\r\nan increase call volume by 3000% (Seriously hope to never work help desk… but I sure do appreciate the work\r\nthey do!). For this reason, organizations still rely on blacklist based policies to prevent the use of net*.exe,\r\ncmd.exe and powershell.exe.\r\nFor the purpose of my demo, I intended to mimic an organization that used AppLocker in a black list fashion. My\r\ngoal was to use AppLocker as much as possible to block PowerShell and test appropriate measures to get around\r\nthe blacklist.\r\nI tested with a Windows 7 system. I performed the following actions to attempt to setup and secure my test\r\nmachine:\r\nStarted the Application Identity service\r\nAdded Executable Rules to deny by hash the following executables:\r\nC:\\windows\\system32\\WindowsPowerShellv1.0\\powershell.exe\r\nC:\\windows\\system32\\WindowsPowerShellv1.0\\powershell_ise.exe\r\nC:\\windows\\Syswow64\\WindowsPowerShellv1.0\\powershell.exe\r\nC:\\windows\\Syswow64\\WindowsPowerShellv1.0\\powershell_ise.exe\r\nAdded Script Rules to deny by path: *.ps1*\r\nEnabled “Enforce” on DLL Rules (AppLocker-\u003eProperties)\r\nAdded DLL Rules to deny by hash the following DLLs:\r\nC:\\Program Files\\Reference\r\nAssemblies\\Microsoft\\WindowsPowerShellv1.0\\Microsoft.PowerShell.Commands.Management.dll\r\nC:\\Program Files\\Reference\r\nAssemblies\\Microsoft\\WindowsPowerShellv1.0\\Microsoft.PowerShell.Commands.Utility.dll\r\nC:\\Program Files\\Reference\r\nAssemblies\\Microsoft\\WindowsPowerShellv1.0\\Microsoft.PowerShell.ConsoleHost.dll\r\nC:\\Program Files\\Reference\r\nAssemblies\\Microsoft\\WindowsPowerShellv1.0\\Microsoft.PowerShell.Security.dll\r\nC:\\Program Files\\Reference\r\nAssemblies\\Microsoft\\WindowsPowerShellv1.0\\System.Management.Automation.dll\r\nTested to ensure the block worked! SUCCESS!\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 2 of 7\n\nThe Work Around – Lock Picking the AppLocker\r\nI have recently gotten into the Offensive PowerShell world and have only tip toed at this point.  I have heard a\r\ncouple people discuss methods of bypassing the AppLocker rules with regards to PowerShell. Personally, I give\r\nprops to harmj0y for the inspiration and tips in the right direction. I also know many of the ideas and initial\r\nresearch discovering this technique came from darkoperator and a few others in the offensive PowerShell\r\ncommunity. Thanks to those who came before and paved the way. Would love to hear if you have better methods!\r\nPowerShell provides backend access through the .NET framework and Windows Common Language Interface\r\n(CLI). Developers love the extensibility this provides and many examples exist online for how to use these\r\nfeatures to create utilities to do fun sys-ad type things. Few people realized that the same code could be used to\r\npackage PowerShell as a workaround for AppLocker restrictions.\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 3 of 7\n\nTake a read of this for info on how to invoke PS scripts in C#.\r\nFirst I must configure my project and add the Automation assembly as a reference:\r\nRC on References-\u003eAdd Reference\r\nBrowse and select: C:Program FilesReference\r\nAssembliesMicrosoftWindowsPowerShellv1.0System.Management.Automation.dll\r\nIn order to load from a resource, I must first create a resource:\r\nOpen Resources.resx\r\nAdd String Resource\r\nName the string “Script”\r\nSet the value to “Get-Process” or whatever script you want to execute\r\nAfter creating the project, I instantiate my Runspace and create the Pipeline that will be used to execute\r\ncommands\r\n//Init stuff\r\nRunspace runspace = RunspaceFactory.CreateRunspace();\r\nrunspace.Open();\r\nRunspaceInvoke scriptInvoker = new RunspaceInvoke(runspace);\r\nPipeline pipeline = runspace.CreatePipeline();\r\nNext, I extract a PowerShell script from the resource section and add it to the pipeline. This could be changed to\r\nread a PowerShell script from the internet, from an encrypted string, etc. In a target environment, it would be\r\nimportant to obfuscate/encrypt the script to prevent AV or HIPS from triggering on the plaintext script. I have see\r\non disk scripts get a Red Team caught every now and then….\r\n//Add commands\r\nstring script = Properties.Resources.ResourceManager.GetString(\"Script\");\r\npipeline.Commands.AddScript(script);\r\nTo retrieve the output from the script, I add the “Out-String” command onto the pipeline and grab the return\r\nobjects. iterate over these objects with a string builder to return the final output string.\r\n//Prep PS for string output and invoke\r\npipeline.Commands.Add(\"Out-String\");\r\nCollection results = pipeline.Invoke();\r\nrunspace.Close();\r\n//Convert records to strings\r\nStringBuilder stringBuilder = new StringBuilder();\r\nforeach (PSObject obj in results)\r\n{\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 4 of 7\n\nstringBuilder.AppendLine(obj.ToString());\r\n}\r\nConsole.Write(stringBuilder.ToString());\r\nCompiling this executable and throwing it into the test environment results in an astounding success. Despite all\r\nof the preventions on running PowerShell, our executable was able to access the API and run any script we chose.\r\nI tested it primarily with Veil-PowerView. 20ish lines of C# demonstrated a pretty rudimentary proof of concept.\r\nThere are some obvious downsides to this bypass…\r\nOffensive capability put on disk (although script could be fetched from internet)\r\nManaged code, namely .NET is easily decompiled\r\nWhitelist environments defeat this\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 5 of 7\n\nDefeat The Workaround\r\nThis was just too easy… The heavy reliance on .NET had me confident there was an easy way to stop this.  In my\r\ntest environment, I spent some time in Process Explorer and Process Monitor digging around a dump of my\r\nmalicious application. I confirmed that the custom executable was loading the .NET assemblies to accomplish the\r\nPowerShell execution. In the words of Microsoft, “Assemblies are the building blocks of the .NET Framework”.\r\nEssentially, assemblies are the libraries that make up the CLI. For the most part, the assemblies are stored in the\r\nGlobal Assembly Cache (GAC) at C:WindowsAssembly. Neat fact, .NET loads the assemblies at run time as they\r\nare needed… not upon initial application execution. As I played with the code, I could see the point where the\r\nassembly would get loaded. Below are a sampling of the file handles I saw open:\r\nC:WindowsassemblyGAC_MSILMicrosoft.PowerShell.Commands.Diagnostics1.0.0.0__31bf3856ad364e35Mic\r\nC:WindowsassemblyGAC_MSILSystem.Management.Automation1.0.0.0__31bf3856ad364e35System.Managemen\r\nRunning quickly back to AppLocker, I added all of the PowerShell specific assemblies from the GAC to the deny\r\npolicy by hash. To get the assembly DLLs blocked in AppLocker and allow explorer to access the backend\r\nassembly libraries, I had to disable the “Cache Viewer” functionality. Definitely be sure to reenable this if you\r\nwant drag-and-drop install of assemblies.  A quick reg command FTW:\r\nreg add HKLMSoftwareMicrosoftFusion /v DisableCacheViewer /t REG_DWORD /d 1\r\nFor some reason, the assembly deny policy still failed to deny execution to my malicious application. At first I\r\nthought it might be due to the fact that the DLL was hidden in an assembly, but after testing, that turned out to be\r\nfalse. Other assembly DLLs could be blocked. See the follow up section for more info! The only DLL that I could\r\nfind that would successfully prevent execution via AppLocker DLL Rules was:\r\nC:WindowsMicrosoft.NETassemblyGAC_32System.Transactionsv4.0_4.0.0.0__b77a5c561934e089System.Transacti\r\nThis prevented the execution of my malicious script but the DLL being blocked was the library responsible for all\r\ntransactional classes (aka the ability to create a resource manager). This was an unreasonable block as tons of\r\nlegitimate .NET applications require resources. Finally, I moved on to the obvious: rename/move the PowerShell\r\nassemblies.\r\nmkdir c:windowsassemblydisabled\r\nmove c:windowsassemblyGAC_MSILMicrosoft.PowerShell.Commands.Management1.0.0.0__31bf3856ad364e35Micros\r\nObviously this worked and prevented execution of my malicious application. In my mind, this is a limited solution\r\ndue to the inflexibility of having to install/uninstall assemblies. It would be ideal to have a configurable policy to\r\nallow the assembly to be used by certain users or in certain situations but prevent use by the standard user.\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 6 of 7\n\n*FOLLOW UP* (added after post)\r\nAfter posting this originally, several people got involved in discussion via twitter. Before going too much further, I\r\nmust state that the best policy to use is a whitelist based policy. Blacklisting should be considered nothing more\r\nthan a stop gap and will be overcome by a dedicated attacker. This post was intended to demo that. With that being\r\nsaid, I rarely even discover companies who have made the jump to any sort of AppLocker policies.\r\nMany thanks for Lee Holmes (@Lee_Holmes) and Carlos Perez (@Carlos_Perez) for the follow up and twitter\r\ndiscussion. Lee Holmes dug in and found out why I was not able to get the PowerShell assemblies working\r\nsuccessfully in DLL blacklist mode. He used the AppLocker audit mode combined with Windows Event logs to\r\ndetect which DLLs were being loaded and blocked based on policies. This will definitely help narrow what\r\nspecifically you can block. After a bunch of playing with this method, I can vouch it is useful.\r\nTo blacklist a .NET assembly, specifically the PowerShell ones, you must block ALL of the related DLLs\r\nbehind the assemblies. This includes the DLLs in GAC_MSIL and NativeImages if they both are present. To\r\ndiscover the DLL for the PowerShell assembly, you can run this in PowerShell: [PSObject].Assembly.Location.\r\nThere are also several different PowerShell dependencies in the .NET assemblies so feel free to check it out\r\nyourself. Using this method, I was able to block the assembly DLL required for the .NET import.\r\nThats All Folks…\r\nThere is some obvious follow on work for this project that I hope to explore:\r\nExecute/Use the PowerShell API through unmanaged code. There might be a way to access the CLI\r\nthrough a COM object allowing you to integrate PowerShell into your existing RATs and Tools without\r\nutilizing the PS executables\r\nExplore and test different AV/HIPS products with .NET assemblies\r\nHopefully this stirs some discussion and encourages both the defensive and offensive PowerShell communities to\r\ndig deeper. Do not think that blocklisting or setting permissions on a single executable will prevent the use of the\r\nPowerShell language. There needs to be an effective and native capability to deny  or limit the use of PowerShell\r\nby an adversary. As this is proof of concept type of work, please let me know if you have better defensive methods\r\nor have seen specific software that works to defend PowerShell really well.\r\nSource: https://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nhttps://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367\r\nPage 7 of 7",
	"extraction_quality": 1,
	"language": "EN",
	"sources": [
		"MITRE"
	],
	"origins": [
		"web"
	],
	"references": [
		"https://web.archive.org/web/20160327101330/http://www.sixdub.net/?p=367"
	],
	"report_names": [
		"?p=367"
	],
	"threat_actors": [],
	"ts_created_at": 1775434781,
	"ts_updated_at": 1775826735,
	"ts_creation_date": 0,
	"ts_modification_date": 0,
	"files": {
		"pdf": "https://archive.orkl.eu/691983778ba51eb4067d35d2c9cad7a4c583dc0f.pdf",
		"text": "https://archive.orkl.eu/691983778ba51eb4067d35d2c9cad7a4c583dc0f.txt",
		"img": "https://archive.orkl.eu/691983778ba51eb4067d35d2c9cad7a4c583dc0f.jpg"
	}
}