/* setup some initial ldif in a ldb */ int gendb_add_ldif(struct ldb_context *ldb, const char *ldif_string) { struct ldb_ldif *ldif; int ret; ldif = ldb_ldif_read_string(ldb, &ldif_string); if (ldif == NULL) return -1; ret = ldb_add(ldb, ldif->msg); talloc_free(ldif); return ret; }
/** \details return the mapped property ID matching the nameid structure passed in parameter. \param ldb_ctx pointer to the namedprops ldb context \param nameid the MAPINAMEID structure to lookup \param propID pointer to the property ID the function returns \return MAPISTORE_SUCCESS on success, otherwise MAPISTORE_ERROR */ _PUBLIC_ enum mapistore_error mapistore_namedprops_create_id(struct ldb_context *ldb_ctx, struct MAPINAMEID nameid, uint16_t mapped_id) { int ret; TALLOC_CTX *mem_ctx; char *ldif_record; struct ldb_ldif *ldif; char *hex_id, *dec_id, *dec_mappedid, *guid; struct ldb_message *normalized_msg; const char *ldif_records[] = { NULL, NULL }; mem_ctx = talloc_zero(NULL, TALLOC_CTX); dec_mappedid = talloc_asprintf(mem_ctx, "%u", mapped_id); guid = GUID_string(mem_ctx, &nameid.lpguid); switch (nameid.ulKind) { case MNID_ID: hex_id = talloc_asprintf(mem_ctx, "%.4x", nameid.kind.lid); dec_id = talloc_asprintf(mem_ctx, "%u", nameid.kind.lid); ldif_record = talloc_asprintf(mem_ctx, "dn: CN=0x%s,CN=%s,CN=default\nobjectClass: MNID_ID\ncn: 0x%s\npropType: PT_NULL\noleguid: %s\nmappedId: %s\npropId: %s\n", hex_id, guid, hex_id, guid, dec_mappedid, dec_id); break; case MNID_STRING: ldif_record = talloc_asprintf(mem_ctx, "dn: CN=%s,CN=%s,CN=default\nobjectClass: MNID_STRING\ncn: %s\npropType: PT_NULL\noleguid: %s\nmappedId: %s\npropName: %s\n", nameid.kind.lpwstr.Name, guid, nameid.kind.lpwstr.Name, guid, dec_mappedid, nameid.kind.lpwstr.Name); break; default: abort(); } DEBUG(5, ("inserting record:\n%s\n", ldif_record)); ldif_records[0] = ldif_record; ldif = ldb_ldif_read_string(ldb_ctx, ldif_records); ret = ldb_msg_normalize(ldb_ctx, mem_ctx, ldif->msg, &normalized_msg); MAPISTORE_RETVAL_IF(ret, MAPISTORE_ERR_DATABASE_INIT, NULL); ret = ldb_add(ldb_ctx, normalized_msg); talloc_free(normalized_msg); if (ret != LDB_SUCCESS) { MAPISTORE_RETVAL_IF(ret, MAPISTORE_ERR_DATABASE_INIT, NULL); } /* we invalidate the cache, if present */ if (nameids_cache) { talloc_free(nameids_cache); nameids_cache = NULL; } return ret; }
int confdb_create_base(struct confdb_ctx *cdb) { int ret; struct ldb_ldif *ldif; const char *base_ldif = CONFDB_BASE_LDIF; while ((ldif = ldb_ldif_read_string(cdb->ldb, &base_ldif))) { ret = ldb_add(cdb->ldb, ldif->msg); if (ret != LDB_SUCCESS) { DEBUG(0, ("Failed to initialize DB (%d,[%s]), aborting!\n", ret, ldb_errstring(cdb->ldb))); return EIO; } ldb_ldif_read_free(cdb->ldb, ldif); } return EOK; }
static int confdb_write_ldif(struct confdb_ctx *cdb, const char *config_ldif, bool replace_whole_db) { int ret; struct ldb_ldif *ldif; while ((ldif = ldb_ldif_read_string(cdb->ldb, &config_ldif))) { if (ldif->changetype == LDB_CHANGETYPE_DELETE) { /* We should remove this section */ ret = ldb_delete(cdb->ldb, ldif->msg->dn); if (ret == LDB_ERR_NO_SUCH_OBJECT) { /* Removing a non-existing section is not an error */ ret = LDB_SUCCESS; } } else { ret = ldb_add(cdb->ldb, ldif->msg); if (ret != LDB_SUCCESS && replace_whole_db == false) { /* This section already existed, remove and re-add it. We * really want to replace the whole thing instead of messing * around with changetypes and flags on individual elements */ ret = ldb_delete(cdb->ldb, ldif->msg->dn); if (ret == LDB_SUCCESS) { ret = ldb_add(cdb->ldb, ldif->msg); } } } if (ret != LDB_SUCCESS) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to initialize DB (%d,[%s]), aborting!\n", ret, ldb_errstring(cdb->ldb)); return EIO; } ldb_ldif_read_free(cdb->ldb, ldif); } return EOK; }
static bool torture_syntax_add_OR_Name(struct torture_context *tctx, struct ldb_context *ldb, struct dsdb_schema *schema) { WERROR werr; int ldb_res; struct ldb_ldif *ldif; const char *ldif_str = "dn: CN=ms-Exch-Auth-Orig,CN=Schema,CN=Configuration,DC=kma-exch,DC=devel\n" "changetype: add\n" "cn: ms-Exch-Auth-Orig\n" "attributeID: 1.2.840.113556.1.2.129\n" "attributeSyntax: 2.5.5.7\n" "isSingleValued: FALSE\n" "linkID: 110\n" "showInAdvancedViewOnly: TRUE\n" "adminDisplayName: ms-Exch-Auth-Orig\n" "oMObjectClass:: VgYBAgULHQ==\n" "adminDescription: ms-Exch-Auth-Orig\n" "oMSyntax: 127\n" "searchFlags: 16\n" "lDAPDisplayName: authOrig\n" "name: ms-Exch-Auth-Orig\n" "objectGUID:: 7tqEWktjAUqsZXqsFPQpRg==\n" "schemaIDGUID:: l3PfqOrF0RG7ywCAx2ZwwA==\n" "attributeSecurityGUID:: VAGN5Pi80RGHAgDAT7lgUA==\n" "isMemberOfPartialAttributeSet: TRUE\n"; ldif = ldb_ldif_read_string(ldb, &ldif_str); torture_assert(tctx, ldif, "Failed to parse LDIF for authOrig"); werr = dsdb_set_attribute_from_ldb(ldb, schema, ldif->msg); ldb_ldif_read_free(ldb, ldif); torture_assert_werr_ok(tctx, werr, "dsdb_set_attribute_from_ldb() failed!"); ldb_res = dsdb_set_schema(ldb, schema); torture_assert_int_equal(tctx, ldb_res, LDB_SUCCESS, "dsdb_set_schema() failed"); return true; };
WERROR dsdb_set_schema_from_ldif(struct ldb_context *ldb, const char *pf, const char *df, const char *dn) { struct ldb_ldif *ldif; struct ldb_message *msg; TALLOC_CTX *mem_ctx; WERROR status; int ret; struct dsdb_schema *schema; const struct ldb_val *prefix_val; const struct ldb_val *info_val; struct ldb_val info_val_default; mem_ctx = talloc_new(ldb); if (!mem_ctx) { goto nomem; } schema = dsdb_new_schema(mem_ctx); if (!schema) { goto nomem; } schema->base_dn = ldb_dn_new(schema, ldb, dn); if (!schema->base_dn) { goto nomem; } schema->fsmo.we_are_master = true; schema->fsmo.update_allowed = true; schema->fsmo.master_dn = ldb_dn_new(schema, ldb, "@PROVISION_SCHEMA_MASTER"); if (!schema->fsmo.master_dn) { goto nomem; } /* * load the prefixMap attribute from pf */ ldif = ldb_ldif_read_string(ldb, &pf); if (!ldif) { status = WERR_INVALID_PARAM; goto failed; } talloc_steal(mem_ctx, ldif); ret = ldb_msg_normalize(ldb, mem_ctx, ldif->msg, &msg); if (ret != LDB_SUCCESS) { goto nomem; } talloc_free(ldif); prefix_val = ldb_msg_find_ldb_val(msg, "prefixMap"); if (!prefix_val) { status = WERR_INVALID_PARAM; goto failed; } info_val = ldb_msg_find_ldb_val(msg, "schemaInfo"); if (!info_val) { status = dsdb_schema_info_blob_new(mem_ctx, &info_val_default); W_ERROR_NOT_OK_GOTO(status, failed); info_val = &info_val_default; } status = dsdb_load_oid_mappings_ldb(schema, prefix_val, info_val); if (!W_ERROR_IS_OK(status)) { DEBUG(0,("ERROR: dsdb_load_oid_mappings_ldb() failed with %s\n", win_errstr(status))); goto failed; } /* load the attribute and class definitions out of df */ while ((ldif = ldb_ldif_read_string(ldb, &df))) { talloc_steal(mem_ctx, ldif); ret = ldb_msg_normalize(ldb, ldif, ldif->msg, &msg); if (ret != LDB_SUCCESS) { goto nomem; } status = dsdb_schema_set_el_from_ldb_msg(ldb, schema, msg); talloc_free(ldif); if (!W_ERROR_IS_OK(status)) { goto failed; } } ret = dsdb_set_schema(ldb, schema); if (ret != LDB_SUCCESS) { status = WERR_FOOBAR; goto failed; } ret = dsdb_schema_fill_extended_dn(ldb, schema); if (ret != LDB_SUCCESS) { status = WERR_FOOBAR; goto failed; } goto done; nomem: status = WERR_NOMEM; failed: done: talloc_free(mem_ctx); return status; }
/* test ldb speed */ static bool test_ldb_speed(struct torture_context *torture, const void *_data) { struct timeval tv; struct ldb_context *ldb; int timelimit = torture_setting_int(torture, "timelimit", 10); int i, count; TALLOC_CTX *tmp_ctx = talloc_new(torture); struct ldb_ldif *ldif; const char *init_ldif = "dn: @INDEXLIST\n" \ "@IDXATTR: UID\n"; float ldb_speed; unlink("./test.ldb"); torture_comment(torture, "Testing ldb speed for sidmap\n"); ldb = ldb_wrap_connect(tmp_ctx, torture->ev, torture->lp_ctx, "tdb://test.ldb", NULL, NULL, LDB_FLG_NOSYNC, NULL); if (!ldb) { unlink("./test.ldb"); talloc_free(tmp_ctx); torture_fail(torture, "Failed to open test.ldb"); } /* add an index */ ldif = ldb_ldif_read_string(ldb, &init_ldif); if (ldif == NULL) goto failed; if (ldb_add(ldb, ldif->msg) != LDB_SUCCESS) goto failed; talloc_free(ldif); torture_comment(torture, "Adding %d SID records\n", torture_entries); for (i=0;i<torture_entries;i++) { if (!ldb_add_record(ldb, i)) { torture_result(torture, TORTURE_FAIL, "Failed to add SID %d\n", i); goto failed; } } if (talloc_total_blocks(torture) > 100) { torture_result(torture, TORTURE_FAIL, "memory leak in ldb add\n"); goto failed; } torture_comment(torture, "Testing for %d seconds\n", timelimit); tv = timeval_current(); for (count=0;timeval_elapsed(&tv) < timelimit;count++) { struct ldb_dn *dn; struct ldb_result *res; i = random() % torture_entries; dn = ldb_dn_new_fmt(tmp_ctx, ldb, "SID=S-1-5-21-53173311-3623041448-2049097239-%u", i); if (ldb_search(ldb, tmp_ctx, &res, dn, LDB_SCOPE_BASE, NULL, NULL) != LDB_SUCCESS || res->count != 1) { torture_fail(torture, talloc_asprintf(torture, "Failed to find SID %d", i)); } talloc_free(res); talloc_free(dn); if (ldb_search(ldb, tmp_ctx, &res, NULL, LDB_SCOPE_SUBTREE, NULL, "(UID=%u)", i) != LDB_SUCCESS || res->count != 1) { torture_fail(torture, talloc_asprintf(torture, "Failed to find UID %d", i)); } talloc_free(res); } if (talloc_total_blocks(torture) > 100) { unlink("./test.ldb"); talloc_free(tmp_ctx); torture_fail(torture, "memory leak in ldb search"); } ldb_speed = count/timeval_elapsed(&tv); torture_comment(torture, "ldb speed %.2f ops/sec\n", ldb_speed); torture_comment(torture, "ldb/tdb speed ratio is %.2f%%\n", (100*ldb_speed/tdb_speed)); unlink("./test.ldb"); talloc_free(tmp_ctx); return true; failed: unlink("./test.ldb"); talloc_free(tmp_ctx); return false; }
int confdb_init_db(const char *config_file, struct confdb_ctx *cdb) { TALLOC_CTX *tmp_ctx; int ret; int sret = EOK; int version; char timestr[21]; char *lasttimestr; bool in_transaction = false; const char *config_ldif; const char *vals[2] = { timestr, NULL }; struct ldb_ldif *ldif; struct sss_ini_initdata *init_data; tmp_ctx = talloc_new(cdb); if (tmp_ctx == NULL) { DEBUG(SSSDBG_FATAL_FAILURE, "Out of memory.\n"); return ENOMEM; } init_data = sss_ini_initdata_init(tmp_ctx); if (!init_data) { DEBUG(SSSDBG_FATAL_FAILURE, "Out of memory.\n"); ret = ENOMEM; goto done; } /* Open config file */ ret = sss_ini_config_file_open(init_data, config_file); if (ret != EOK) { DEBUG(SSSDBG_TRACE_FUNC, "sss_ini_config_file_open failed: %s [%d]\n", strerror(ret), ret); if (ret == ENOENT) { /* sss specific error denoting missing configuration file */ ret = ERR_MISSING_CONF; } goto done; } ret = sss_ini_config_access_check(init_data); if (ret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "Permission check on config file failed.\n"); ret = EPERM; goto done; } /* Determine if the conf file has changed since we last updated * the confdb */ ret = sss_ini_get_stat(init_data); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Status check on config file failed.\n"); ret = errno; goto done; } errno = 0; ret = sss_ini_get_mtime(init_data, sizeof(timestr), timestr); if (ret <= 0 || ret >= sizeof(timestr)) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to convert time_t to string ??\n"); ret = errno ? errno : EFAULT; } ret = confdb_get_string(cdb, tmp_ctx, "config", "lastUpdate", NULL, &lasttimestr); if (ret == EOK) { /* check if we lastUpdate and last file modification change differ*/ if ((lasttimestr != NULL) && (strcmp(lasttimestr, timestr) == 0)) { /* not changed, get out, nothing more to do */ ret = EOK; goto done; } } else { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to get lastUpdate attribute.\n"); goto done; } ret = sss_ini_get_config(init_data, config_file); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to load configuration\n"); goto done; } /* Make sure that the config file version matches the confdb version */ ret = sss_ini_get_cfgobj(init_data, "sssd", "config_file_version"); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Internal error determining config_file_version\n"); goto done; } ret = sss_ini_check_config_obj(init_data); if (ret != EOK) { /* No known version. Assumed to be version 1 */ DEBUG(SSSDBG_FATAL_FAILURE, "Config file is an old version. " "Please run configuration upgrade script.\n"); ret = EINVAL; goto done; } version = sss_ini_get_int_config_value(init_data, 1, -1, &ret); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Config file version could not be determined\n"); goto done; } else if (version < CONFDB_VERSION_INT) { DEBUG(SSSDBG_FATAL_FAILURE, "Config file is an old version. " "Please run configuration upgrade script.\n"); ret = EINVAL; goto done; } else if (version > CONFDB_VERSION_INT) { DEBUG(SSSDBG_FATAL_FAILURE, "Config file version is newer than confdb\n"); ret = EINVAL; goto done; } /* Set up a transaction to replace the configuration */ ret = ldb_transaction_start(cdb->ldb); if (ret != LDB_SUCCESS) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to start a transaction for " "updating the configuration\n"); ret = sysdb_error_to_errno(ret); goto done; } in_transaction = true; /* Purge existing database */ ret = confdb_purge(cdb); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Could not purge existing configuration\n"); goto done; } ret = sss_confdb_create_ldif(tmp_ctx, init_data, &config_ldif); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Could not create LDIF for confdb\n"); goto done; } DEBUG(SSSDBG_TRACE_LIBS, "LDIF file to import: \n%s", config_ldif); while ((ldif = ldb_ldif_read_string(cdb->ldb, &config_ldif))) { ret = ldb_add(cdb->ldb, ldif->msg); if (ret != LDB_SUCCESS) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to initialize DB (%d,[%s]), aborting!\n", ret, ldb_errstring(cdb->ldb)); ret = EIO; goto done; } ldb_ldif_read_free(cdb->ldb, ldif); } /* now store the lastUpdate time so that we do not re-init if nothing * changed on restart */ ret = confdb_add_param(cdb, true, "config", "lastUpdate", vals); if (ret != EOK) { DEBUG(SSSDBG_FATAL_FAILURE, "Failed to set last update time on db!\n"); goto done; } ret = ldb_transaction_commit(cdb->ldb); if (ret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "Failed to commit transaction\n"); goto done; } in_transaction = false; ret = EOK; done: if (in_transaction) { sret = ldb_transaction_cancel(cdb->ldb); if (sret != EOK) { DEBUG(SSSDBG_CRIT_FAILURE, "Failed to cancel transaction\n"); } } sss_ini_config_destroy(init_data); sss_ini_close_file(init_data); talloc_zfree(tmp_ctx); return ret; }
WERROR dsdb_set_schema_from_ldif(struct ldb_context *ldb, const char *pf, const char *df) { struct ldb_ldif *ldif; struct ldb_message *msg; TALLOC_CTX *mem_ctx; WERROR status; int ret; struct dsdb_schema *schema; const struct ldb_val *prefix_val; const struct ldb_val *info_val; struct ldb_val info_val_default; mem_ctx = talloc_new(ldb); if (!mem_ctx) { goto nomem; } schema = dsdb_new_schema(mem_ctx, lp_iconv_convenience(ldb_get_opaque(ldb, "loadparm"))); schema->fsmo.we_are_master = true; schema->fsmo.master_dn = ldb_dn_new_fmt(schema, ldb, "@PROVISION_SCHEMA_MASTER"); if (!schema->fsmo.master_dn) { goto nomem; } /* * load the prefixMap attribute from pf */ ldif = ldb_ldif_read_string(ldb, &pf); if (!ldif) { status = WERR_INVALID_PARAM; goto failed; } talloc_steal(mem_ctx, ldif); msg = ldb_msg_canonicalize(ldb, ldif->msg); if (!msg) { goto nomem; } talloc_steal(mem_ctx, msg); talloc_free(ldif); prefix_val = ldb_msg_find_ldb_val(msg, "prefixMap"); if (!prefix_val) { status = WERR_INVALID_PARAM; goto failed; } info_val = ldb_msg_find_ldb_val(msg, "schemaInfo"); if (!info_val) { info_val_default = strhex_to_data_blob(mem_ctx, "FF0000000000000000000000000000000000000000"); if (!info_val_default.data) { goto nomem; } info_val = &info_val_default; } status = dsdb_load_oid_mappings_ldb(schema, prefix_val, info_val); if (!W_ERROR_IS_OK(status)) { goto failed; } /* * load the attribute and class definitions outof df */ while ((ldif = ldb_ldif_read_string(ldb, &df))) { talloc_steal(mem_ctx, ldif); msg = ldb_msg_canonicalize(ldb, ldif->msg); if (!msg) { goto nomem; } status = dsdb_schema_set_el_from_ldb_msg(ldb, schema, msg); talloc_free(ldif); if (!W_ERROR_IS_OK(status)) { goto failed; } } ret = dsdb_set_schema(ldb, schema); if (ret != LDB_SUCCESS) { status = WERR_FOOBAR; goto failed; } ret = dsdb_schema_fill_extended_dn(ldb, schema); if (ret != LDB_SUCCESS) { status = WERR_FOOBAR; goto failed; } goto done; nomem: status = WERR_NOMEM; failed: done: talloc_free(mem_ctx); return status; }
/* connect to the group mapping ldb */ static bool init_group_mapping(void) { bool existed; const char *init_ldif[] = { "dn: @ATTRIBUTES\n" \ "ntName: CASE_INSENSITIVE\n" \ "\n", "dn: @INDEXLIST\n" \ "@IDXATTR: gidNumber\n" \ "@IDXATTR: ntName\n" \ "@IDXATTR: member\n" }; const char *db_path, *tdb_path; int ret; int flags = 0; if (ldb != NULL) { return True; } /* this is needed as Samba3 doesn't have this globally yet */ ldb_global_init(); db_path = state_path("group_mapping.ldb"); ldb = ldb_init(NULL); if (ldb == NULL) goto failed; /* Ensure this db is created read/write for root only. */ ldb_set_create_perms(ldb, 0600); existed = file_exist(db_path, NULL); if (lp_parm_bool(-1, "groupmap", "nosync", False)) { flags |= LDB_FLG_NOSYNC; } if (!lp_use_mmap()) { flags |= LDB_FLG_NOMMAP; } ret = ldb_connect(ldb, db_path, flags, NULL); if (ret != LDB_SUCCESS) { goto failed; } /* force the permissions on the ldb to 0600 - this will fix existing databases as well as new ones */ if (chmod(db_path, 0600) != 0) { goto failed; } if (!existed) { /* initialise the ldb with an index */ struct ldb_ldif *ldif; int i; for (i=0;i<ARRAY_SIZE(init_ldif);i++) { ldif = ldb_ldif_read_string(ldb, &init_ldif[i]); if (ldif == NULL) goto failed; ret = ldb_add(ldb, ldif->msg); talloc_free(ldif); if (ret == -1) goto failed; } } /* possibly upgrade */ tdb_path = state_path("group_mapping.tdb"); if (file_exist(tdb_path, NULL) && !mapping_upgrade(tdb_path)) { unlink(state_path("group_mapping.ldb")); goto failed; } return True; failed: DEBUG(0,("Failed to open group mapping ldb '%s' - '%s'\n", db_path, ldb?ldb_errstring(ldb):strerror(errno))); talloc_free(ldb); ldb = NULL; return False; }