Now on AskDS!

It is my sincere honor to inform you that you may now also find me waxing poetic on the AskDS blog, Microsoft's official enterprise support blog for AD DS and more. Special thanks to the superstars (*cough*Ned*cough*) that came before me and inspired me to get to where I've always wanted to be.

Check me out!

AD Is Full of Bitmasks, Decipher Them with Powershell

Active Directory uses bit masks, or bit fields, or bit flags or bit maps or whatever you want to call them.  Anyway, AD uses them, a lot.  Let's say you're digging deep into Active Directory internals, and you want to see all the attributes in your schema that are eligible for being made confidential.  We know that something called "base schema attributes" cannot be made confidential, and that we know whether an attribute is a base schema attribute or not based on a certain bit that is set in that attribute's systemFlags attribute.

Get-ADObject -LDAPFilter "(objectClass=attributeSchema)" `
             -SearchBase (Get-ADRootDSE).schemaNamingContext `
             -Properties SystemFlags

That'll give us all attributes (regardless to what type of object they apply) in the schema, including their systemFlags property.  Problem is, the systemFlags property is all condensed into an integer, and unless you're Rain Man and have no problems doing it all in your head, you might like it if that systemFlags property were translated into something more meaningful.

This is where the magic of enumerations comes in.

Add-Type -TypeDefinition @'

    public enum SystemFlagsAttr : uint
        FLAG_ATTR_NOT_REPLICATED         = 0x00000001,
        FLAG_ATTR_REQ_PARTIAL_SET_MEMBER = 0x00000002,
        FLAG_ATTR_IS_CONSTRUCTED         = 0x00000004,
        FLAG_ATTR_IS_OPERATIONAL         = 0x00000008,
        FLAG_SCHEMA_BASE_OBJECT          = 0x00000010,
        FLAG_ATTR_IS_RDN                 = 0x00000020,
        FLAG_DISALLOW_MOVE_ON_DELETE     = 0x02000000,
        FLAG_DOMAIN_DISALLOW_MOVE        = 0x04000000,
        FLAG_DOMAIN_DISALLOW_RENAME      = 0x08000000,
        FLAG_CONFIG_ALLOW_LIMITED_MOVE   = 0x10000000,
        FLAG_CONFIG_ALLOW_MOVE           = 0x20000000,
        FLAG_CONFIG_ALLOW_RENAME         = 0x40000000,
        FLAG_DISALLOW_DELETE             = 0x80000000

So a smart reader already knows that since we are looking for "base schema objects," which in the enum above equates to 0x10 hex, which is 16 decimal which is the fourth bit... then it becomes pretty easy to spot all the attributes that have a SystemFlags of 16 in our above Powershell command. But what about when bit 4 and bit 2 and bit 26 are all turned on?  This is why enums are our friends.  Let's retry our Powershell command using the enum now:

Get-ADObject -LDAPFilter "(objectClass=attributeSchema)" `
             -SearchBase (Get-ADRootDSE).schemaNamingContext `
             -Properties SystemFlags | `
             Select Name, `
             @{n='SystemFlags'; e={[Enum]::Parse('SystemFlagsAttr', $_.SystemFlags)}}

Now it's a lot more readable:

ms-DS-Assigned-AuthN-Policy      FLAG_SCHEMA_BASE_OBJECT

Pretty easy to filter those results and see which attributes are base schema attributes, and which are not.

Lastly, as an exercise I will leave to the reader, you can also use the SearchFlags (not SystemFlags) property of an attribute to determine whether the attribute is already set as confidential or not.

    public enum SearchFlags
        fATTINDEX              = 0x0001,
        fPDNTATTINDEX          = 0x0002,
        fANR                   = 0x0004,
        fPRESERVEONDELETE      = 0x0008,
        fCOPY                  = 0x0010,
        fTUPLEINDEX            = 0x0020,
        fSUBTREEATTINDEX       = 0x0040,
        fCONFIDENTIAL          = 0x0080,
        fNEVERVALUEAUDIT       = 0x0100,
        fRODCFilteredAttribute = 0x0200,
        fEXTENDEDLINKTRACKING  = 0x0400,
        fBASEONLY              = 0x0800,
        fPARTITIONSECRET       = 0x1000


NTDS.dit (Microsoft Active Directory) forensics module for Powershell.

