Jump to content

Recommended Posts

Posted

Hi,

My goal is as follows...  Grant "full control" permissions to a computer object in A.D. over a different computer object in A.D.  Both objects are in the same A.D. and the same O.U.

This code works to grant "full control" permissions to a user object in A.D. over a computer object.  However when the "trustee" is changed to a computer object it throws a com error of:

Description: "Exception Occurred"

Error Number: 80020009

I've been working on this for a few days and getting closer but not quite there yet.  Does anyone know what I'm missing to allow this code to work with a computer object instead of a user?  

Alternatively, does anyone know of a different approach to grant a computer object full permissions over another computer object in A.D.?

Thanks in advance for any help offered!

;Script to set A.D. permissions on an object
;Working when setting User permissions on a computer object
;Not working when setting Computer permissions on a computer object

Const $USER_ACCOUNT_RESTRICTIONS =     "{4C164200-20C0-11D0-A768-00AA006E0529}"
Const $DNS_Host_Name_Attributes =     "{72e39547-7b18-11d1-adef-00c04fd8d5cd}"
Const $VALIDATED_SPN = "{F3A64788-5306-11D1-A9C5-0000F80367C1}"
Const $VALIDATED_DNS_HOST_NAME = "{72E39547-7B18-11D1-ADEF-00C04FD8D5CD}"
Const $RESET_PASSWORD_GUID = "{00299570-246D-11D0-A768-00AA006E0529}"


Const $ADS_RIGHT_DS_CONTROL_ACCESS = 0x100
Const $ADS_RIGHT_DS_WRITE_PROP = 0x20
Const $ADS_RIGHT_DS_READ_PROP = 0x10
Const $ADS_RIGHT_DS_SELF = 0x8
Const $ADS_ACETYPE_ACCESS_ALLOWED = 0x0
Const $ADS_ACETYPE_ACCESS_DENIED = 0x1
Const $ADS_ACETYPE_ACCESS_ALLOWED_OBJECT = 0x5
Const $ADS_ACETYPE_ACCESS_DENIED_OBJECT = 0x6
Const $ADS_ACEFLAG_INHERITED_ACE = 0x10
Const $ADS_ACEFLAG_OBJECT_TYPE_PRESENT = 0x1

Dim $objSecDescriptor, $objDACL, $objComputer
Dim $strComputerDN, $strTrustee
Dim $objACE1, $objACE2, $objACE3, $objACE4

$oMyError = ObjEvent("AutoIt.Error", "MyErrFunc") ; Install a custom error handler

$strInstallerUserName = "<user name>"
$strInstallerUserPassword = "<user password>"
$strCredDomain = "<user domain>"
;~  Specify the trustee - group NT name in form "MyDomain\GroupNTName".
$strTrustee = "<domain name>\<name of object which will have full control>" ;if name of objec is a User it works.  If it is a computer it fails


;~  Bind to the computer object with the LDAP provider.
$dsoLDAP = ObjGet("LDAP:")


