/* retry */
return;
}
+ if (state->received == 0) {
+ tevent_req_error(req, EPIPE);
+ return;
+ }
if (state->received == -1) {
tevent_req_error(req, errno);
return;
enum commands {
CMD_CREATE_TDB,
CMD_OPEN_TDB,
+ CMD_TRANSACTION_START,
+ CMD_TRANSACTION_COMMIT,
+ CMD_TRANSACTION_CANCEL,
CMD_ERASE,
CMD_DUMP,
CMD_INSERT,
COMMAND_TABLE cmd_table[] = {
{"create", CMD_CREATE_TDB},
{"open", CMD_OPEN_TDB},
+ {"transaction_start", CMD_TRANSACTION_START},
+ {"transaction_commit", CMD_TRANSACTION_COMMIT},
+ {"transaction_cancel", CMD_TRANSACTION_CANCEL},
{"erase", CMD_ERASE},
{"dump", CMD_DUMP},
{"insert", CMD_INSERT},
"tdbtool: \n"
" create dbname : create a database\n"
" open dbname : open an existing database\n"
+" transaction_start : start a transaction\n"
+" transaction_commit : commit a transaction\n"
+" transaction_cancel : cancel a transaction\n"
" erase : erase the database\n"
" dump : dump the database as strings\n"
" keys : dump the database keys as strings\n"
" list : print the database hash table and freelist\n"
" free : print the database freelist\n"
" check : check the integrity of an opened database\n"
+" speed : perform speed tests on the database\n"
" ! command : execute system command\n"
" 1 | first : print the first record\n"
" n | next : print the next record\n"
int cmd_len;
if (cmdname && strlen(cmdname) == 0) {
- mycmd = CMD_NEXT;
+ mycmd = CMD_NEXT;
} else {
- while (ctp->name) {
- cmd_len = strlen(ctp->name);
- if (strncmp(ctp->name,cmdname,cmd_len) == 0) {
- mycmd = ctp->cmd;
- break;
+ while (ctp->name) {
+ cmd_len = strlen(ctp->name);
+ if (strncmp(ctp->name,cmdname,cmd_len) == 0) {
+ mycmd = ctp->cmd;
+ break;
+ }
+ ctp++;
}
- ctp++;
- }
}
switch (mycmd) {
case CMD_CREATE_TDB:
- bIterate = 0;
- create_tdb(arg1);
- return 0;
- case CMD_OPEN_TDB:
- bIterate = 0;
- open_tdb(arg1);
- return 0;
- case CMD_SYSTEM:
- /* Shell command */
- if (system(arg1) == -1) {
- terror("system() call failed\n");
- }
- return 0;
- case CMD_QUIT:
- return 1;
- default:
- /* all the rest require a open database */
- if (!tdb) {
- bIterate = 0;
- terror("database not open");
- help();
- return 0;
- }
- switch (mycmd) {
- case CMD_ERASE:
- bIterate = 0;
- tdb_traverse(tdb, do_delete_fn, NULL);
- return 0;
- case CMD_DUMP:
- bIterate = 0;
- tdb_traverse(tdb, print_rec, NULL);
- return 0;
- case CMD_INSERT:
bIterate = 0;
- insert_tdb(arg1, arg1len,arg2,arg2len);
+ create_tdb(arg1);
return 0;
- case CMD_MOVE:
- bIterate = 0;
- move_rec(arg1,arg1len,arg2);
- return 0;
- case CMD_STORE:
- bIterate = 0;
- store_tdb(arg1,arg1len,arg2,arg2len);
- return 0;
- case CMD_SHOW:
- bIterate = 0;
- show_tdb(arg1, arg1len);
- return 0;
- case CMD_KEYS:
- tdb_traverse(tdb, print_key, NULL);
- return 0;
- case CMD_HEXKEYS:
- tdb_traverse(tdb, print_hexkey, NULL);
- return 0;
- case CMD_DELETE:
+ case CMD_OPEN_TDB:
bIterate = 0;
- delete_tdb(arg1,arg1len);
- return 0;
- case CMD_LIST_HASH_FREE:
- tdb_dump_all(tdb);
+ open_tdb(arg1);
return 0;
- case CMD_LIST_FREE:
- tdb_printfreelist(tdb);
- return 0;
- case CMD_INFO:
- info_tdb();
- return 0;
- case CMD_SPEED:
- speed_tdb(arg1);
- return 0;
- case CMD_MMAP:
- toggle_mmap();
- return 0;
- case CMD_FIRST:
- bIterate = 1;
- first_record(tdb, &iterate_kbuf);
- return 0;
- case CMD_NEXT:
- if (bIterate)
- next_record(tdb, &iterate_kbuf);
- return 0;
- case CMD_CHECK:
- check_db(tdb);
- return 0;
- case CMD_HELP:
- help();
+ case CMD_SYSTEM:
+ /* Shell command */
+ if (system(arg1) == -1) {
+ terror("system() call failed\n");
+ }
return 0;
- case CMD_CREATE_TDB:
- case CMD_OPEN_TDB:
- case CMD_SYSTEM:
- case CMD_QUIT:
- /*
- * unhandled commands. cases included here to avoid compiler
- * warnings.
- */
- return 0;
- }
+ case CMD_QUIT:
+ return 1;
+ default:
+ /* all the rest require a open database */
+ if (!tdb) {
+ bIterate = 0;
+ terror("database not open");
+ help();
+ return 0;
+ }
+ switch (mycmd) {
+ case CMD_TRANSACTION_START:
+ bIterate = 0;
+ tdb_transaction_start(tdb);
+ return 0;
+ case CMD_TRANSACTION_COMMIT:
+ bIterate = 0;
+ tdb_transaction_commit(tdb);
+ return 0;
+ case CMD_TRANSACTION_CANCEL:
+ bIterate = 0;
+ tdb_transaction_cancel(tdb);
+ return 0;
+ case CMD_ERASE:
+ bIterate = 0;
+ tdb_traverse(tdb, do_delete_fn, NULL);
+ return 0;
+ case CMD_DUMP:
+ bIterate = 0;
+ tdb_traverse(tdb, print_rec, NULL);
+ return 0;
+ case CMD_INSERT:
+ bIterate = 0;
+ insert_tdb(arg1, arg1len,arg2,arg2len);
+ return 0;
+ case CMD_MOVE:
+ bIterate = 0;
+ move_rec(arg1,arg1len,arg2);
+ return 0;
+ case CMD_STORE:
+ bIterate = 0;
+ store_tdb(arg1,arg1len,arg2,arg2len);
+ return 0;
+ case CMD_SHOW:
+ bIterate = 0;
+ show_tdb(arg1, arg1len);
+ return 0;
+ case CMD_KEYS:
+ tdb_traverse(tdb, print_key, NULL);
+ return 0;
+ case CMD_HEXKEYS:
+ tdb_traverse(tdb, print_hexkey, NULL);
+ return 0;
+ case CMD_DELETE:
+ bIterate = 0;
+ delete_tdb(arg1,arg1len);
+ return 0;
+ case CMD_LIST_HASH_FREE:
+ tdb_dump_all(tdb);
+ return 0;
+ case CMD_LIST_FREE:
+ tdb_printfreelist(tdb);
+ return 0;
+ case CMD_INFO:
+ info_tdb();
+ return 0;
+ case CMD_SPEED:
+ speed_tdb(arg1);
+ return 0;
+ case CMD_MMAP:
+ toggle_mmap();
+ return 0;
+ case CMD_FIRST:
+ bIterate = 1;
+ first_record(tdb, &iterate_kbuf);
+ return 0;
+ case CMD_NEXT:
+ if (bIterate)
+ next_record(tdb, &iterate_kbuf);
+ return 0;
+ case CMD_CHECK:
+ check_db(tdb);
+ return 0;
+ case CMD_HELP:
+ help();
+ return 0;
+ case CMD_CREATE_TDB:
+ case CMD_OPEN_TDB:
+ case CMD_SYSTEM:
+ case CMD_QUIT:
+ /*
+ * unhandled commands. cases included here to avoid compiler
+ * warnings.
+ */
+ return 0;
+ }
}
return 0;
static char *convert_string(char *instring, size_t *sizep)
{
- size_t length = 0;
- char *outp, *inp;
- char temp[3];
-
-
- outp = inp = instring;
-
- while (*inp) {
- if (*inp == '\\') {
- inp++;
- if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
- temp[0] = *inp++;
- temp[1] = '\0';
- if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
- temp[1] = *inp++;
- temp[2] = '\0';
+ size_t length = 0;
+ char *outp, *inp;
+ char temp[3];
+
+ outp = inp = instring;
+
+ while (*inp) {
+ if (*inp == '\\') {
+ inp++;
+ if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
+ temp[0] = *inp++;
+ temp[1] = '\0';
+ if (*inp && strchr("0123456789abcdefABCDEF",(int)*inp)) {
+ temp[1] = *inp++;
+ temp[2] = '\0';
+ }
+ *outp++ = (char)strtol((const char *)temp,NULL,16);
+ } else {
+ *outp++ = *inp++;
+ }
+ } else {
+ *outp++ = *inp++;
}
- *outp++ = (char)strtol((const char *)temp,NULL,16);
- } else {
- *outp++ = *inp++;
- }
- } else {
- *outp++ = *inp++;
+ length++;
}
- length++;
- }
- *sizep = length;
- return instring;
+ *sizep = length;
+ return instring;
}
int main(int argc, char *argv[])
{
- cmdname = "";
- arg1 = NULL;
- arg1len = 0;
- arg2 = NULL;
- arg2len = 0;
-
- if (argv[1]) {
- cmdname = "open";
- arg1 = argv[1];
- do_command();
- cmdname = "";
+ cmdname = "";
arg1 = NULL;
- }
+ arg1len = 0;
+ arg2 = NULL;
+ arg2len = 0;
+
+ if (argv[1]) {
+ cmdname = "open";
+ arg1 = argv[1];
+ do_command();
+ cmdname = "";
+ arg1 = NULL;
+ }
- switch (argc) {
+ switch (argc) {
case 1:
case 2:
- /* Interactive mode */
- while ((cmdname = tdb_getline("tdb> "))) {
- arg2 = arg1 = NULL;
- if ((arg1 = strchr((const char *)cmdname,' ')) != NULL) {
- arg1++;
- arg2 = arg1;
- while (*arg2) {
- if (*arg2 == ' ') {
- *arg2++ = '\0';
- break;
- }
- if ((*arg2++ == '\\') && (*arg2 == ' ')) {
- arg2++;
+ /* Interactive mode */
+ while ((cmdname = tdb_getline("tdb> "))) {
+ arg2 = arg1 = NULL;
+ if ((arg1 = strchr((const char *)cmdname,' ')) != NULL) {
+ arg1++;
+ arg2 = arg1;
+ while (*arg2) {
+ if (*arg2 == ' ') {
+ *arg2++ = '\0';
+ break;
+ }
+ if ((*arg2++ == '\\') && (*arg2 == ' ')) {
+ arg2++;
+ }
+ }
}
- }
+ if (arg1) arg1 = convert_string(arg1,&arg1len);
+ if (arg2) arg2 = convert_string(arg2,&arg2len);
+ if (do_command()) break;
}
- if (arg1) arg1 = convert_string(arg1,&arg1len);
- if (arg2) arg2 = convert_string(arg2,&arg2len);
- if (do_command()) break;
- }
- break;
+ break;
case 5:
- arg2 = convert_string(argv[4],&arg2len);
+ arg2 = convert_string(argv[4],&arg2len);
case 4:
- arg1 = convert_string(argv[3],&arg1len);
+ arg1 = convert_string(argv[3],&arg1len);
case 3:
- cmdname = argv[2];
+ cmdname = argv[2];
default:
- do_command();
- break;
- }
+ do_command();
+ break;
+ }
- if (tdb) tdb_close(tdb);
+ if (tdb) tdb_close(tdb);
- return 0;
+ return 0;
}
ssize_t res;
struct tevent_common_signal_list *sl;
struct tevent_context *ev = NULL;
+ int saved_errno = errno;
SIG_INCREMENT(sig_state->signal_count[signum]);
SIG_INCREMENT(sig_state->got_signal);
ev = sl->se->event_ctx;
}
}
+
+ errno = saved_errno;
}
#ifdef SA_SIGINFO
void sys_select_signal(char c)
{
+ int saved_errno = errno;
+
if (!initialised) return;
if (pipe_written > pipe_read+256) return;
if (write(select_pipe[1], &c, 1) == 1) pipe_written++;
+
+ errno = saved_errno;
}
/*******************************************************************
*******************************************************************************/
#define SCHANNEL_STORE_VERSION_1 1
-#define SCHANNEL_STORE_VERSION_2 2
-#define SCHANNEL_STORE_VERSION_CURRENT SCHANNEL_STORE_VERSION_2
+#define SCHANNEL_STORE_VERSION_2 2 /* should not be used */
+#define SCHANNEL_STORE_VERSION_CURRENT SCHANNEL_STORE_VERSION_1
TDB_CONTEXT *open_schannel_session_store(TALLOC_CTX *mem_ctx)
{
vers.dptr = NULL;
} else if (vers.dsize == 4) {
ver = IVAL(vers.dptr,0);
- if (ver != SCHANNEL_STORE_VERSION_CURRENT) {
+ if (ver == SCHANNEL_STORE_VERSION_2) {
DEBUG(0,("open_schannel_session_store: wrong version number %d in %s\n",
(int)ver, fname ));
tdb_wipe_all(tdb_sc);
goto again;
}
+ if (ver != SCHANNEL_STORE_VERSION_CURRENT) {
+ DEBUG(0,("open_schannel_session_store: wrong version number %d in %s\n",
+ (int)ver, fname ));
+ tdb_close(tdb_sc);
+ tdb_sc = NULL;
+ }
} else {
tdb_close(tdb_sc);
tdb_sc = NULL;
ret = wb_resp_write_recv(req, &err);
TALLOC_FREE(req);
if (ret == -1) {
+ close(state->sock);
+ state->sock = -1;
DEBUG(2, ("Could not write response to client: %s\n",
strerror(err)));
remove_client(state);
ret = wb_req_read_recv(req, state, &state->request, &err);
TALLOC_FREE(req);
if (ret == -1) {
+ close(state->sock);
+ state->sock = -1;
DEBUG(2, ("Could not read client request: %s\n",
strerror(err)));
remove_client(state);
return;
}
- /* tell client, we are closing ... */
- nwritten = write(state->sock, &c, sizeof(c));
- if (nwritten == -1) {
- /*
- * ignore EPIPE error here, because the other end might
- * have already closed the socket.
- */
- if (errno != EPIPE) {
+ if (state->sock != -1) {
+ /* tell client, we are closing ... */
+ nwritten = write(state->sock, &c, sizeof(c));
+ if (nwritten == -1) {
DEBUG(2, ("final write to client failed: %s\n",
- strerror(errno)));
+ strerror(errno)));
}
- }
- /* Close socket */
+ /* Close socket */
- close(state->sock);
+ close(state->sock);
+ state->sock = -1;
+ }
/* Free any getent state */
char *name;
char *saltbody;
- name = talloc_strdup(io->ac, io->u.sAMAccountName);
+ name = strlower_talloc(io->ac, io->u.sAMAccountName);
if (!name) {
ldb_oom(ldb);
return LDB_ERR_OPERATIONS_ERROR;
#include "ldb_module.h"
#include "dsdb/samdb/samdb.h"
+static int resolve_oids_need_value(struct ldb_context *ldb,
+ struct dsdb_schema *schema,
+ const struct dsdb_attribute *a,
+ const struct ldb_val *valp)
+{
+ const struct dsdb_attribute *va = NULL;
+ const struct dsdb_class *vo = NULL;
+ const void *p2;
+ char *str = NULL;
+
+ if (a->syntax->oMSyntax != 6) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ if (valp) {
+ p2 = memchr(valp->data, '.', valp->length);
+ } else {
+ p2 = NULL;
+ }
+
+ if (!p2) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ switch (a->attributeID_id) {
+ case DRSUAPI_ATTRIBUTE_objectClass:
+ case DRSUAPI_ATTRIBUTE_subClassOf:
+ case DRSUAPI_ATTRIBUTE_auxiliaryClass:
+ case DRSUAPI_ATTRIBUTE_systemPossSuperiors:
+ case DRSUAPI_ATTRIBUTE_possSuperiors:
+ str = talloc_strndup(ldb, (char *)valp->data, valp->length);
+ if (!str) {
+ ldb_oom(ldb);
+ return LDB_ERR_OPERATIONS_ERROR;
+ }
+ vo = dsdb_class_by_governsID_oid(schema, str);
+ talloc_free(str);
+ if (!vo) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+ return LDB_ERR_COMPARE_TRUE;
+ case DRSUAPI_ATTRIBUTE_systemMustContain:
+ case DRSUAPI_ATTRIBUTE_systemMayContain:
+ case DRSUAPI_ATTRIBUTE_mustContain:
+ case DRSUAPI_ATTRIBUTE_mayContain:
+ str = talloc_strndup(ldb, (char *)valp->data, valp->length);
+ if (!str) {
+ ldb_oom(ldb);
+ return LDB_ERR_OPERATIONS_ERROR;
+ }
+ va = dsdb_attribute_by_attributeID_oid(schema, str);
+ talloc_free(str);
+ if (!va) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+ return LDB_ERR_COMPARE_TRUE;
+ case DRSUAPI_ATTRIBUTE_governsID:
+ case DRSUAPI_ATTRIBUTE_attributeID:
+ case DRSUAPI_ATTRIBUTE_attributeSyntax:
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ return LDB_ERR_COMPARE_FALSE;
+}
+
+static int resolve_oids_parse_tree_need(struct ldb_context *ldb,
+ struct dsdb_schema *schema,
+ const struct ldb_parse_tree *tree)
+{
+ int i;
+ const struct dsdb_attribute *a = NULL;
+ const char *attr;
+ const char *p1;
+ const void *p2;
+ const struct ldb_val *valp = NULL;
+ int ret;
+
+ switch (tree->operation) {
+ case LDB_OP_AND:
+ case LDB_OP_OR:
+ for (i=0;i<tree->u.list.num_elements;i++) {
+ ret = resolve_oids_parse_tree_need(ldb, schema,
+ tree->u.list.elements[i]);
+ if (ret != LDB_ERR_COMPARE_FALSE) {
+ return ret;
+ }
+ }
+ return LDB_ERR_COMPARE_FALSE;
+ case LDB_OP_NOT:
+ return resolve_oids_parse_tree_need(ldb, schema,
+ tree->u.isnot.child);
+ case LDB_OP_EQUALITY:
+ case LDB_OP_GREATER:
+ case LDB_OP_LESS:
+ case LDB_OP_APPROX:
+ attr = tree->u.equality.attr;
+ valp = &tree->u.equality.value;
+ break;
+ case LDB_OP_SUBSTRING:
+ attr = tree->u.substring.attr;
+ break;
+ case LDB_OP_PRESENT:
+ attr = tree->u.present.attr;
+ break;
+ case LDB_OP_EXTENDED:
+ attr = tree->u.extended.attr;
+ valp = &tree->u.extended.value;
+ break;
+ default:
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ p1 = strchr(attr, '.');
+
+ if (valp) {
+ p2 = memchr(valp->data, '.', valp->length);
+ } else {
+ p2 = NULL;
+ }
+
+ if (!p1 && !p2) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ if (p1) {
+ a = dsdb_attribute_by_attributeID_oid(schema, attr);
+ } else {
+ a = dsdb_attribute_by_lDAPDisplayName(schema, attr);
+ }
+ if (!a) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ if (!p2) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ if (a->syntax->oMSyntax != 6) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ return resolve_oids_need_value(ldb, schema, a, valp);
+}
+
+static int resolve_oids_element_need(struct ldb_context *ldb,
+ struct dsdb_schema *schema,
+ const struct ldb_message_element *el)
+{
+ int i;
+ const struct dsdb_attribute *a = NULL;
+ const char *p1;
+
+ p1 = strchr(el->name, '.');
+
+ if (p1) {
+ a = dsdb_attribute_by_attributeID_oid(schema, el->name);
+ } else {
+ a = dsdb_attribute_by_lDAPDisplayName(schema, el->name);
+ }
+ if (!a) {
+ return LDB_ERR_COMPARE_FALSE;
+ }
+
+ for (i=0; i < el->num_values; i++) {
+ int ret;
+ ret = resolve_oids_need_value(ldb, schema, a,
+ &el->values[i]);
+ if (ret != LDB_ERR_COMPARE_FALSE) {
+ return ret;
+ }
+ }
+
+ return LDB_ERR_COMPARE_FALSE;
+}
+
+static int resolve_oids_message_need(struct ldb_context *ldb,
+ struct dsdb_schema *schema,
+ const struct ldb_message *msg)
+{
+ int i;
+
+ for (i=0; i < msg->num_elements; i++) {
+ int ret;
+ ret = resolve_oids_element_need(ldb, schema,
+ &msg->elements[i]);
+ if (ret != LDB_ERR_COMPARE_FALSE) {
+ return ret;
+ }
+ }
+
+ return LDB_ERR_COMPARE_FALSE;
+}
+
static int resolve_oids_replace_value(struct ldb_context *ldb,
struct dsdb_schema *schema,
const struct dsdb_attribute *a,
const char *p1;
const void *p2;
struct ldb_val *valp = NULL;
+ int ret;
switch (tree->operation) {
case LDB_OP_AND:
case LDB_OP_OR:
for (i=0;i<tree->u.list.num_elements;i++) {
- resolve_oids_parse_tree_replace(ldb, schema,
+ ret = resolve_oids_parse_tree_replace(ldb, schema,
tree->u.list.elements[i]);
+ if (ret != LDB_SUCCESS) {
+ return ret;
+ }
}
return LDB_SUCCESS;
case LDB_OP_NOT:
- resolve_oids_parse_tree_replace(ldb, schema,
+ return resolve_oids_parse_tree_replace(ldb, schema,
tree->u.isnot.child);
- return LDB_SUCCESS;
case LDB_OP_EQUALITY:
case LDB_OP_GREATER:
case LDB_OP_LESS:
return ldb_next_request(module, req);
}
+ ret = resolve_oids_parse_tree_need(ldb, schema,
+ req->op.search.tree);
+ if (ret == LDB_ERR_COMPARE_FALSE) {
+ return ldb_next_request(module, req);
+ } else if (ret != LDB_ERR_COMPARE_TRUE) {
+ return ret;
+ }
+
ac = talloc(req, struct resolve_oids_context);
if (ac == NULL) {
ldb_oom(ldb);
return ldb_next_request(module, req);
}
+ ret = resolve_oids_message_need(ldb, schema,
+ req->op.add.message);
+ if (ret == LDB_ERR_COMPARE_FALSE) {
+ return ldb_next_request(module, req);
+ } else if (ret != LDB_ERR_COMPARE_TRUE) {
+ return ret;
+ }
+
ac = talloc(req, struct resolve_oids_context);
if (ac == NULL) {
ldb_oom(ldb);
return ldb_next_request(module, req);
}
+ ret = resolve_oids_message_need(ldb, schema,
+ req->op.mod.message);
+ if (ret == LDB_ERR_COMPARE_FALSE) {
+ return ldb_next_request(module, req);
+ } else if (ret != LDB_ERR_COMPARE_TRUE) {
+ return ret;
+ }
+
ac = talloc(req, struct resolve_oids_context);
if (ac == NULL) {
ldb_oom(ldb);
if (ldb->transaction_active) {
ldb_debug(ldb, LDB_DEBUG_FATAL,
- "A transaction is still active in ldb context [%p]",
- ldb);
+ "A transaction is still active in ldb context [%p] on %s",
+ ldb, (const char *)ldb_get_opaque(ldb, "ldb_url"));
}
return 0;
vd[0] = data_blob_talloc(vd, NULL, 4);
if (composite_nomem(vd[0].data, c)) return;
- SIVAL(vd[0].data, 0, DS_DC_FUNCTION_2008_R2);
+ SIVAL(vd[0].data, 0, DS_DC_FUNCTION_2008);
vs[0].blob = &vd[0];
#include "auth/credentials/credentials_krb5.h"
#include "librpc/gen_ndr/ndr_samr_c.h"
#include "param/param.h"
+#include "param/provision.h"
/*
* complete a domain join, when joining to a AD domain:
return status;
}
-NTSTATUS libnet_set_join_secrets(struct libnet_context *ctx,
- TALLOC_CTX *mem_ctx,
- struct libnet_set_join_secrets *r)
-{
- TALLOC_CTX *tmp_mem;
- int ret, rtn;
- struct ldb_context *ldb;
- struct ldb_dn *base_dn;
- struct ldb_message **msgs, *msg;
- const char *sct;
- const char * const attrs[] = {
- "whenChanged",
- "secret",
- "priorSecret",
- "priorChanged",
- "krb5Keytab",
- "privateKeytab",
- NULL
- };
-
- tmp_mem = talloc_new(mem_ctx);
- if (!tmp_mem) {
- return NT_STATUS_NO_MEMORY;
- }
-
- /* Open the secrets database */
- ldb = secrets_db_connect(tmp_mem, ctx->event_ctx, ctx->lp_ctx);
- if (!ldb) {
- r->out.error_string
- = talloc_asprintf(mem_ctx,
- "Could not open secrets database");
- talloc_free(tmp_mem);
- return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
- }
-
- /*
- * now prepare the record for secrets.ldb
- */
- sct = talloc_asprintf(tmp_mem, "%d", r->in.join_type);
- if (!sct) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- msg = ldb_msg_new(tmp_mem);
- if (!msg) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- base_dn = ldb_dn_new(tmp_mem, ldb, "cn=Primary Domains");
- if (!base_dn) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- msg->dn = ldb_dn_copy(tmp_mem, base_dn);
- if ( ! ldb_dn_add_child_fmt(msg->dn, "flatname=%s", r->in.domain_name)) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "flatname", r->in.domain_name);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- if (r->in.realm) {
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "realm", r->in.realm);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "objectClass", "primaryDomain");
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "objectClass", "kerberosSecret");
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "secret", r->in.join_password);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "samAccountName", r->in.account_name);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_add_string(ldb, tmp_mem, msg, "secureChannelType", sct);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- if (r->in.kvno) {
- rtn = samdb_msg_add_uint(ldb, tmp_mem, msg, "msDS-KeyVersionNumber",
- r->in.kvno);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
-
- if (r->in.domain_sid) {
- rtn = samdb_msg_add_dom_sid(ldb, tmp_mem, msg, "objectSid",
- r->in.domain_sid);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
-
- /*
- * search for the secret record
- * - remove the records we find
- * - and fetch the old secret and store it under priorSecret
- */
- ret = gendb_search(ldb,
- tmp_mem, base_dn,
- &msgs, attrs,
- "(|" SECRETS_PRIMARY_DOMAIN_FILTER "(realm=%s))",
- r->in.domain_name, r->in.realm);
- if (ret == 0) {
- rtn = samdb_msg_set_string(ldb, tmp_mem, msg, "privateKeytab", "secrets.keytab");
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- } else if (ret == -1) {
- r->out.error_string
- = talloc_asprintf(mem_ctx,
- "Search for domain: %s and realm: %s failed: %s",
- r->in.domain_name, r->in.realm, ldb_errstring(ldb));
- talloc_free(tmp_mem);
- return NT_STATUS_INTERNAL_DB_CORRUPTION;
- } else {
- const struct ldb_val *private_keytab;
- const struct ldb_val *krb5_main_keytab;
- const struct ldb_val *prior_secret;
- const struct ldb_val *prior_modified_time;
- int i;
-
- for (i = 0; i < ret; i++) {
- ldb_delete(ldb, msgs[i]->dn);
- }
-
- prior_secret = ldb_msg_find_ldb_val(msgs[0], "secret");
- if (prior_secret) {
- rtn = samdb_msg_set_value(ldb, tmp_mem, msg, "priorSecret", prior_secret);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
- rtn = samdb_msg_set_string(ldb, tmp_mem, msg, "secret", r->in.join_password);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- prior_modified_time = ldb_msg_find_ldb_val(msgs[0],
- "whenChanged");
- if (prior_modified_time) {
- rtn = samdb_msg_set_value(ldb, tmp_mem, msg, "priorWhenChanged",
- prior_modified_time);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
-
- rtn = samdb_msg_set_string(ldb, tmp_mem, msg, "samAccountName", r->in.account_name);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- rtn = samdb_msg_set_string(ldb, tmp_mem, msg, "secureChannelType", sct);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
-
- /* We will want to keep the keytab names */
- private_keytab = ldb_msg_find_ldb_val(msgs[0], "privateKeytab");
- if (private_keytab) {
- rtn = samdb_msg_set_value(ldb, tmp_mem, msg, "privateKeytab", private_keytab);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
- krb5_main_keytab = ldb_msg_find_ldb_val(msgs[0], "krb5Keytab");
- if (krb5_main_keytab) {
- rtn = samdb_msg_set_value(ldb, tmp_mem, msg,
- "krb5Keytab", krb5_main_keytab);
- if (rtn == -1) {
- r->out.error_string = NULL;
- talloc_free(tmp_mem);
- return NT_STATUS_NO_MEMORY;
- }
- }
- }
-
- /* create the secret */
- ret = ldb_add(ldb, msg);
- if (ret != 0) {
- r->out.error_string = talloc_asprintf(mem_ctx, "Failed to create secret record %s",
- ldb_dn_get_linearized(msg->dn));
- talloc_free(tmp_mem);
- return NT_STATUS_INTERNAL_DB_CORRUPTION;
- }
-
- return NT_STATUS_OK;
-}
-
static NTSTATUS libnet_Join_primary_domain(struct libnet_context *ctx,
TALLOC_CTX *mem_ctx,
struct libnet_Join *r)
NTSTATUS status;
TALLOC_CTX *tmp_mem;
struct libnet_JoinDomain *r2;
- struct libnet_set_join_secrets *r3;
+ struct provision_store_self_join_settings *set_secrets;
uint32_t acct_type = 0;
const char *account_name;
const char *netbios_name;
-
+ const char *error_string;
+
r->out.error_string = NULL;
tmp_mem = talloc_new(mem_ctx);
return status;
}
- r3 = talloc(tmp_mem, struct libnet_set_join_secrets);
- if (!r3) {
+ set_secrets = talloc(tmp_mem, struct provision_store_self_join_settings);
+ if (!set_secrets) {
r->out.error_string = NULL;
talloc_free(tmp_mem);
return NT_STATUS_NO_MEMORY;
}
- ZERO_STRUCTP(r3);
- r3->in.domain_name = r2->out.domain_name;
- r3->in.realm = r2->out.realm;
- r3->in.account_name = account_name;
- r3->in.netbios_name = netbios_name;
- r3->in.join_type = r->in.join_type;
- r3->in.join_password = r2->out.join_password;
- r3->in.kvno = r2->out.kvno;
- r3->in.domain_sid = r2->out.domain_sid;
+ ZERO_STRUCTP(set_secrets);
+ set_secrets->domain_name = r2->out.domain_name;
+ set_secrets->realm = r2->out.realm;
+ set_secrets->account_name = account_name;
+ set_secrets->netbios_name = netbios_name;
+ set_secrets->secure_channel_type = r->in.join_type;
+ set_secrets->machine_password = r2->out.join_password;
+ set_secrets->key_version_number = r2->out.kvno;
+ set_secrets->domain_sid = r2->out.domain_sid;
- status = libnet_set_join_secrets(ctx, r3, r3);
+ status = provision_store_self_join(ctx, ctx->lp_ctx, ctx->event_ctx, set_secrets, &error_string);
if (!NT_STATUS_IS_OK(status)) {
- r->out.error_string = talloc_steal(mem_ctx, r3->out.error_string);
+ r->out.error_string = talloc_steal(mem_ctx, error_string);
talloc_free(tmp_mem);
return status;
}
/* move all out parameter to the callers TALLOC_CTX */
r->out.error_string = NULL;
r->out.join_password = r2->out.join_password;
- talloc_steal(mem_ctx, r2->out.join_password);
+ talloc_reparent(r2, mem_ctx, r2->out.join_password);
r->out.domain_sid = r2->out.domain_sid;
- talloc_steal(mem_ctx, r2->out.domain_sid);
+ talloc_reparent(r2, mem_ctx, r2->out.domain_sid);
r->out.domain_name = r2->out.domain_name;
- talloc_steal(mem_ctx, r2->out.domain_name);
+ talloc_reparent(r2, mem_ctx, r2->out.domain_name);
talloc_free(tmp_mem);
return NT_STATUS_OK;
}
struct libnet_Vampire *r)
{
struct libnet_JoinDomain *join;
- struct libnet_set_join_secrets *set_secrets;
+ struct provision_store_self_join_settings *set_secrets;
struct libnet_BecomeDC b;
struct vampire_state *s;
struct ldb_message *msg;
+ const char *error_string;
int ldb_ret;
uint32_t i;
NTSTATUS status;
return NT_STATUS_INTERNAL_DB_ERROR;
}
- /* commit the transaction - this commits all the changes in
- the ldb from the whole vampire. Note that this commit
+ /* prepare the transaction - this prepares to commit all the changes in
+ the ldb from the whole vampire. Note that this
triggers the writing of the linked attribute backlinks.
*/
- if (ldb_transaction_commit(s->ldb) != LDB_SUCCESS) {
- printf("Failed to commit vampire transaction\n");
+ if (ldb_transaction_prepare_commit(s->ldb) != LDB_SUCCESS) {
+ printf("Failed to prepare_commit vampire transaction\n");
return NT_STATUS_INTERNAL_DB_ERROR;
}
- set_secrets = talloc_zero(s, struct libnet_set_join_secrets);
+ set_secrets = talloc(s, struct provision_store_self_join_settings);
if (!set_secrets) {
+ r->out.error_string = NULL;
+ talloc_free(s);
return NT_STATUS_NO_MEMORY;
}
-
- set_secrets->in.domain_name = join->out.domain_name;
- set_secrets->in.realm = join->out.realm;
- set_secrets->in.account_name = account_name;
- set_secrets->in.netbios_name = netbios_name;
- set_secrets->in.join_type = SEC_CHAN_BDC;
- set_secrets->in.join_password = join->out.join_password;
- set_secrets->in.kvno = join->out.kvno;
- set_secrets->in.domain_sid = join->out.domain_sid;
- status = libnet_set_join_secrets(ctx, set_secrets, set_secrets);
+ ZERO_STRUCTP(set_secrets);
+ set_secrets->domain_name = join->out.domain_name;
+ set_secrets->realm = join->out.realm;
+ set_secrets->account_name = account_name;
+ set_secrets->netbios_name = netbios_name;
+ set_secrets->secure_channel_type = SEC_CHAN_BDC;
+ set_secrets->machine_password = join->out.join_password;
+ set_secrets->key_version_number = join->out.kvno;
+ set_secrets->domain_sid = join->out.domain_sid;
+
+ status = provision_store_self_join(ctx, ctx->lp_ctx, ctx->event_ctx, set_secrets, &error_string);
if (!NT_STATUS_IS_OK(status)) {
- r->out.error_string = talloc_steal(mem_ctx, set_secrets->out.error_string);
+ r->out.error_string = talloc_steal(mem_ctx, error_string);
talloc_free(s);
return status;
}
r->out.domain_name = talloc_steal(r, join->out.domain_name);
r->out.domain_sid = talloc_steal(r, join->out.domain_sid);
- talloc_free(s);
+ /* commit the transaction now we know the secrets were written
+ * out properly
+ */
+ if (ldb_transaction_commit(s->ldb) != LDB_SUCCESS) {
+ printf("Failed to commit vampire transaction\n");
+ return NT_STATUS_INTERNAL_DB_ERROR;
+ }
+
+ talloc_free(s);
+
return NT_STATUS_OK;
}
#define Py_RETURN_NONE return Py_INCREF(Py_None), Py_None
#endif
+PyObject *py_dom_sid_FromSid(struct dom_sid *sid)
+{
+ return py_talloc_reference(&dom_sid_Type, sid);
+}
+
static void PyType_AddMethods(PyTypeObject *type, PyMethodDef *methods)
{
PyObject *dict;
--- /dev/null
+/*
+ Unix SMB/CIFS implementation.
+ Samba utility functions
+ Copyright (C) Jelmer Vernooij <jelmer@samba.org> 2008
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "libcli/security/security.h"
+
+/* a lone prototype for this function, because it's python */
+PyObject *py_dom_sid_FromSid(struct dom_sid *sid);
PC_FILES += $(paramsrcdir)/samba-hostconfig.pc
[SUBSYSTEM::PROVISION]
-PRIVATE_DEPENDENCIES = LIBPYTHON pyldb pyparam_util
+PRIVATE_DEPENDENCIES = LIBPYTHON pyldb pyparam_util python_dcerpc_security
PROVISION_OBJ_FILES = $(paramsrcdir)/provision.o $(param_OBJ_FILES)
Unix SMB/CIFS implementation.
Samba utility functions
Copyright (C) Jelmer Vernooij <jelmer@samba.org> 2008
-
+ Copyright (C) Andrew Bartlett <abartlet@samba.org> 2005
+
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
#include "includes.h"
#include "auth/auth.h"
#include "lib/ldb_wrap.h"
+#include "ldb/include/ldb.h"
+#include "ldb_errors.h"
#include "libcli/raw/libcliraw.h"
#include "librpc/ndr/libndr.h"
#include "param/param.h"
#include "param/provision.h"
+#include "param/secrets.h"
#include <Python.h>
+#include "lib/talloc/pytalloc.h"
+#include "librpc/rpc/pyrpc.h"
#include "scripting/python/modules.h"
#include "lib/ldb/pyldb.h"
#include "param/pyparam.h"
+#include "librpc/ndr/py_security.h"
NTSTATUS provision_bare(TALLOC_CTX *mem_ctx, struct loadparm_context *lp_ctx,
struct provision_settings *settings,
return NT_STATUS_OK;
}
+
+extern void initldb(void);
+extern void initsecurity(void);
+
+NTSTATUS provision_store_self_join(TALLOC_CTX *mem_ctx, struct loadparm_context *lp_ctx,
+ struct tevent_context *event_ctx,
+ struct provision_store_self_join_settings *settings,
+ const char **error_string)
+{
+ int ret;
+ PyObject *provision_mod, *provision_dict, *provision_fn, *py_result, *parameters, *py_sid;
+ struct ldb_context *ldb;
+ TALLOC_CTX *tmp_mem = talloc_new(mem_ctx);
+ if (!tmp_mem) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ /* Open the secrets database */
+ ldb = secrets_db_connect(tmp_mem, event_ctx, lp_ctx);
+ if (!ldb) {
+ *error_string
+ = talloc_asprintf(mem_ctx,
+ "Could not open secrets database");
+ talloc_free(tmp_mem);
+ return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
+ }
+
+ ret = ldb_transaction_start(ldb);
+
+ if (ret != LDB_SUCCESS) {
+ *error_string
+ = talloc_asprintf(mem_ctx,
+ "Could not start transaction on secrets database: %s", ldb_errstring(ldb));
+ talloc_free(tmp_mem);
+ return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
+ }
+
+ py_load_samba_modules();
+ Py_Initialize();
+ py_update_path("bin"); /* FIXME: Can't assume this is always the case */
+ initldb();
+ initsecurity();
+ provision_mod = PyImport_Import(PyString_FromString("samba.provision"));
+
+ if (provision_mod == NULL) {
+ PyErr_Print();
+ *error_string
+ = talloc_asprintf(mem_ctx, "Unable to import provision Python module.");
+ talloc_free(tmp_mem);
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ provision_dict = PyModule_GetDict(provision_mod);
+
+ if (provision_dict == NULL) {
+ *error_string
+ = talloc_asprintf(mem_ctx, "Unable to get dictionary for provision module");
+ talloc_free(tmp_mem);
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ provision_fn = PyDict_GetItemString(provision_dict, "secretsdb_self_join");
+ if (provision_fn == NULL) {
+ PyErr_Print();
+ *error_string
+ = talloc_asprintf(mem_ctx, "Unable to get provision_become_dc function");
+ talloc_free(tmp_mem);
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ parameters = PyDict_New();
+
+ PyDict_SetItemString(parameters, "secretsdb",
+ PyLdb_FromLdbContext(ldb));
+ PyDict_SetItemString(parameters, "domain",
+ PyString_FromString(settings->domain_name));
+ PyDict_SetItemString(parameters, "domain",
+ PyString_FromString(settings->domain_name));
+ PyDict_SetItemString(parameters, "realm",
+ PyString_FromString(settings->realm));
+ PyDict_SetItemString(parameters, "machinepass",
+ PyString_FromString(settings->machine_password));
+ PyDict_SetItemString(parameters, "netbiosname",
+ PyString_FromString(settings->netbios_name));
+
+ py_sid = py_dom_sid_FromSid(settings->domain_sid);
+
+ PyDict_SetItemString(parameters, "domainsid",
+ py_sid);
+
+ PyDict_SetItemString(parameters, "secure_channel_type",
+ PyInt_FromLong(settings->secure_channel_type));
+
+ PyDict_SetItemString(parameters, "key_version_number",
+ PyInt_FromLong(settings->key_version_number));
+
+ py_result = PyEval_CallObjectWithKeywords(provision_fn, NULL, parameters);
+
+ Py_DECREF(parameters);
+
+ if (py_result == NULL) {
+ ldb_transaction_cancel(ldb);
+ talloc_free(tmp_mem);
+
+ PyErr_Print();
+ PyErr_Clear();
+ return NT_STATUS_UNSUCCESSFUL;
+ }
+
+ ret = ldb_transaction_commit(ldb);
+ if (ret != LDB_SUCCESS) {
+ *error_string
+ = talloc_asprintf(mem_ctx,
+ "Could not commit transaction on secrets database: %s", ldb_errstring(ldb));
+ talloc_free(tmp_mem);
+ return NT_STATUS_INTERNAL_DB_ERROR;
+ }
+
+ talloc_free(tmp_mem);
+
+ return NT_STATUS_OK;
+}
struct loadparm_context *lp_ctx;
};
+struct provision_store_self_join_settings {
+ const char *domain_name;
+ const char *realm;
+ const char *netbios_name;
+ const char *account_name;
+ enum netr_SchannelType secure_channel_type;
+ const char *machine_password;
+ int key_version_number;
+ struct dom_sid *domain_sid;
+};
+
NTSTATUS provision_bare(TALLOC_CTX *mem_ctx, struct loadparm_context *lp_ctx,
struct provision_settings *settings,
struct provision_result *result);
+NTSTATUS provision_store_self_join(TALLOC_CTX *mem_ctx, struct loadparm_context *lp_ctx,
+ struct tevent_context *ev_ctx,
+ struct provision_store_self_join_settings *settings,
+ const char **error_string);
+
#endif /* _PROVISION_H_ */
from auth import system_session, admin_session
from samba import version, Ldb, substitute_var, valid_netbios_name
from samba import check_all_substituted
-from samba import DS_DOMAIN_FUNCTION_2000, DS_DC_FUNCTION_2008_R2
+from samba import DS_DOMAIN_FUNCTION_2000, DS_DOMAIN_FUNCTION_2008, DS_DC_FUNCTION_2008, DS_DC_FUNCTION_2008_R2
from samba.samdb import SamDB
from samba.idmap import IDmapDB
from samba.dcerpc import security
from ms_schema import read_ms_schema
from ms_display_specifiers import read_ms_ldif
from signal import SIGTERM
+from dcerpc.misc import SEC_CHAN_BDC, SEC_CHAN_WKSTA
__docformat__ = "restructuredText"
-
-class ProvisioningError(ValueError):
- pass
-
-
def find_setup_dir():
"""Find the setup directory used by provision."""
dirname = os.path.dirname(__file__)
DEFAULTSITE = "Default-First-Site-Name"
+# Exception classes
+
+class ProvisioningError(Exception):
+ """A generic provision error."""
+
class InvalidNetbiosName(Exception):
"""A specified name was not a valid NetBIOS name."""
def __init__(self, name):
"""
paths = ProvisionPaths()
paths.private_dir = lp.get("private dir")
- paths.keytab = "secrets.keytab"
paths.dns_keytab = "dns.keytab"
paths.shareconf = os.path.join(paths.private_dir, "share.ldb")
samdb.transaction_commit()
+def secretsdb_self_join(secretsdb, domain,
+ netbiosname, domainsid, machinepass,
+ realm=None, dnsdomain=None,
+ keytab_path=None,
+ key_version_number=1,
+ secure_channel_type=SEC_CHAN_WKSTA):
+ """Add domain join-specific bits to a secrets database.
+
+ :param secretsdb: Ldb Handle to the secrets database
+ :param machinepass: Machine password
+ """
+ attrs=["whenChanged",
+ "secret",
+ "priorSecret",
+ "priorChanged",
+ "krb5Keytab",
+ "privateKeytab"]
+
+
+ msg = ldb.Message(ldb.Dn(secretsdb, "flatname=%s,cn=Primary Domains" % domain));
+ msg["secureChannelType"] = str(secure_channel_type)
+ msg["flatname"] = [domain]
+ msg["objectClass"] = ["top", "primaryDomain"]
+ if realm is not None:
+ if dnsdomain is None:
+ dnsdomain = realm.lower()
+ msg["objectClass"] = ["top", "primaryDomain", "kerberosSecret"]
+ msg["realm"] = realm
+ msg["saltPrincipal"] = "host/%s.%s@%s" % (netbiosname.lower(), dnsdomain.lower(), realm.upper())
+ msg["msDS-KeyVersionNumber"] = [str(key_version_number)]
+ msg["privateKeytab"] = ["secrets.keytab"];
+
+
+ msg["secret"] = [machinepass]
+ msg["samAccountName"] = ["%s$" % netbiosname]
+ msg["secureChannelType"] = [str(secure_channel_type)]
+ msg["objectSid"] = [ndr_pack(domainsid)]
+
+ res = secretsdb.search(base="cn=Primary Domains",
+ attrs=attrs,
+ expression=("(&(|(flatname=%s)(realm=%s)(objectSid=%s))(objectclass=primaryDomain))" % (domain, realm, str(domainsid))),
+ scope=SCOPE_ONELEVEL)
+
+ for del_msg in res:
+ if del_msg.dn is not msg.dn:
+ secretsdb.delete(del_msg.dn)
+
+ res = secretsdb.search(base=msg.dn, attrs=attrs, scope=SCOPE_BASE)
+ if len(res) == 1:
+ msg["priorSecret"] = res[0]["secret"]
+ msg["priorWhenChanged"] = res[0]["whenChanged"]
-def secretsdb_become_dc(secretsdb, setup_path, domain, realm, dnsdomain,
- netbiosname, domainsid, keytab_path, samdb_url,
- dns_keytab_path, dnspass, machinepass):
- """Add DC-specific bits to a secrets database.
+ if res["privateKeytab"] is not None:
+ msg["privateKeytab"] = res[0]["privateKeytab"]
+
+ if res["krb5Keytab"] is not None:
+ msg["krb5Keytab"] = res[0]["krb5Keytab"]
+
+ for el in msg:
+ el.set_flags(ldb.FLAG_MOD_REPLACE)
+ secretsdb.modify(msg)
+ else:
+ secretsdb.add(msg)
+
+
+def secretsdb_setup_dns(secretsdb, setup_path, realm, dnsdomain,
+ dns_keytab_path, dnspass):
+ """Add DNS specific bits to a secrets database.
:param secretsdb: Ldb Handle to the secrets database
:param setup_path: Setup path function
:param machinepass: Machine password
"""
- setup_ldb(secretsdb, setup_path("secrets_dc.ldif"), {
- "MACHINEPASS_B64": b64encode(machinepass),
- "DOMAIN": domain,
+ setup_ldb(secretsdb, setup_path("secrets_dns.ldif"), {
"REALM": realm,
"DNSDOMAIN": dnsdomain,
- "DOMAINSID": str(domainsid),
- "SECRETS_KEYTAB": keytab_path,
- "NETBIOSNAME": netbiosname,
- "SAM_LDB": samdb_url,
"DNS_KEYTAB": dns_keytab_path,
"DNSPASS_B64": b64encode(dnspass),
})
secrets_ldb.load_ldif_file_add(setup_path("secrets_init.ldif"))
secrets_ldb = Ldb(path, session_info=session_info, credentials=credentials,
lp=lp)
+ secrets_ldb.transaction_start()
secrets_ldb.load_ldif_file_add(setup_path("secrets.ldif"))
if credentials is not None and credentials.authentication_requested():
:note: This will wipe the main SAM database file!
"""
- domainFunctionality = DS_DOMAIN_FUNCTION_2000
- forestFunctionality = DS_DOMAIN_FUNCTION_2000
- domainControllerFunctionality = DS_DC_FUNCTION_2008_R2
+ # Do NOT change these default values without discussion with the team and reslease manager.
+ domainFunctionality = DS_DOMAIN_FUNCTION_2008
+ forestFunctionality = DS_DOMAIN_FUNCTION_2008
+ domainControllerFunctionality = DS_DC_FUNCTION_2008
# Also wipes the database
setup_samdb_partitions(path, setup_path, message=message, lp=lp,
# Only make a zone file on the first DC, it should be replicated with DNS replication
if serverrole == "domain controller":
- secrets_ldb = Ldb(paths.secrets, session_info=session_info,
- credentials=credentials, lp=lp)
- secretsdb_become_dc(secrets_ldb, setup_path, domain=domain,
+ secretsdb_self_join(secrets_ldb, domain=domain,
realm=names.realm,
+ dnsdomain=names.dnsdomain,
netbiosname=names.netbiosname,
domainsid=domainsid,
- keytab_path=paths.keytab, samdb_url=paths.samdb,
+ machinepass=machinepass,
+ secure_channel_type=SEC_CHAN_BDC)
+
+ secretsdb_setup_dns(secrets_ldb, setup_path,
+ realm=names.realm, dnsdomain=names.dnsdomain,
dns_keytab_path=paths.dns_keytab,
- dnspass=dnspass, machinepass=machinepass,
- dnsdomain=names.dnsdomain)
+ dnspass=dnspass)
domainguid = samdb.searchone(basedn=domaindn, attribute="objectGUID")
assert isinstance(domainguid, str)
realm=names.realm)
message("A Kerberos configuration suitable for Samba 4 has been generated at %s" % paths.krb5conf)
+ #Now commit the secrets.ldb to disk
+ secrets_ldb.transaction_commit()
if provision_backend is not None:
if ldap_backend_type == "fedora-ds":
self.transaction_start()
try:
res = self.search(base=self.domain_dn(), scope=ldb.SCOPE_SUBTREE,
- expression=filter,
- attrs=["userAccountControl", "accountExpires"])
+ expression=filter,
+ attrs=["userAccountControl", "accountExpires"])
assert(len(res) == 1)
user_dn = res[0].dn
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--quiet", help="Be quiet", action="store_true")
parser.add_option("--forest",
help="The forest function level (2000 | 2003 | 2008 | 2008_R2). We don't support the 2003 with mixed domains (NT4 DC support) level.", type=str)
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
domain_dn = SamDB.domain_dn(samdb)
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--filter", help="LDAP Filter to set password on", type=str)
opts, args = parser.parse_args()
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
+
samdb.enable_account(filter)
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--unixname", help="Unix Username", type=str)
parser.add_option("--must-change-at-next-login", help="Force password to be changed on next login", action="store_true")
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
+
samdb.newuser(username, opts.unixname, password, force_password_change_at_next_login_req=opts.must_change_at_next_login)
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--quiet", help="Be quiet", action="store_true")
parser.add_option("--complexity",
help="The password complexity (on | off | default). Default is 'on'", type=str)
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
domain_dn = SamDB.domain_dn(samdb)
res = samdb.search(domain_dn, scope=ldb.SCOPE_BASE,
+++ /dev/null
-dn: flatname=${DOMAIN},CN=Primary Domains
-objectClass: top
-objectClass: primaryDomain
-objectClass: kerberosSecret
-flatname: ${DOMAIN}
-realm: ${REALM}
-secret:: ${MACHINEPASS_B64}
-secureChannelType: 6
-sAMAccountName: ${NETBIOSNAME}$
-msDS-KeyVersionNumber: 1
-objectSid: ${DOMAINSID}
-privateKeytab: ${SECRETS_KEYTAB}
-
-#Update a keytab for the external DNS server to use
-dn: servicePrincipalName=DNS/${DNSDOMAIN},CN=Principals
-objectClass: top
-objectClass: secret
-objectClass: kerberosSecret
-realm: ${REALM}
-servicePrincipalName: DNS/${DNSDOMAIN}
-msDS-KeyVersionNumber: 1
-privateKeytab: ${DNS_KEYTAB}
-secret:: ${DNSPASS_B64}
-
--- /dev/null
+#Update a keytab for the external DNS server to use
+dn: servicePrincipalName=DNS/${DNSDOMAIN},CN=Principals
+objectClass: top
+objectClass: secret
+objectClass: kerberosSecret
+realm: ${REALM}
+servicePrincipalName: DNS/${DNSDOMAIN}
+msDS-KeyVersionNumber: 1
+privateKeytab: ${DNS_KEYTAB}
+secret:: ${DNSPASS_B64}
+
--- /dev/null
+dn: flatname=${DOMAIN},CN=Primary Domains
+objectClass: top
+objectClass: primaryDomain
+objectClass: kerberosSecret
+flatname: ${DOMAIN}
+realm: ${REALM}
+secret:: ${MACHINEPASS_B64}
+secureChannelType: 6
+sAMAccountName: ${NETBIOSNAME}$
+msDS-KeyVersionNumber: ${KEY_VERSION_NUMBER}
+objectSid: ${DOMAINSID}
+privateKeytab: ${SECRETS_KEYTAB}
+saltPrincipal: ${SALT_PRINCIPAL}
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--filter", help="LDAP Filter to set password on", type=str)
parser.add_option("--days", help="Days to expiry", type=int)
parser.add_option("--noexpiry", help="Password does never expire", action="store_true")
opts, args = parser.parse_args()
+filter = opts.filter
+
if (len(args) == 0) and (filter is None):
print "Either the username or '--filter' must be specified!"
parser.print_usage()
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
+
samdb.setexpiry(filter, days*24*3600, no_expiry_req=opts.noexpiry)
parser.add_option_group(options.VersionOptions(parser))
credopts = options.CredentialsOptions(parser)
parser.add_option_group(credopts)
+parser.add_option("-H", help="LDB URL for database or target server", type=str)
parser.add_option("--filter", help="LDAP Filter to set password on", type=str)
parser.add_option("--newpassword", help="Set password", type=str)
parser.add_option("--must-change-at-next-login", help="Force password to be changed on next login", action="store_true")
lp = sambaopts.get_loadparm()
creds = credopts.get_credentials(lp)
-samdb = SamDB(url=lp.get("sam database"), session_info=system_session(),
- credentials=creds, lp=lp)
-samdb.setpassword(filter, password, force_password_change_at_next_login=opts.must_change_at_next_login)
+if opts.H is not None:
+ url = opts.H
+else:
+ url = lp.get("sam database")
+
+samdb = SamDB(url=url, session_info=system_session(), credentials=creds, lp=lp)
+
+samdb.setpassword(filter, password, force_password_change_at_next_login_req=opts.must_change_at_next_login)
testit "set user password with kerberos ccache" $VALGRIND $net password set $DOMAIN\\nettestuser $USERPASS $CONFIGURATION -k yes $@ || failed=`expr $failed + 1`
-testit "enable user with kerberos cache" $VALGRIND $enableaccount nettestuser -k yes $@ || failed=`expr $failed + 1`
+testit "enable user with kerberos cache" $VALGRIND $enableaccount nettestuser -H ldap://$SERVER -k yes $@ || failed=`expr $failed + 1`
KRB5CCNAME="$PREFIX/tmpuserccache"
export KRB5CCNAME