Find it on Github here.

Current bug: Unencrypted NT hashes are incorrect!

This Powershell module is intended to aid in the process of examining and extracting information from the Active Directory database known as NTDS.dit.

Special thanks to Csaba Barta (, without whom this module would not be possible.

Also thanks to @moyix,,

Also thanks to Brendan Dolan-Gavitt, author of creddump

Q: So why did I reinvent the wheel?

A: Because:

  1. Python shouldn't have all the fun. I wanted to port the ideas into idiomatic Powershell.
  2. I wanted to gain in-depth knowledge of the subject for myself, not just run someone else's scripts.
  3. I have further plans with this data and it will be very handy to have it in Powershell format.

Currently exported Cmdlets:


A couple of screenshots:

alt tag

alt tag

alt tag


I wrote something this weekend.

TinyWebRedirector v1.0 - Redirects HTTP Requests
Copyright (C) 2015 Joseph Ryan Ries

Install:   TinyWebRedirector -install
Uninstall: TinyWebRedirector -uninstall

I wrote this micro web server for all the sysadmins out there who have an internal Active Directory that shares the same DNS name as their public domain name. Let's say your internal AD domain name is Your public website is also In this scenario, internal employees at the office cannot reach your public website by entering into their web browsers, because internally resolves to the IP address of one of your AD domain controllers. This has lead to messy solutions, such as installing IIS on each domain controller, for the sole purpose of redirecting requests on port 80 to But installing IIS on your domain controllers is not a great idea.

TinyWebRedirector is more suited to this purpose because:

  • It is tiny. The image file is 110KB, and runs with a ~2.6MB working set. It requires no redistributable DLLs.
  • It does one thing and one thing only. This translates to a much smaller potential attack surface than a large web server such as IIS.
  • It is written in C, and so does not require .NET. Will run on any Windows machine Vista/2008 or greater.
  • The listening port (default 80) and the URL to redirect visitors to is configurable in the registry at HKLM\SYSTEM\CurrentControlSet\Services\TinyWebRedirector. Restart the service for changes to take effect.
  • The service runs as Local Service. This is a much safer configuration than services that run as Local System.

Please let me know if you find any bugs or weaknesses.

Github repository is here.

The compiled and signed x64 binary is here:

TinyWebRedirector.exe (112.8KB)

Bulk Modification of Active Directory ACLs with Powershell

The other day, I encountered an Active Directory-related problem.  The security model on the organizational units in this particular domain was quite complicated, arising from the multi-tenant nature of this domain and its "List Object Mode" configuration. (I've talked about List Object Mode before.)

First, a little background.  Imagine you're looking at the OUs in Active Directory Users & Computers:

   + Builtin
   + Computers
   - Customers_OU
        + Customer1_OU
        + Customer2_OU
        + Customer3_OU
        + Customer4_OU
        + ...

To cut to the chase, there was a problem with the ACL on each individual OU beneath Customers_OU (and there were hundreds!) where an access control entry (ACE) had been applied directly to each OU that allowed "Authenticated Users" the generic read permission.  This was essentially undermining the inheritance of permissions from parent object to child object, and allowing an account in Customer1_OU to view the contents of Customer2_OU, and vice versa.

*The siren noise from Kill Bill plays here.*

I'm glossing over some of the details, but basically what needed to happen, was for me to enumerate over each and every one of those hundreds of individual customer OUs, and remove those <not inherited> ACEs.

There was no way I was going to do that by hand, through the GUI.

So I scripted it.

Import-Module ActiveDirectory
Set-Location AD:\
$AllOUs = Get-ADOrganizationalUnit -Filter * `
             -SearchBase 'OU=CUSTOMERS_OU,DC=CONTOSO,DC=COM' `
             -Properties * -SearchScope OneLevel

Foreach ($OU In $AllOUs)
    $ACL = Get-ACL $OU.DistinguishedName
    Foreach ($ACE In $ACL.Access)
        If (($ACE.IdentityReference -EQ 'NT AUTHORITY\Authenticated Users') -AND `
            ($ACE.IsInherited -EQ $False))
            Set-ACL -AclObject $ACL $OU.DistinguishedName -Verbose

That would have taken hours if done manually.  Hours that I'd rather spend playing GTA V.