$objComputer = $dsoLDAP.OpenDSObject("LDAP://<distinguished name of compter>" , $strCredDomain & "\" & $strInstallerUserName, $strInstallerUserPassword, 1)
;If the above, serverless binding attempt doesnt work you can try the below
;~ $objComputer = $dsoLDAP.OpenDSObject("LDAP://<fqdn of domain controller>/<distinguished name of computer>" , $strCredDomain & "\" & $strInstallerUserName, $strInstallerUserPassword, 1)
;~ The above binding direct targets a domain controller which prevents the need to do a lookup which if it fails will produce a "Specified domain either does not exist or could not be contacted" error
;~ Serverless binding refers to a process in which a client attempts to bind to an Active Directory object without explicitly specifying an Active Directory server in the binding string. This is possible because the LDAP provider relies on the locator services of Windows to find the best domain controller (DC) for the client. However, the client must have an account on the Active Directory domain controller to take advantage of the serverless binding feature, and the DC used by a serverless bind will always be located in the default domain; that is, the domain associated with the current security context of the thread that performs the binding.



;~  Bind to the computer security objects.
$objSecDescriptor = $objComputer.Get("ntSecurityDescriptor")

; Create the discretionaryACL object
$objDACL = $objSecDescriptor.discretionaryAcl


;~  Create Access control Entry 1... ACE 1 
$objACE1 = objCreate("AccessControlEntry")
$objACE1.Trustee = $strTrustee

;Assign read and write rights to ACE1
$objACE1.AccessMask = $ADS_RIGHT_DS_WRITE_PROP And $ADS_RIGHT_DS_READ_PROP

;Add additional properties to the ACE
$objACE1.AceType = $ADS_ACETYPE_ACCESS_ALLOWED_OBJECT
$objACE1.AceFlags = 0

;Add the ACE properties into the discretionary ACL object
$objDACL.AddAce ($objACE1)


;~  Reorder ACEs in DACL.
$objSecDescriptor.discretionaryACL = _AD_ReorderACE($objDACL)
      
;~  Update the Computer object.
$objComputer.SetOption (3,4)

;Update the A.D. cache with the new discretionary ACL
$objComputer.Put ("ntSecurityDescriptor", $objSecDescriptor)

;Update A.D. with new discretionary ACL
$objComputer.SetInfo


MsgBox(0,"", "Done")





Func _AD_ReorderACE($objDACL)
;~     Reorder ACEs in DACL.

    Dim $objNewDACL, $objInheritedDACL, $objAllowDACL, $objDenyDACL
    Dim $objAllowObjectDACL, $objDenyObjectDACL, $objACE

    $objNewDACL = objcreate("AccessControlList")
    $objInheritedDACL = objcreate("AccessControlList")
    $objAllowDACL = objcreate("AccessControlList")
    $objDenyDACL = objcreate("AccessControlList")
    $objAllowobjectDACL = objcreate("AccessControlList")
    $objDenyObjectDACL = objcreate("AccessControlList")

    For  $objACE In $objDACL
        If (($objACE.AceFlags And $ADS_ACEFLAG_INHERITED_ACE) = $ADS_ACEFLAG_INHERITED_ACE) Then
            $objInheritedDACL.AddAce ($objACE)
        Else
            Select 
                Case $objACE.AceType = $ADS_ACETYPE_ACCESS_ALLOWED
                    $objAllowDACL.AddAce ( $objACE)
                Case $objACE.AceType = $ADS_ACETYPE_ACCESS_DENIED
                    $objDenyDACL.AddAce ( $objACE)
                Case $objACE.AceType = $ADS_ACETYPE_ACCESS_ALLOWED_OBJECT
                    $objAllowObjectDACL.AddAce ( $objACE)
                Case $objACE.AceType = $ADS_ACETYPE_ACCESS_DENIED_OBJECT
                    $objDenyObjectDACL.AddAce ( $objACE)
            EndSelect
        EndIf
    Next
        
    For  $objACE In $objDenyDACL
        $objNewDACL.AddAce ( $objACE)
    Next
      
    For  $objACE In $objDenyObjectDACL
        $objNewDACL.AddAce ( $objACE)
    Next
        
    For  $objACE In $objAllowDACL
        $objNewDACL.AddAce ( $objACE)
    Next
        
    For  $objACE In $objAllowObjectDACL
        $objNewDACL.AddAce ( $objACE)
    Next
        
    For  $objACE In $objInheritedDACL
        $objNewDACL.AddAce ( $objACE)
    Next
        
    $objNewDACL.ACLRevision = $objDACL.ACLRevision
    Return $objNewDACL

EndFunc




Func MyErrFunc()
$g_eventerror = 1 ; something to check for when this function returns
  Msgbox(0,"AutoItCOM Test","We intercepted a COM Error !"      & @CRLF  & @CRLF & _
             "err.description is: "    & @TAB & $oMyError.description    & @CRLF & _
             "err.windescription:"     & @TAB & $oMyError.windescription & @CRLF & _
             "err.number is: "         & @TAB & hex($oMyError.number,8)  & @CRLF & _
             "err.lastdllerror is: "   & @TAB & $oMyError.lastdllerror   & @CRLF & _
             "err.scriptline is: "     & @TAB & $oMyError.scriptline     & @CRLF & _
             "err.source is: "         & @TAB & $oMyError.source         & @CRLF & _
             "err.helpfile is: "       & @TAB & $oMyError.helpfile       & @CRLF & _
             "err.helpcontext is: "    & @TAB & $oMyError.helpcontext _
            )
    Local $err = $oMyError.number
    If $err = 0 Then $err = -1

    $g_eventerror = $err  ; to check for after this function returns
Endfunc

 

Posted

What is your expected end result? What exactly is this supposed to be able to do in your plan? Computers aren't people, they don't get to control other computers or users, users control computers.

If I posted any code, assume that code was written using the latest release version unless stated otherwise. Also, if it doesn't work on XP I can't help with that because I don't have access to XP, and I'm not going to.
Give a programmer the correct code and he can do his work for a day. Teach a programmer to debug and he can do his work for a lifetime - by Chirag Gude
How to ask questions the smart way!

I hereby grant any person the right to use any code I post, that I am the original author of, on the autoitscript.com forums, unless I've specifically stated otherwise in the code or the thread post. If you do use my code all I ask, as a courtesy, is to make note of where you got it from.

Back up and restore Windows user files _Array.au3 - Modified array functions that include support for 2D arrays.  -  ColorChooser - An add-on for SciTE that pops up a color dialog so you can select and paste a color code into a script.  -  Customizable Splashscreen GUI w/Progress Bar - Create a custom "splash screen" GUI with a progress bar and custom label.  -  _FileGetProperty - Retrieve the properties of a file  -  SciTE Toolbar - A toolbar demo for use with the SciTE editor  -  GUIRegisterMsg demo - Demo script to show how to use the Windows messages to interact with controls and your GUI.  -   Latin Square password generator

Posted

There is an AD UDF available to do what you want.

My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download
Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki
Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki

Standard UDFs:
Excel - Example Scripts - Wiki
Word - Wiki

Tutorials:
ADO - Wiki
WebDriver - Wiki

 

Posted (edited)

@BrewManNH - expected outcome is a computer object has full control over another compute object in A.D.  This is a requirement for Windows SQL clustering.

@water - I reviewed the AD UDF (HERE) and don't see this functionality.  Can you pinpoint what specific function in that UDF could be used to grant full control to a computer object over another computer object?

Thanks

Edited by mojomatt
Posted

Can you show me the documentation you're following that states that? I've not done any clustering and can't find any references that mention computer objects needing to have full control over another computer object, so I'd like to read up on it.

On the other hand, what permissions does the user that  is running the script have?

If I posted any code, assume that code was written using the latest release version unless stated otherwise. Also, if it doesn't work on XP I can't help with that because I don't have access to XP, and I'm not going to.
Give a programmer the correct code and he can do his work for a day. Teach a programmer to debug and he can do his work for a lifetime - by Chirag Gude
How to ask questions the smart way!

I hereby grant any person the right to use any code I post, that I am the original author of, on the autoitscript.com forums, unless I've specifically stated otherwise in the code or the thread post. If you do use my code all I ask, as a courtesy, is to make note of where you got it from.

Back up and restore Windows user files _Array.au3 - Modified array functions that include support for 2D arrays.  -  ColorChooser - An add-on for SciTE that pops up a color dialog so you can select and paste a color code into a script.  -  Customizable Splashscreen GUI w/Progress Bar - Create a custom "splash screen" GUI with a progress bar and custom label.  -  _FileGetProperty - Retrieve the properties of a file  -  SciTE Toolbar - A toolbar demo for use with the SciTE editor  -  GUIRegisterMsg demo - Demo script to show how to use the Windows messages to interact with controls and your GUI.  -   Latin Square password generator

Posted

You are correct. There is no function to directly change the ACL of a computer.
Function _AD_CreateComputer grants permission to a user only.

How do you specify the computer account you want to grant the permissions? You know that a SamAccountName needs a trailing "$"?

My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download
Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki
Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki

Standard UDFs:
Excel - Example Scripts - Wiki
Word - Wiki

Tutorials:
ADO - Wiki
WebDriver - Wiki

 

Posted

@water - Your suggestion to add a "$" after the computer name was what was missing.  Apparently the script couldn't find the computer object without it.  Thanks so much for the help.  The script is now working as expected.

 

@BrewManNH - Windows SQL clustering is pretty complex and can be setup in various ways.  Detailing our specific setup is beyond the scope of this topic so I'll leave that for another day.  However, thanks for your willingness to help. :)

Posted

Glad you like the solution :)

My UDFs and Tutorials:

Spoiler

UDFs:
Active Directory (NEW 2024-07-28 - Version 1.6.3.0) - Download - General Help & Support - Example Scripts - Wiki
ExcelChart (2017-07-21 - Version 0.4.0.1) - Download - General Help & Support - Example Scripts
OutlookEX (2021-11-16 - Version 1.7.0.0) - Download - General Help & Support - Example Scripts - Wiki
OutlookEX_GUI (2021-04-13 - Version 1.4.0.0) - Download
Outlook Tools (2019-07-22 - Version 0.6.0.0) - Download - General Help & Support - Wiki
PowerPoint (2021-08-31 - Version 1.5.0.0) - Download - General Help & Support - Example Scripts - Wiki
Task Scheduler (2022-07-28 - Version 1.6.0.1) - Download - General Help & Support - Wiki

Standard UDFs:
Excel - Example Scripts - Wiki
Word - Wiki

Tutorials:
ADO - Wiki
WebDriver - Wiki

 

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...