diff options
-rw-r--r-- | source3/utils/net_idmap.c | 182 |
1 files changed, 130 insertions, 52 deletions
diff --git a/source3/utils/net_idmap.c b/source3/utils/net_idmap.c index d145693a22..46014cab7c 100644 --- a/source3/utils/net_idmap.c +++ b/source3/utils/net_idmap.c @@ -90,29 +90,100 @@ static int net_idmap_dump(struct net_context *c, int argc, const char **argv) Write entries from stdin to current local idmap **********************************************************/ +static int net_idmap_store_id_mapping(struct db_context *db, + enum id_type type, + unsigned long idval, + const char *sid_string) +{ + NTSTATUS status; + char *idstr = NULL; + + switch(type) { + case ID_TYPE_UID: + idstr = talloc_asprintf(talloc_tos(), "UID %lu", idval); + break; + case ID_TYPE_GID: + idstr = talloc_asprintf(talloc_tos(), "GID %lu", idval); + break; + default: + d_fprintf(stderr, "Invalid id mapping type: %d\n", type); + return -1; + } + + status = dbwrap_store_bystring(db, idstr, + string_term_tdb_data(sid_string), + TDB_REPLACE); + if (!NT_STATUS_IS_OK(status)) { + d_fprintf(stderr, "Error storing ID -> SID: " + "%s\n", nt_errstr(status)); + talloc_free(idstr); + return -1; + } + status = dbwrap_store_bystring(db, sid_string, + string_term_tdb_data(idstr), + TDB_REPLACE); + if (!NT_STATUS_IS_OK(status)) { + d_fprintf(stderr, "Error storing SID -> ID: " + "%s\n", nt_errstr(status)); + talloc_free(idstr); + return -1; + } + + return 0; +} + static int net_idmap_restore(struct net_context *c, int argc, const char **argv) { - TALLOC_CTX *ctx; - FILE *input; + TALLOC_CTX *mem_ctx; + FILE *input = NULL; + struct db_context *db; + char *dbfile = NULL; + int ret = 0; if (c->display_usage) { d_printf("%s\n%s", _("Usage:"), - _("net idmap restore [inputfile]\n" + _("net idmap restore [<inputfile>]\n" " Restore ID mappings from file\n" - " inputfile\tFile to load ID mappings from. If " - "not given, load data from stdin.\n")); + " inputfile\tFile to load ID mappings from. If not " + "given, load data from stdin.\n")); return 0; } - if (! winbind_ping()) { - d_fprintf(stderr, - _("To use net idmap Winbindd must be running.\n")); - return -1; + mem_ctx = talloc_stackframe(); + + if (strequal(lp_idmap_backend(), "tdb")) { + dbfile = state_path("winbindd_idmap.tdb"); + if (dbfile == NULL) { + d_fprintf(stderr, _("Out of memory!\n")); + return -1; + } + } else if (strequal(lp_idmap_backend(), "tdb2")) { + dbfile = lp_parm_talloc_string(-1, "tdb", "idmap2.tdb", NULL); + if (dbfile == NULL) { + dbfile = talloc_asprintf(mem_ctx, "%s/idmap2.tdb", + lp_private_dir()); + } + } else { + char *backend, *args; + + backend = talloc_strdup(mem_ctx, lp_idmap_backend()); + args = strchr(backend, ':'); + if (args != NULL) { + *args = '\0'; + } + + d_printf(_("Sorry, 'net idmap restore' is currently not " + "supported for idmap backend = %s.\n" + "Only tdb and tdb2 are supported.\n"), + backend); + + ret = -1; + goto done; } - ctx = talloc_new(NULL); - ALLOC_CHECK(ctx); + d_fprintf(stderr, _("restoring id mapping to %s data base in '%s'\n"), + lp_idmap_backend(), dbfile); if (argc == 1) { input = fopen(argv[0], "r"); @@ -120,13 +191,24 @@ static int net_idmap_restore(struct net_context *c, int argc, const char **argv) input = stdin; } + db = db_open(mem_ctx, dbfile, 0, TDB_DEFAULT, O_RDWR|O_CREAT, 0644); + if (db == NULL) { + d_fprintf(stderr, _("Could not open idmap db (%s): %s\n"), + dbfile, strerror(errno)); + ret = -1; + goto done; + } + + if (db->transaction_start(db) != 0) { + d_fprintf(stderr, _("Failed to start transaction.\n")); + ret = -1; + goto done; + } + while (!feof(input)) { char line[128], sid_string[128]; int len; - struct wbcDomainSid sid; - enum id_type type = ID_TYPE_NOT_SPECIFIED; unsigned long idval; - wbcErr wbc_status; if (fgets(line, 127, input) == NULL) break; @@ -136,62 +218,58 @@ static int net_idmap_restore(struct net_context *c, int argc, const char **argv) if ( (len > 0) && (line[len-1] == '\n') ) line[len-1] = '\0'; - if (sscanf(line, "GID %lu %128s", &idval, sid_string) == 2) { - type = ID_TYPE_GID; - } else if (sscanf(line, "UID %lu %128s", &idval, sid_string) == 2) { - type = ID_TYPE_UID; + if (sscanf(line, "GID %lu %128s", &idval, sid_string) == 2) + { + ret = net_idmap_store_id_mapping(db, ID_TYPE_GID, + idval, sid_string); + if (ret != 0) { + break; + } + } else if (sscanf(line, "UID %lu %128s", &idval, sid_string) == 2) + { + ret = net_idmap_store_id_mapping(db, ID_TYPE_UID, + idval, sid_string); + if (ret != 0) { + break; + } } else if (sscanf(line, "USER HWM %lu", &idval) == 1) { - /* set uid hwm */ - wbc_status = wbcSetUidHwm(idval); - if (!WBC_ERROR_IS_OK(wbc_status)) { - d_fprintf(stderr, - _("Could not set USER HWM: %s\n"), - wbcErrorString(wbc_status)); + ret = dbwrap_store_int32(db, "USER HWM", idval); + if (ret != 0) { + d_fprintf(stderr, _("Could not store USER HWM.\n")); + break; } - continue; } else if (sscanf(line, "GROUP HWM %lu", &idval) == 1) { - /* set gid hwm */ - wbc_status = wbcSetGidHwm(idval); - if (!WBC_ERROR_IS_OK(wbc_status)) { + ret = dbwrap_store_int32(db, "GROUP HWM", idval); + if (ret != 0) { d_fprintf(stderr, - _("Could not set GROUP HWM: %s\n"), - wbcErrorString(wbc_status)); + _("Could not store GROUP HWM.\n")); + break; } - continue; } else { d_fprintf(stderr, _("ignoring invalid line [%s]\n"), line); continue; } + } - wbc_status = wbcStringToSid(sid_string, &sid); - if (!WBC_ERROR_IS_OK(wbc_status)) { - d_fprintf(stderr, _("ignoring invalid sid [%s]: %s\n"), - sid_string, wbcErrorString(wbc_status)); - continue; - } - - if (type == ID_TYPE_UID) { - wbc_status = wbcSetUidMapping(idval, &sid); - } else { - wbc_status = wbcSetGidMapping(idval, &sid); + if (ret == 0) { + if(db->transaction_commit(db) != 0) { + d_fprintf(stderr, _("Failed to commit transaction.\n")); + ret = -1; } - if (!WBC_ERROR_IS_OK(wbc_status)) { - d_fprintf(stderr, - _("Could not set mapping of %s %lu to sid %s: %s\n"), - (type == ID_TYPE_GID) ? "GID" : "UID", - idval, sid_string, - wbcErrorString(wbc_status)); - continue; + } else { + if (db->transaction_cancel(db) != 0) { + d_fprintf(stderr, _("Failed to cancel transaction.\n")); } } - if (input != stdin) { +done: + if ((input != NULL) && (input != stdin)) { fclose(input); } - talloc_free(ctx); - return 0; + talloc_free(mem_ctx); + return ret; } /*********************************************************** |