Пример кода для задания ACE в объекте каталога
Определение функции SetRight
В следующем примере кода определяется функция, которая добавляет контроль доступа запись (ACE) в список дискреционных контроль доступа (DACL) дескриптора безопасности указанного объекта в службах домен Active Directory Services. Подпрограмма позволяет выполнять следующие действия:
- Предоставление или запрет доступа ко всему объекту.
- Предоставление или запрет доступа к определенному свойству объекта.
- Предоставление или запрет доступа к набору свойств объекта.
- Предоставьте или запретите право на создание определенного типа дочернего объекта.
- Задайте ACE, который может наследоваться всеми дочерними объектами или дочерними объектами указанного класса объектов.
После этого примера кода Visual Basic приведены несколько примеров кода, в которых показано, как использовать функцию SetRight для задания различных типов acEs.
Const ACL_REVISION_DS = &H4
Public Function SetRight(objectDN As String, _
accessrights As Long, _
accesstype As Long, _
aceinheritflags As Long, _
objectGUID As String, _
inheritedObjectGUID As String, _
trustee As String) As Boolean
Dim dsobject As IADs
Dim sd As IADsSecurityDescriptor
Dim dacl As IADsAccessControlList
Dim newace As New AccessControlEntry
Dim lflags As Long
On Error GoTo Cleanup
' Bind to the specified object.
Set dsobject = GetObject(objectDN)
' Read the security descriptor on the object.
Set sd = dsobject.Get("ntSecurityDescriptor")
' Get the DACL from the security descriptor.
Set dacl = sd.DiscretionaryAcl
' Set the properties of the new ACE.
newace.AccessMask = accessrights
newace.AceType = accesstype
newace.AceFlags = aceinheritflags
newace.trustee = trustee
' Set the GUID for the object type or inherited object type.
lflags = 0
If Not objectGUID = vbNullString Then
newace.ObjectType = objectGUID
lflags = lflags Or &H1 'ADS_FLAG_OBJECT_TYPE_PRESENT
End If
If Not inheritedObjectGUID = vbNullString Then
newace.InheritedObjectType = inheritedObjectGUID
lflags = lflags Or &H2 'ADS_FLAG_INHERITED_OBJECT_TYPE_PRESENT
End If
If Not (lflags = 0) Then newace.Flags = lflags
' Set the ACL Revision.
dacl.AclRevision = ACL_REVISION_DS
' Add the ACE to the DACL and to the security descriptor.
dacl.AddAce newace
sd.DiscretionaryAcl = dacl
' Apply it to the object.
dsobject.Put "ntSecurityDescriptor", sd
dsobject.SetInfo
SetRight = True
Exit Function
Cleanup:
Set dsobject = Nothing
Set sd = Nothing
Set dacl = Nothing
Set newace = Nothing
SetRight = False
End Function
HRESULT SetRight(
IADs *pObject,
long lAccessMask,
long lAccessType,
long lAccessInheritFlags,
LPOLESTR szObjectGUID,
LPOLESTR szInheritedObjectGUID,
LPOLESTR szTrustee)
{
VARIANT varSD;
HRESULT hr = E_FAIL;
IADsAccessControlList *pACL = NULL;
IADsSecurityDescriptor *pSD = NULL;
IDispatch *pDispDACL = NULL;
IADsAccessControlEntry *pACE = NULL;
IDispatch *pDispACE = NULL;
long lFlags = 0L;
// The following code example takes the szTrustee in an expected naming format
// and assumes it is the name for the correct trustee.
// The application should validate the specified trustee.
if (!szTrustee || !pObject)
return E_INVALIDARG;
VariantInit(&varSD);
// Get the nTSecurityDescriptor.
// Type should be VT_DISPATCH - an IDispatch pointer to the security descriptor object.
hr = pObject->Get(_bstr_t("nTSecurityDescriptor"), &varSD);
if ( FAILED(hr) || varSD.vt != VT_DISPATCH ) {
wprintf(L"get nTSecurityDescriptor failed: 0x%x\n", hr);
return hr;
}
hr = V_DISPATCH( &varSD )->QueryInterface(IID_IADsSecurityDescriptor,(void**)&pSD);
if ( FAILED(hr) ) {
wprintf(L"QueryInterface for IADsSecurityDescriptor failed: 0x%x\n", hr);
goto cleanup;
}
// Get the DACL.
hr = pSD->get_DiscretionaryAcl(&pDispDACL);
if (SUCCEEDED(hr))
hr = pDispDACL->QueryInterface(IID_IADsAccessControlList,(void**)&pACL);
if ( FAILED(hr) ) {
wprintf(L"Could not get DACL: 0x%x\n", hr);
goto cleanup;
}
// Create the COM object for the new ACE.
hr = CoCreateInstance(
CLSID_AccessControlEntry,
NULL,
CLSCTX_INPROC_SERVER,
IID_IADsAccessControlEntry,
(void **)&pACE
);
if ( FAILED(hr) ) {
wprintf(L"Could not create ACE object: 0x%x\n", hr);
goto cleanup;
}
// Set the properties for the new ACE.
// Set the mask that specifies the access right.
hr = pACE->put_AccessMask( lAccessMask );
// Set the trustee.
hr = pACE->put_Trustee( szTrustee );
// Set AceType.
hr = pACE->put_AceType( lAccessType );
// Set AceFlags to specify whether other objects can inherit the ACE from the specified object.
hr = pACE->put_AceFlags( lAccessInheritFlags );
// If an szObjectGUID is specified, add ADS_FLAG_OBJECT_TYPE_PRESENT
// to the lFlags mask and set the ObjectType.
if (szObjectGUID)
{
lFlags |= ADS_FLAG_OBJECT_TYPE_PRESENT;
hr = pACE->put_ObjectType( szObjectGUID );
}
// If an szInheritedObjectGUID is specified, add ADS_FLAG_INHERITED_OBJECT_TYPE_PRESENT
// to the lFlags mask and set the InheritedObjectType.
if (szInheritedObjectGUID)
{
lFlags |= ADS_FLAG_INHERITED_OBJECT_TYPE_PRESENT;
hr = pACE->put_InheritedObjectType( szInheritedObjectGUID );
}
// Set flags if ObjectType or InheritedObjectType were set.
if (lFlags)
hr = pACE->put_Flags(lFlags);
// Add the ACE to the ACL to the SD to the cache to the object.
// Call the QueryInterface method for the IDispatch pointer to pass to the AddAce method.
hr = pACE->QueryInterface(IID_IDispatch, (void**)&pDispACE);
if (SUCCEEDED(hr))
{
// Set the ACL revision.
hr = pACL->put_AclRevision(ACL_REVISION_DS);
// Add the ACE.
hr = pACL->AddAce(pDispACE);
if (SUCCEEDED(hr))
{
// Write the DACL.
hr = pSD->put_DiscretionaryAcl(pDispDACL);
if (SUCCEEDED(hr))
{
// Write the ntSecurityDescriptor property to the property cache.
hr = pObject->Put(CComBSTR("nTSecurityDescriptor"), varSD);
if (SUCCEEDED(hr))
{
// Call SetInfo to update the property on the object in the directory.
hr = pObject->SetInfo();
}
}
}
}
cleanup:
if (pDispACE)
pDispACE->Release();
if (pACE)
pACE->Release();
if (pACL)
pACL->Release();
if (pDispDACL)
pDispDACL->Release();
if (pSD)
pSD->Release();
VariantClear(&varSD);
return hr;
}
Предоставление или запрет доступа ко всему объекту
Следующий пример кода Visual Basic создает строку привязки для контейнера Users, а затем вызывает функцию SetRight для задания ACE в контейнере Users. В этом примере задается ACE, который предоставляет доверенному лицу право на чтение или запись любого свойства в объекте.
Dim rootDSE As IADs
Dim objectDN As String
Dim bResult As Boolean
Const ADS_RIGHT_READ_PROP = &H10
Const ADS_RIGHT_WRITE_PROP = &H20
' Bind to the Users container in the local domain.
Set rootDSE = GetObject("LDAP://rootDSE")
objectDN = "LDAP://cn=users," & rootDSE.Get("defaultNamingContext")
' Grant trustee the right to read/write any property.
bResult = SetRight objectDN, _
ADS_RIGHT_READ_PROP Or ADS_RIGHT_WRITE_PROP, _
ADS_ACETYPE_ACCESS_ALLOWED, _
0, _
vbNullString, _
vbNullString, _
"someone@fabrikam.com" ' Trustee
If bResult = True Then
MsgBox ("The trustee can read or write any property.")
Else
MsgBox ("An error occurred.")
End If
Следующий пример кода C++ задает ACE, который предоставляет доверенному лицу разрешение на чтение или запись любого свойства в объекте. В примере кода предполагается, что для pObject и szTrustee заданы допустимые значения. Дополнительные сведения см. в разделе "Настройка прав доступа к объекту".
HRESULT hr;
IADs *pObject;
LPWSTR szTrustee;
hr = SetRight(
pObject, // IADs pointer to the object
ADS_RIGHT_READ_PROP | ADS_RIGHT_WRITE_PROP,
ADS_ACETYPE_ACCESS_ALLOWED,
0, // Not inheritable
NULL, // No object type GUID
NULL, // No inherited object type GUID
szTrustee
);
Предоставление или запрет доступа к конкретному свойству объекта
Этот пример кода вызывает функцию SetRight , чтобы предоставить доверенному лицу право на чтение или запись определенного свойства в объекте. Помните, что необходимо указать schemaIDGUID свойства, и необходимо указать ADS_ACETYPE_ACCESS_ALLOWED_OBJECT, чтобы указать, что это определенный объект ACE. В этом примере кода также указывается флаг ADS_ACEFLAG_INHERIT_ACE , указывающий, что ACE может наследоваться дочерними объектами.
' Grant trustee the right to read the Telephone-Number property
' of all child objects in the Users container.
' {bf967a49-0de6-11d0-a285-00aa003049e2} is the schemaIDGUID of
' the Telephone-Number property.
bResult = SetRight objectDN, _
ADS_RIGHT_WRITE_PROP Or ADS_RIGHT_READ_PROP, _
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT, _
ADS_ACEFLAG_INHERIT_ACE, _
"{bf967a49-0de6-11d0-a285-00aa003049e2}", _
vbNullString, _
"someone@fabrikam.com" ' Trustee
If bResult = True Then
MsgBox ("The trustee can read the telephone number property.")
Else
MsgBox ("An error occurred.")
End If
// Grant trustee the right to read the Telephone-Number property
// of all child objects in the Users container.
// {bf967a49-0de6-11d0-a285-00aa003049e2} is the schemaIDGUID of
// the Telephone-Number property.
hr = SetRight(
pObject, // IADs pointer to the object.
ADS_RIGHT_READ_PROP | ADS_RIGHT_WRITE_PROP,
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT,
ADS_ACEFLAG_INHERIT_ACE,
L"{bf967a49-0de6-11d0-a285-00aa003049e2}",
NULL, // No inherited object type GUID.
szTrustee
);
Предоставление или запрет доступа к набору свойств объекта
Этот пример кода вызывает функцию SetRight , чтобы предоставить доверенному лицу право на чтение или запись определенного набора свойств объекта. Укажите ADS_ACETYPE_ACCESS_ALLOWED_OBJECT , чтобы указать, что это определенный объект ACE.
Набор свойств определяется объектом controlAccessRight в контейнере расширенных прав секции конфигурации. Чтобы определить набор свойств в ACE, укажите свойство rightsGUID объекта controlAccessRight. Помните, что этот идентификатор GUID набора свойств также задан в свойстве AttributeSecurityGUID каждого объекта attributeSchema , включенного в набор свойств. Дополнительные сведения см. в разделе "Управление правами доступа".
В этом примере кода также указываются флаги наследования, которые задают ACE как наследуемые дочерними объектами, но неэффективными для немедленного объекта. Кроме того, в примере указывается GUID класса User, который указывает, что ACE может наследоваться только объектами этого класса.
' Grant trustee permission to read or write a set of properties.
' {77B5B886-944A-11d1-AEBD-0000F80367C1} is a GUID that identifies
' a property set.
' {bf967aba-0de6-11d0-a285-00aa003049e2} is a GUID that identifies the
' User class, so this ACE is inherited only by objects of that class.
bResult = SetRight objectDN, _
ADS_RIGHT_READ_PROP Or ADS_RIGHT_WRITE_PROP, _
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT, _
ADS_ACEFLAG_INHERIT_ACE Or ADS_ACEFLAG_INHERIT_ONLY_ACE, _
"{77B5B886-944A-11d1-AEBD-0000F80367C1}", _
"{bf967aba-0de6-11d0-a285-00aa003049e2}", _
"someone@fabrikam.com" ' Trustee
If bResult = True Then
MsgBox ("The trustee can read or write a set of properties.")
Else
MsgBox ("An error occurred.")
End If
// Grant trustee the right to read or write a set of properties.
// {77B5B886-944A-11d1-AEBD-0000F80367C1} is a GUID that identifies
// a property set (rightsGUID of a controlAccessRight object).
// {bf967aba-0de6-11d0-a285-00aa003049e2} is the schemaIDGUID of the
// User class, so this ACE is inherited only by objects of that class.
hr = SetRight(
pObject, // IADs pointer to the object.
ADS_RIGHT_READ_PROP | ADS_RIGHT_WRITE_PROP,
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT,
ADS_ACEFLAG_INHERIT_ACE | ADS_ACEFLAG_INHERIT_ONLY_ACE,
L"{77B5B886-944A-11d1-AEBD-0000F80367C1}",
L"{bf967aba-0de6-11d0-a285-00aa003049e2}",
szTrustee
);
Предоставление или запрет разрешения на создание определенного типа дочернего объекта
В следующем примере кода вызывается функция SetRight , чтобы предоставить указанному доверенному лицу право создавать и удалять объекты User в поддереве в указанном объекте. Помните, что в примере указывается GUID класса User, что означает, что ACE позволяет создавать объекты User, а не объекты других классов. Укажите ADS_ACETYPE_ACCESS_ALLOWED_OBJECT , чтобы указать, что это определенный объект ACE.
' Grant trustee the right to create or delete User objects
' in the specified object.
' {bf967aba-0de6-11d0-a285-00aa003049e2} is a GUID that identifies the
' User class.
bResult = SetRight objectDN, _
ADS_RIGHT_DS_CREATE_CHILD Or ADS_RIGHT_DS_DELETE_CHILD, _
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT, _
0, _
"{bf967aba-0de6-11d0-a285-00aa003049e2}", _
vbNullString, _
"jeffsmith@fabrikam.com" 'trustee
If bResult = True Then
MsgBox ("The trustee can create or delete User objects.")
Else
MsgBox ("An error occurred.")
End If
// Grant trustee the right to create or delete User objects
// in the specified object.
// {bf967aba-0de6-11d0-a285-00aa003049e2} is the schemaIDGUID of the
// User class.
hr = SetRight(
pObject, // IADs pointer to the object.
ADS_RIGHT_DS_CREATE_CHILD | ADS_RIGHT_DS_DELETE_CHILD,
ADS_ACETYPE_ACCESS_ALLOWED_OBJECT,
0, // Not inheritable.
L"{bf967aba-0de6-11d0-a285-00aa003049e2}",
NULL, // No inherited object type GUID.
szTrustee
);
Дополнительные сведения и идентификатор schemaIDGUID предопределенного атрибута или класса см. на странице ссылок на атрибут или класс в справочнике по схеме Active Directory. Дополнительные сведения и пример кода, который можно использовать для получения schemaIDGUID программным способом, см. в разделе "Чтение атрибутовSchema" и classSchema Objects.