mirror of
https://github.com/samba-team/samba.git
synced 2025-08-03 04:22:09 +03:00
Version 1.0 of the directory service acls module.
At this point, support for checks on LDAP add, delete, rename and modify. Old kludge_acl is still there to handle the searches. This module is synchronous as the async version was impossible to debug, will be converted to async after some user testing.
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@ -527,10 +527,10 @@ done:
|
||||
_PUBLIC_ const struct ldb_module_ops ldb_kludge_acl_module_ops = {
|
||||
.name = "kludge_acl",
|
||||
.search = kludge_acl_search,
|
||||
.add = kludge_acl_change,
|
||||
/* .add = kludge_acl_change,
|
||||
.modify = kludge_acl_change,
|
||||
.del = kludge_acl_change,
|
||||
.rename = kludge_acl_change,
|
||||
.rename = kludge_acl_change, */
|
||||
.extended = kludge_acl_extended,
|
||||
.init_context = kludge_acl_init
|
||||
};
|
||||
|
@ -419,8 +419,8 @@ const char **dsdb_full_attribute_list(TALLOC_CTX *mem_ctx,
|
||||
|
||||
/* Return the schemaIDGUID of a class */
|
||||
|
||||
const struct GUID * class_schemaid_guid_by_lDAPDisplayName(const struct dsdb_schema *schema,
|
||||
const char *name)
|
||||
const struct GUID *class_schemaid_guid_by_lDAPDisplayName(const struct dsdb_schema *schema,
|
||||
const char *name)
|
||||
{
|
||||
const struct dsdb_class *object_class = dsdb_class_by_lDAPDisplayName(schema, name);
|
||||
if (!object_class)
|
||||
@ -428,3 +428,13 @@ const struct GUID * class_schemaid_guid_by_lDAPDisplayName(const struct dsdb_sch
|
||||
|
||||
return &object_class->schemaIDGUID;
|
||||
}
|
||||
|
||||
const struct GUID *attribute_schemaid_guid_by_lDAPDisplayName(const struct dsdb_schema *schema,
|
||||
const char *name)
|
||||
{
|
||||
const struct dsdb_attribute *attr = dsdb_attribute_by_lDAPDisplayName(schema, name);
|
||||
if (!attr)
|
||||
return NULL;
|
||||
|
||||
return &attr->schemaIDGUID;
|
||||
}
|
||||
|
@ -30,7 +30,6 @@
|
||||
*/
|
||||
#include "includes.h"
|
||||
#include "libcli/security/security.h"
|
||||
#include "lib/util/dlinklist.h"
|
||||
#include "librpc/ndr/libndr.h"
|
||||
|
||||
/* Adds a new node to the object tree. If attributeSecurityGUID is not zero and
|
||||
@ -38,69 +37,85 @@
|
||||
* In all other cases as a child of the root
|
||||
*/
|
||||
|
||||
struct object_tree * insert_in_object_tree(TALLOC_CTX *mem_ctx,
|
||||
const struct GUID *schemaGUIDID,
|
||||
const struct GUID *attributeSecurityGUID,
|
||||
uint32_t init_access,
|
||||
struct object_tree *root)
|
||||
bool insert_in_object_tree(TALLOC_CTX *mem_ctx,
|
||||
const struct GUID *guid,
|
||||
uint32_t init_access,
|
||||
struct object_tree **root,
|
||||
struct object_tree **new_node)
|
||||
{
|
||||
struct object_tree * parent = NULL;
|
||||
struct object_tree * new_node;
|
||||
|
||||
new_node = talloc(mem_ctx, struct object_tree);
|
||||
if (!new_node)
|
||||
return NULL;
|
||||
memset(new_node, 0, sizeof(struct object_tree));
|
||||
new_node->remaining_access = init_access;
|
||||
|
||||
if (!root){
|
||||
memcpy(&new_node->guid, schemaGUIDID, sizeof(struct GUID));
|
||||
return new_node;
|
||||
if (!guid || GUID_all_zero(guid)){
|
||||
return true;
|
||||
}
|
||||
|
||||
if (attributeSecurityGUID && !GUID_all_zero(attributeSecurityGUID)){
|
||||
parent = get_object_tree_by_GUID(root, attributeSecurityGUID);
|
||||
memcpy(&new_node->guid, attributeSecurityGUID, sizeof(struct GUID));
|
||||
if (!*root){
|
||||
*root = talloc_zero(mem_ctx, struct object_tree);
|
||||
if (!*root) {
|
||||
return false;
|
||||
}
|
||||
(*root)->guid = *guid;
|
||||
*new_node = *root;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
memcpy(&new_node->guid, schemaGUIDID, sizeof(struct GUID));
|
||||
|
||||
if (!parent)
|
||||
parent = root;
|
||||
|
||||
new_node->remaining_access = init_access;
|
||||
DLIST_ADD(parent, new_node);
|
||||
return new_node;
|
||||
if (!(*root)->children) {
|
||||
(*root)->children = talloc_array(mem_ctx, struct object_tree, 1);
|
||||
(*root)->children[0].guid = *guid;
|
||||
(*root)->children[0].num_of_children = 0;
|
||||
(*root)->children[0].children = NULL;
|
||||
(*root)->num_of_children++;
|
||||
(*root)->children[0].remaining_access = init_access;
|
||||
*new_node = &((*root)->children[0]);
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
int i;
|
||||
for (i = 0; i < (*root)->num_of_children; i++) {
|
||||
if (GUID_equal(&((*root)->children[i].guid), guid)) {
|
||||
*new_node = &((*root)->children[i]);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
(*root)->children = talloc_realloc(mem_ctx, (*root)->children, struct object_tree,
|
||||
(*root)->num_of_children +1);
|
||||
(*root)->children[(*root)->num_of_children].guid = *guid;
|
||||
(*root)->children[(*root)->num_of_children].remaining_access = init_access;
|
||||
*new_node = &((*root)->children[(*root)->num_of_children]);
|
||||
(*root)->num_of_children++;
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/* search by GUID */
|
||||
struct object_tree * get_object_tree_by_GUID(struct object_tree *root,
|
||||
struct object_tree *get_object_tree_by_GUID(struct object_tree *root,
|
||||
const struct GUID *guid)
|
||||
{
|
||||
struct object_tree *p;
|
||||
struct object_tree *result = NULL;
|
||||
int i;
|
||||
|
||||
if (!root || GUID_equal(&root->guid, guid))
|
||||
if (!root || GUID_equal(&root->guid, guid)) {
|
||||
result = root;
|
||||
else{
|
||||
for (p = root->children; p != NULL; p = p->next)
|
||||
if ((result = get_object_tree_by_GUID(p, guid)))
|
||||
break;
|
||||
return result;
|
||||
}
|
||||
else if (root->num_of_children > 0) {
|
||||
for (i = 0; i < root->num_of_children; i++) {
|
||||
if ((result = get_object_tree_by_GUID(&root->children[i], guid)))
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Change the granted access per each ACE */
|
||||
|
||||
void object_tree_modify_access(struct object_tree *root,
|
||||
uint32_t access_mask)
|
||||
uint32_t access)
|
||||
{
|
||||
struct object_tree *p;
|
||||
if (root){
|
||||
root->remaining_access &= ~access_mask;
|
||||
root->remaining_access &= ~access;
|
||||
if (root->num_of_children > 0) {
|
||||
int i;
|
||||
for (i = 0; i < root->num_of_children; i++) {
|
||||
object_tree_modify_access(&root->children[i], access);
|
||||
}
|
||||
}
|
||||
|
||||
for (p = root->children; p != NULL; p = p->next)
|
||||
object_tree_modify_access(p, access_mask);
|
||||
}
|
||||
|
@ -32,10 +32,8 @@ struct auth_session_info;
|
||||
struct object_tree {
|
||||
uint32_t remaining_access;
|
||||
struct GUID guid;
|
||||
/* linked list of children */
|
||||
struct object_tree * children;
|
||||
struct object_tree * prev;
|
||||
struct object_tree * next;
|
||||
int num_of_children;
|
||||
struct object_tree *children;
|
||||
};
|
||||
|
||||
/* Moved the dom_sid functions to the top level dir with manual proto header */
|
||||
|
@ -593,7 +593,6 @@ def setup_samdb_partitions(samdb_path, setup_path, message, lp, session_info,
|
||||
modules_list = ["resolve_oids",
|
||||
"rootdse",
|
||||
"lazy_commit",
|
||||
"acl",
|
||||
"paged_results",
|
||||
"ranged_results",
|
||||
"anr",
|
||||
@ -604,6 +603,7 @@ def setup_samdb_partitions(samdb_path, setup_path, message, lp, session_info,
|
||||
"rdn_name",
|
||||
"objectclass",
|
||||
"descriptor",
|
||||
"acl",
|
||||
"samldb",
|
||||
"password_hash",
|
||||
"operational",
|
||||
|
Reference in New Issue
Block a user