AD .NET - User's Can't Change Password Attribute (Get/Set)

The following is an example on how to read a user's Can't Change Password attribute in Active Directory using C#.

public bool GetCantChangePassword(string userid)
{
 bool cantChange = false;
 try
 {
  DirectoryEntry entry = new DirectoryEntry(string.Format("LDAP://{0},{1}", "OU=Standard Users,OU=Domain", "DC=domain,DC=org"));
  entry.AuthenticationType = AuthenticationTypes.Secure | AuthenticationTypes.ServerBind;
  DirectorySearcher search = new DirectorySearcher(entry);
  search.Filter = string.Format("(&(objectClass=user)(objectCategory=person)(sAMAccountName={0}))", userid);
  search.SearchScope = SearchScope.Subtree;
  SearchResult results = search.FindOne();
  if (results != null)
  {
   try
   {
    DirectoryEntry user = results.GetDirectoryEntry();
    ActiveDirectorySecurity userSecurity = user.ObjectSecurity;
    SecurityDescriptor sd = (SecurityDescriptor)user.Properties["ntSecurityDescriptor"].Value;
    AccessControlList oACL = (AccessControlList)sd.DiscretionaryAcl;

    bool everyoneCantChange = false;
    bool selfCantChange = false;

    foreach (ActiveDs.AccessControlEntry ace in oACL)
    {
     try
     {
      if (ace.ObjectType.ToUpper().Equals("{AB721A53-1E2F-11D0-9819-00AA0040529B}".ToUpper()))
      {
       if (ace.Trustee.Equals("Everyone") && (ace.AceType == (int)ADS_ACETYPE_ENUM.ADS_ACETYPE_ACCESS_DENIED_OBJECT))
       {
        everyoneCantChange = true;
       }
       if (ace.Trustee.Equals(@"NT AUTHORITY\SELF") && (ace.AceType == (int)ADS_ACETYPE_ENUM.ADS_ACETYPE_ACCESS_DENIED_OBJECT))
       {
        selfCantChange = true;
       }
      }
     }
     catch (NullReferenceException ex)
     {
      //Logger.append(ex.Message);
     }
     catch (Exception ex)
     {
      Logger.append(ex);
     }
    }


    if (everyoneCantChange || selfCantChange)
    {
     cantChange = true;
    }
    else
    {
     cantChange = false;
    }
    
    user.Close();
   }
   catch (Exception ex)
   {
    // Log your errors!
   }
  }
  entry.Close();
 }
 catch (Exception ex)
 {
  // Log your errors!
 }
 return cantChange;
}

The following is an example on toggling a user's Can't Change Password attribute in Active Directory using C#.

public void SetCantChangePassword(string userid, bool cantChangePassword)
{
 try
 {
  DirectoryEntry entry = new DirectoryEntry(string.Format("LDAP://{0},{1}", "OU=Standard Users,OU=Domain", "DC=domain,DC=org"));
  entry.AuthenticationType = AuthenticationTypes.Secure | AuthenticationTypes.ServerBind;
  DirectorySearcher search = new DirectorySearcher(entry);
  search.Filter = string.Format("(&(objectClass=user)(objectCategory=person)(sAMAccountName={0}))", userid);
  search.SearchScope = SearchScope.Subtree;
  SearchResult results = search.FindOne();
  if (results != null)
  {
   try
   {
    DirectoryEntry user = results.GetDirectoryEntry();
    ActiveDirectorySecurity userSecurity = user.ObjectSecurity;
    SecurityIdentifier everyoneSid = new SecurityIdentifier(WellKnownSidType.WorldSid, null);
    SecurityIdentifier selfSid = new SecurityIdentifier(WellKnownSidType.SelfSid, null);
    Guid changePasswordGuid = new Guid("{AB721A53-1E2F-11D0-9819-00AA0040529B}");
    ActiveDirectoryAccessRule allowEveryone = new ActiveDirectoryAccessRule(everyoneSid, ActiveDirectoryRights.ExtendedRight, AccessControlType.Allow,  changePasswordGuid);
    ActiveDirectoryAccessRule allowSelf = new ActiveDirectoryAccessRule(selfSid, ActiveDirectoryRights.ExtendedRight, AccessControlType.Allow, changePasswordGuid);
    ActiveDirectoryAccessRule denyEveryone = new ActiveDirectoryAccessRule(everyoneSid, ActiveDirectoryRights.ExtendedRight, AccessControlType.Deny, changePasswordGuid);
    ActiveDirectoryAccessRule denySelf = new ActiveDirectoryAccessRule(selfSid, ActiveDirectoryRights.ExtendedRight, AccessControlType.Deny, changePasswordGuid);
    if (!cantChangePassword)
    {
     // Remove any existing rule that denies "everyone" the change password right.
     userSecurity.RemoveAccessRuleSpecific(denyEveryone);
     // Add a new access rule to allow "everyone" the change password right.
     userSecurity.AddAccessRule(allowEveryone);
     // Remove any existing rule that denies "self" the change password right.
     userSecurity.RemoveAccessRuleSpecific(denySelf);
     // Add a new access rule to allows "self" the change password right.
     userSecurity.AddAccessRule(allowSelf);
    }
    else
    {
     // Remove any existing rule that gives "everyone" the change password right.
     userSecurity.RemoveAccessRuleSpecific(allowEveryone);
     // Add a new access rule to deny "everyone" the change password right.
     userSecurity.AddAccessRule(denyEveryone);
     // Remove any existing rule that gives "self" the change password right.
     userSecurity.RemoveAccessRuleSpecific(allowSelf);
     // Add a new access rule to deny "self" the change password right.
     userSecurity.AddAccessRule(denySelf);
    }
    user.CommitChanges();
    user.Close();
   }
   catch (Exception ex)
   {
    // Log your errors!
   }
  }
  entry.Close();
 }
 catch (Exception ex)
 {
  // Log your errors!
 }
}
Mastodon: @[email protected]