Skip to content

Commit

Permalink
Simplify ulog_map
Browse files Browse the repository at this point in the history
Get rid of the caller parameter.  The kproplog semantics (without -R)
for mapping the ulog are simple and almost completely different from
other users of the ulog, so implement them as a static helper in
kproplog.  With hierarchical iprop, kpropd will need the same
semantics as FKCOMMAND and FKADMIND, which were already identical.

Get rid of the db_args parameter, since ulog_map no longer opens the
database after #7552.

Remove an inoperative lseek() call when creating a new ulog file.
Rename ulog_filesize to filesize and compute it from scratch each time
we use it, for easier analysis.  If kdb_hmagic is zero, init the ulog
header but don't skip the rest of the function; it's possible that we
need to expand the ulog file.  Remove an unneeded conditional before
calling extend_file_to for an existing ulog.

ticket: 7855
  • Loading branch information
greghudson committed Feb 21, 2014
1 parent 71d028f commit 6a4a4b7
Show file tree
Hide file tree
Showing 10 changed files with 61 additions and 123 deletions.
10 changes: 1 addition & 9 deletions src/include/kdb_log.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,14 +43,6 @@ extern "C" {
#define KDB_ULOG_MAGIC 0x6661212
#define KDB_ULOG_HDR_MAGIC 0x6662323

/*
* DB Flags
*/
#define FKADMIND 1
#define FKPROPLOG 2
#define FKPROPD 3
#define FKCOMMAND 4 /* Includes kadmin.local and kdb5_util */

/*
* Default ulog file attributes
*/
Expand All @@ -68,7 +60,7 @@ extern "C" {
* Prototype declarations
*/
krb5_error_code ulog_map(krb5_context context, const char *logname,
uint32_t entries, int caller, char **db_args);
uint32_t entries);
krb5_error_code ulog_init_header(krb5_context context);
krb5_error_code ulog_add_update(krb5_context context, kdb_incr_update_t *upd);
krb5_error_code ulog_get_entries(krb5_context context, const kdb_last_t *last,
Expand Down
2 changes: 1 addition & 1 deletion src/kadmin/dbutil/dump.c
Original file line number Diff line number Diff line change
Expand Up @@ -1570,7 +1570,7 @@ load_db(int argc, char **argv)

if (global_params.iprop_enabled &&
ulog_map(util_context, global_params.iprop_logfile,
global_params.iprop_ulogsize, FKCOMMAND, db5util_db_args)) {
global_params.iprop_ulogsize)) {
fprintf(stderr, _("Could not open iprop ulog\n"));
goto error;
}
Expand Down
6 changes: 3 additions & 3 deletions src/kadmin/dbutil/kdb5_create.c
Original file line number Diff line number Diff line change
Expand Up @@ -288,9 +288,9 @@ void kdb5_create(argc, argv)
/* } */

if (log_ctx && log_ctx->iproprole) {
if ((retval = ulog_map(util_context, global_params.iprop_logfile,
global_params.iprop_ulogsize, FKCOMMAND,
db5util_db_args))) {
retval = ulog_map(util_context, global_params.iprop_logfile,
global_params.iprop_ulogsize);
if (retval) {
com_err(argv[0], retval, _("while creating update log"));
exit_status++;
return;
Expand Down
3 changes: 1 addition & 2 deletions src/kadmin/dbutil/kdb5_util.c
Original file line number Diff line number Diff line change
Expand Up @@ -505,8 +505,7 @@ static int open_db_and_mkey()

if (global_params.iprop_enabled) {
if (ulog_map(util_context, global_params.iprop_logfile,
global_params.iprop_ulogsize, FKCOMMAND,
db5util_db_args)) {
global_params.iprop_ulogsize)) {
fprintf(stderr, _("%s: Could not map log\n"), progname);
exit_status++;
return(1);
Expand Down
3 changes: 1 addition & 2 deletions src/kadmin/server/ovsec_kadmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -508,8 +508,7 @@ main(int argc, char *argv[])
if (params.iprop_enabled == TRUE) {
ulog_set_role(context, IPROP_MASTER);

ret = ulog_map(context, params.iprop_logfile, params.iprop_ulogsize,
FKADMIND, db_args);
ret = ulog_map(context, params.iprop_logfile, params.iprop_ulogsize);
if (ret)
fail_to_start(ret, _("mapping update log"));

Expand Down
7 changes: 3 additions & 4 deletions src/lib/kadm5/srv/server_init.c
Original file line number Diff line number Diff line change
Expand Up @@ -431,10 +431,9 @@ kadm5_init_iprop(void *handle, char **db_args)
iprop_h = handle;
if (iprop_h->params.iprop_enabled) {
ulog_set_role(iprop_h->context, IPROP_MASTER);
if ((retval = ulog_map(iprop_h->context,
iprop_h->params.iprop_logfile,
iprop_h->params.iprop_ulogsize,
FKCOMMAND, db_args)) != 0)
retval = ulog_map(iprop_h->context, iprop_h->params.iprop_logfile,
iprop_h->params.iprop_ulogsize);
if (retval)
return (retval);
}
return (0);
Expand Down
95 changes: 15 additions & 80 deletions src/lib/kdb/kdb_log.c
Original file line number Diff line number Diff line change
Expand Up @@ -445,82 +445,32 @@ ulog_init_header(krb5_context context)
* Called by: if iprop_enabled then ulog_map();
* Assumes that the caller will terminate on ulog_map, hence munmap and
* closing of the fd are implicitly performed by the caller.
*
* Semantics for various values of caller:
*
* - FKPROPLOG
*
* Don't create if it doesn't exist, map as MAP_PRIVATE.
*
* - FKPROPD
*
* Create and initialize if need be, map as MAP_SHARED.
*
* - FKCOMMAND
*
* Create and [re-]initialize if need be, size appropriately, map as
* MAP_SHARED. (Intended for kdb5_util create and kdb5_util load of
* non-iprop dump.)
*
* - FKADMIN
*
* Create and [re-]initialize if need be, size appropriately, map as
* MAP_SHARED, and check consistency and recover as necessary. (Intended
* for kadmind and kadmin.local.)
*
* Returns 0 on success else failure.
*/
krb5_error_code
ulog_map(krb5_context context, const char *logname, uint32_t ulogentries,
int caller, char **db_args)
ulog_map(krb5_context context, const char *logname, uint32_t ulogentries)
{
struct stat st;
krb5_error_code retval;
uint32_t ulog_filesize;
uint32_t filesize;
kdb_log_context *log_ctx;
kdb_hlog_t *ulog = NULL;
int ulogfd = -1;

ulog_filesize = sizeof(kdb_hlog_t);

if (stat(logname, &st) == -1) {
/* File doesn't exist so we exit with kproplog. */
if (caller == FKPROPLOG)
return errno;

ulogfd = open(logname, O_RDWR | O_CREAT, 0600);
if (ulogfd == -1)
return errno;

if (lseek(ulogfd, 0L, SEEK_CUR) == -1)
return errno;

if (caller == FKADMIND || caller == FKCOMMAND)
ulog_filesize += ulogentries * ULOG_BLOCK;

if (extend_file_to(ulogfd, ulog_filesize) < 0)
filesize = sizeof(kdb_hlog_t) + ulogentries * ULOG_BLOCK;
if (extend_file_to(ulogfd, filesize) < 0)
return errno;
} else {
ulogfd = open(logname, O_RDWR, 0600);
if (ulogfd == -1)
return errno;
}

if (caller == FKPROPLOG) {
if (fstat(ulogfd, &st) < 0) {
close(ulogfd);
return errno;
}
ulog_filesize = st.st_size;

ulog = mmap(0, ulog_filesize, PROT_READ | PROT_WRITE, MAP_PRIVATE,
ulogfd, 0);
} else {
/* kadmind, kpropd, & kcommands should udpate stores. */
ulog = mmap(0, MAXLOGLEN, PROT_READ | PROT_WRITE, MAP_SHARED,
ulogfd, 0);
}

ulog = mmap(0, MAXLOGLEN, PROT_READ | PROT_WRITE, MAP_SHARED, ulogfd, 0);
if (ulog == MAP_FAILED) {
/* Can't map update log file to memory. */
close(ulogfd);
Expand All @@ -544,27 +494,15 @@ ulog_map(krb5_context context, const char *logname, uint32_t ulogentries,
if (retval)
return retval;

if (ulog->kdb_hmagic != KDB_ULOG_HDR_MAGIC && ulog->kdb_hmagic != 0) {
unlock_ulog(context);
return KRB5_LOG_CORRUPT;
}

if (ulog->kdb_hmagic != KDB_ULOG_HDR_MAGIC) {
if (ulog->kdb_hmagic != 0) {
unlock_ulog(context);
return KRB5_LOG_CORRUPT;
}
reset_header(ulog);
if (caller != FKPROPLOG)
sync_header(ulog);
unlock_ulog(context);
return 0;
}

if (caller == FKPROPLOG || caller == FKPROPD) {
/* kproplog and kpropd don't need to do anything else. */
unlock_ulog(context);
return 0;
sync_header(ulog);
}

assert(caller == FKADMIND || caller == FKCOMMAND);

/* Reinit ulog if the log is being truncated or expanded after we have
* circled. */
if (ulog->kdb_num != ulogentries) {
Expand All @@ -575,14 +513,11 @@ ulog_map(krb5_context context, const char *logname, uint32_t ulogentries,
sync_header(ulog);
}

/* Expand ulog if we have specified a greater size. */
if (ulog->kdb_num < ulogentries) {
ulog_filesize += ulogentries * ulog->kdb_block;

if (extend_file_to(ulogfd, ulog_filesize) < 0) {
unlock_ulog(context);
return errno;
}
/* Expand the ulog file if it isn't big enough. */
filesize = sizeof(kdb_hlog_t) + ulogentries * ulog->kdb_block;
if (extend_file_to(ulogfd, filesize) < 0) {
unlock_ulog(context);
return errno;
}
}
unlock_ulog(context);
Expand Down
2 changes: 1 addition & 1 deletion src/lib/kdb/t_ulog.c
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ main(int argc, char **argv)
filename = argv[1];
unlink(filename);

if (ulog_map(context, filename, 10, FKCOMMAND, NULL) != 0)
if (ulog_map(context, filename, 10) != 0)
abort();
lctx = context->kdblog_context;
ulog = lctx->ulog;
Expand Down
2 changes: 1 addition & 1 deletion src/slave/kpropd.c
Original file line number Diff line number Diff line change
Expand Up @@ -1172,7 +1172,7 @@ parse_args(char **argv)
ulog_set_role(kpropd_context, IPROP_SLAVE);

if (ulog_map(kpropd_context, params.iprop_logfile,
params.iprop_ulogsize, FKPROPD, db_args)) {
params.iprop_ulogsize)) {
com_err(progname, errno, _("Unable to map log!\n"));
exit(1);
}
Expand Down
54 changes: 34 additions & 20 deletions src/slave/kproplog.c
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
#include <locale.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/mman.h>
#include <time.h>
#include <limits.h>
#include <locale.h>
Expand Down Expand Up @@ -409,6 +410,24 @@ print_update(kdb_hlog_t *ulog, uint32_t entry, uint32_t ulogentries,
}
}

/* Return a read-only mmap of the ulog, or NULL on failure. Assumes fd is
* released on process exit. */
static kdb_hlog_t *
map_ulog(const char *filename)
{
int fd;
struct stat st;
kdb_hlog_t *ulog;

fd = open(filename, O_RDONLY);
if (fd == -1)
return NULL;
if (fstat(fd, &st) < 0)
return NULL;
ulog = mmap(0, st.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
return (ulog == MAP_FAILED) ? NULL : ulog;
}

int
main(int argc, char **argv)
{
Expand All @@ -418,7 +437,6 @@ main(int argc, char **argv)
uint32_t entry = 0;
krb5_context context;
kadm5_config_params params;
kdb_log_context *log_ctx;
kdb_hlog_t *ulog = NULL;

setlocale(LC_ALL, "");
Expand Down Expand Up @@ -458,17 +476,23 @@ main(int argc, char **argv)

printf(_("\nKerberos update log (%s)\n"), params.iprop_logfile);

if (ulog_map(context, params.iprop_logfile, 0,
reset ? FKADMIND : FKPROPLOG, NULL)) {
fprintf(stderr, _("Unable to map log file %s\n\n"),
params.iprop_logfile);
exit(1);
if (reset) {
if (ulog_map(context, params.iprop_logfile, params.iprop_ulogsize)) {
fprintf(stderr, _("Unable to map log file %s\n\n"),
params.iprop_logfile);
exit(1);
}
if (ulog_init_header(context) != 0) {
fprintf(stderr, _("Couldn't reinitialize ulog file %s\n\n"),
params.iprop_logfile);
exit(1);
}
printf(_("Reinitialized the ulog.\n"));
exit(0);
}

log_ctx = context->kdblog_context;
if (log_ctx) {
ulog = log_ctx->ulog;
} else {
ulog = map_ulog(params.iprop_logfile);
if (ulog == NULL) {
fprintf(stderr, _("Unable to map log file %s\n\n"),
params.iprop_logfile);
exit(1);
Expand All @@ -479,16 +503,6 @@ main(int argc, char **argv)
exit(1);
}

if (reset) {
if (ulog_init_header(context) != 0) {
fprintf(stderr, _("Couldn't reinitialize ulog file %s\n\n"),
params.iprop_logfile);
exit(1);
}
printf(_("Reinitialized the ulog.\n"));
exit(0);
}

printf(_("Update log dump :\n"));
printf(_("\tLog version # : %u\n"), ulog->db_version_num);
printf(_("\tLog state : "));
Expand Down

0 comments on commit 6a4a4b7

Please sign in to comment.