[systemd-commits] 3 commits - src/journal

Lennart Poettering lennart at kemper.freedesktop.org
Thu Aug 16 12:01:24 PDT 2012


 src/journal/journal-authenticate.c |   54 +++++++++++----------------
 src/journal/journal-def.h          |    1 
 src/journal/journal-file.c         |   11 ++++-
 src/journal/journal-file.h         |   13 +++++-
 src/journal/journal-verify.c       |   73 ++++++++++++++++++++++++++++++++++++-
 src/journal/journalctl.c           |    9 +++-
 6 files changed, 122 insertions(+), 39 deletions(-)

New commits:
commit 56e81f7ca8276e40f8c88c4c30713a5b54009613
Author: Lennart Poettering <lennart at poettering.net>
Date:   Thu Aug 16 21:00:34 2012 +0200

    journalctl: immeidately terminate on invalid seed

diff --git a/src/journal/journal-verify.c b/src/journal/journal-verify.c
index f6cec1e..6871433 100644
--- a/src/journal/journal-verify.c
+++ b/src/journal/journal-verify.c
@@ -667,7 +667,7 @@ int journal_file_verify(JournalFile *f, const char *seed) {
                 r = journal_file_parse_seed(f, seed);
                 if (r < 0) {
                         log_error("Failed to parse seed.");
-                        goto fail;
+                        return r;
                 }
         }
 
diff --git a/src/journal/journalctl.c b/src/journal/journalctl.c
index 3d274c8..25e441b 100644
--- a/src/journal/journalctl.c
+++ b/src/journal/journalctl.c
@@ -601,13 +601,18 @@ static int verify(sd_journal *j) {
         HASHMAP_FOREACH(f, j->files, i) {
                 int k;
 
+#ifdef HAVE_GCRYPT
                 if (!arg_verify_seed && journal_file_fsprg_enabled(f))
                         log_warning("Journal file %s has authentication enabled but verification seed has not been passed using --verify-seed=.", f->path);
+#endif
 
                 k = journal_file_verify(f, arg_verify_seed);
-                if (k < 0) {
+                if (k == -EINVAL) {
+                        /* If the seed was invalid give up right-away. */
+                        return k;
+                } else if (k < 0) {
                         log_warning("FAIL: %s (%s)", f->path, strerror(-k));
-                        r = -r;
+                        r = k;
                 } else
                         log_info("PASS: %s", f->path);
         }

commit b7c9ae91d111b3e89d1ffc00e08f9ed97a8ff5db
Author: Lennart Poettering <lennart at poettering.net>
Date:   Thu Aug 16 20:51:43 2012 +0200

    journal: parse fsprg seed

diff --git a/src/journal/journal-authenticate.c b/src/journal/journal-authenticate.c
index 5a0314b..809655e 100644
--- a/src/journal/journal-authenticate.c
+++ b/src/journal/journal-authenticate.c
@@ -27,22 +27,6 @@
 #include "journal-authenticate.h"
 #include "fsprg.h"
 
-static void *fsprg_state(JournalFile *f) {
-        uint64_t a, b;
-        assert(f);
-
-        if (!f->authenticate)
-                return NULL;
-
-        a = le64toh(f->fsprg_header->header_size);
-        b = le64toh(f->fsprg_header->state_size);
-
-        if (a + b > f->fsprg_size)
-                return NULL;
-
-        return (uint8_t*) f->fsprg_header + a;
-}
-
 static uint64_t journal_file_tag_seqnum(JournalFile *f) {
         uint64_t r;
 
@@ -67,7 +51,7 @@ int journal_file_append_tag(JournalFile *f) {
         if (!f->hmac_running)
                 return 0;
 
-        log_debug("Writing tag for epoch %llu\n", (unsigned long long) FSPRG_GetEpoch(fsprg_state(f)));
+        log_debug("Writing tag for epoch %llu\n", (unsigned long long) FSPRG_GetEpoch(f->fsprg_state));
 
         assert(f->hmac);
 
@@ -103,7 +87,7 @@ static int journal_file_hmac_start(JournalFile *f) {
 
         /* Prepare HMAC for next cycle */
         gcry_md_reset(f->hmac);
-        FSPRG_GetKey(fsprg_state(f), key, sizeof(key), 0);
+        FSPRG_GetKey(f->fsprg_state, key, sizeof(key), 0);
         gcry_md_setkey(f->hmac, key, sizeof(key));
 
         f->hmac_running = true;
@@ -118,15 +102,15 @@ static int journal_file_get_epoch(JournalFile *f, uint64_t realtime, uint64_t *e
         assert(epoch);
         assert(f->authenticate);
 
-        if (le64toh(f->fsprg_header->fsprg_start_usec) == 0 ||
-            le64toh(f->fsprg_header->fsprg_interval_usec) == 0)
+        if (f->fsprg_start_usec == 0 ||
+            f->fsprg_interval_usec == 0)
                 return -ENOTSUP;
 
-        if (realtime < le64toh(f->fsprg_header->fsprg_start_usec))
+        if (realtime < f->fsprg_start_usec)
                 return -ESTALE;
 
-        t = realtime - le64toh(f->fsprg_header->fsprg_start_usec);
-        t = t / le64toh(f->fsprg_header->fsprg_interval_usec);
+        t = realtime - f->fsprg_start_usec;
+        t = t / f->fsprg_interval_usec;
 
         *epoch = t;
         return 0;
@@ -144,7 +128,7 @@ static int journal_file_need_evolve(JournalFile *f, uint64_t realtime) {
         if (r < 0)
                 return r;
 
-        epoch = FSPRG_GetEpoch(fsprg_state(f));
+        epoch = FSPRG_GetEpoch(f->fsprg_state);
         if (epoch > goal)
                 return -ESTALE;
 
@@ -164,7 +148,7 @@ static int journal_file_evolve(JournalFile *f, uint64_t realtime) {
         if (r < 0)
                 return r;
 
-        epoch = FSPRG_GetEpoch(fsprg_state(f));
+        epoch = FSPRG_GetEpoch(f->fsprg_state);
         if (epoch < goal)
                 log_debug("Evolving FSPRG key from epoch %llu to %llu.", (unsigned long long) epoch, (unsigned long long) goal);
 
@@ -174,8 +158,8 @@ static int journal_file_evolve(JournalFile *f, uint64_t realtime) {
                 if (epoch == goal)
                         return 0;
 
-                FSPRG_Evolve(fsprg_state(f));
-                epoch = FSPRG_GetEpoch(fsprg_state(f));
+                FSPRG_Evolve(f->fsprg_state);
+                epoch = FSPRG_GetEpoch(f->fsprg_state);
         }
 }
 
@@ -345,8 +329,8 @@ int journal_file_load_fsprg(JournalFile *f) {
                 goto finish;
         }
 
-        f->fsprg_size = le64toh(m->header_size) + le64toh(m->state_size);
-        if ((uint64_t) st.st_size < f->fsprg_size) {
+        f->fsprg_file_size = le64toh(m->header_size) + le64toh(m->state_size);
+        if ((uint64_t) st.st_size < f->fsprg_file_size) {
                 r = -ENODATA;
                 goto finish;
         }
@@ -362,13 +346,19 @@ int journal_file_load_fsprg(JournalFile *f) {
                 goto finish;
         }
 
-        f->fsprg_header = mmap(NULL, PAGE_ALIGN(f->fsprg_size), PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
-        if (f->fsprg_header == MAP_FAILED) {
-                f->fsprg_header = NULL;
+        f->fsprg_file = mmap(NULL, PAGE_ALIGN(f->fsprg_file_size), PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0);
+        if (f->fsprg_file == MAP_FAILED) {
+                f->fsprg_file = NULL;
                 r = -errno;
                 goto finish;
         }
 
+        f->fsprg_start_usec = le64toh(f->fsprg_file->fsprg_start_usec);
+        f->fsprg_interval_usec = le64toh(f->fsprg_file->fsprg_interval_usec);
+
+        f->fsprg_state = (uint8_t*) f->fsprg_file + le64toh(f->fsprg_file->header_size);
+        f->fsprg_state_size = le64toh(f->fsprg_file->state_size);
+
         r = 0;
 
 finish:
diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 81952a0..3bb1e90 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -96,8 +96,12 @@ void journal_file_close(JournalFile *f) {
 #endif
 
 #ifdef HAVE_GCRYPT
-        if (f->fsprg_header)
-                munmap(f->fsprg_header, PAGE_ALIGN(f->fsprg_size));
+        if (f->fsprg_file)
+                munmap(f->fsprg_file, PAGE_ALIGN(f->fsprg_file_size));
+        else if (f->fsprg_state)
+                free(f->fsprg_state);
+
+        free(f->fsprg_seed);
 
         if (f->hmac)
                 gcry_md_close(f->hmac);
diff --git a/src/journal/journal-file.h b/src/journal/journal-file.h
index 1da1d3b..9d437ae 100644
--- a/src/journal/journal-file.h
+++ b/src/journal/journal-file.h
@@ -73,8 +73,17 @@ typedef struct JournalFile {
         gcry_md_hd_t hmac;
         bool hmac_running;
 
-        FSPRGHeader *fsprg_header;
-        size_t fsprg_size;
+        FSPRGHeader *fsprg_file;
+        size_t fsprg_file_size;
+
+        void *fsprg_state;
+        size_t fsprg_state_size;
+
+        void *fsprg_seed;
+        size_t fsprg_seed_size;
+
+        uint64_t fsprg_start_usec;
+        uint64_t fsprg_interval_usec;
 #endif
 } JournalFile;
 
diff --git a/src/journal/journal-verify.c b/src/journal/journal-verify.c
index b4e34d1..f6cec1e 100644
--- a/src/journal/journal-verify.c
+++ b/src/journal/journal-verify.c
@@ -31,6 +31,7 @@
 #include "journal-verify.h"
 #include "lookup3.h"
 #include "compress.h"
+#include "fsprg.h"
 
 /* FIXME:
  *
@@ -591,7 +592,62 @@ static int verify_entry_array(
         return 0;
 }
 
-int journal_file_verify(JournalFile *f, const char *key) {
+static int journal_file_parse_seed(JournalFile *f, const char *s) {
+        uint8_t *seed;
+        size_t seed_size, c;
+        const char *k;
+        int r;
+        unsigned long long start, interval;
+
+        seed_size = FSPRG_RECOMMENDED_SEEDLEN;
+        seed = malloc(seed_size);
+        if (!seed)
+                return -ENOMEM;
+
+        k = s;
+        for (c = 0; c < seed_size; c++) {
+                int x, y;
+
+                while (*k == '-')
+                        k++;
+
+                x = unhexchar(*k);
+                if (x < 0) {
+                        free(seed);
+                        return -EINVAL;
+                }
+                k++;
+                y = unhexchar(*k);
+                if (y < 0) {
+                        free(seed);
+                        return -EINVAL;
+                }
+                k++;
+
+                seed[c] = (uint8_t) (x * 16 + y);
+        }
+
+        if (*k != '/') {
+                free(seed);
+                return -EINVAL;
+        }
+        k++;
+
+        r = sscanf(k, "%llx-%llx", &start, &interval);
+        if (r != 2) {
+                free(seed);
+                return -EINVAL;
+        }
+
+        f->fsprg_seed = seed;
+        f->fsprg_seed_size = seed_size;
+        f->fsprg_start_usec = start;
+        f->fsprg_interval_usec = interval;
+
+        return 0;
+}
+
+int journal_file_verify(JournalFile *f, const char *seed) {
         int r;
         Object *o;
         uint64_t p = 0;
@@ -607,6 +663,14 @@ int journal_file_verify(JournalFile *f, const char *key) {
 
         assert(f);
 
+        if (seed) {
+                r = journal_file_parse_seed(f, seed);
+                if (r < 0) {
+                        log_error("Failed to parse seed.");
+                        goto fail;
+                }
+        }
+
         data_fd = mkostemp(data_path, O_CLOEXEC);
         if (data_fd < 0) {
                 log_error("Failed to create data file: %m");

commit 2dee23ebe09965308c67a661ed0a8d2cc0ae1d5f
Author: Lennart Poettering <lennart at poettering.net>
Date:   Thu Aug 16 20:51:24 2012 +0200

    journal: count number of entry arrays in header

diff --git a/src/journal/journal-def.h b/src/journal/journal-def.h
index e61e81c..660a92c 100644
--- a/src/journal/journal-def.h
+++ b/src/journal/journal-def.h
@@ -185,6 +185,7 @@ _packed_ struct Header {
         le64_t n_fields;
         /* Added in 189 */
         le64_t n_tags;
+        le64_t n_entry_arrays;
 };
 
 #define FSPRG_HEADER_SIGNATURE ((char[]) { 'K', 'S', 'H', 'H', 'R', 'H', 'L', 'P' })
diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index e0b20cc..81952a0 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -839,6 +839,9 @@ static int link_entry_into_array(JournalFile *f,
                 o->entry_array.next_entry_array_offset = htole64(q);
         }
 
+        if (JOURNAL_HEADER_CONTAINS(f->header, n_entry_arrays))
+                f->header->n_entry_arrays = htole64(le64toh(f->header->n_entry_arrays) + 1);
+
         *idx = htole64(hidx + 1);
 
         return 0;
diff --git a/src/journal/journal-verify.c b/src/journal/journal-verify.c
index 55ca52a..b4e34d1 100644
--- a/src/journal/journal-verify.c
+++ b/src/journal/journal-verify.c
@@ -837,6 +837,13 @@ int journal_file_verify(JournalFile *f, const char *key) {
                 goto fail;
         }
 
+        if (JOURNAL_HEADER_CONTAINS(f->header, n_entry_arrays) &&
+            n_entry_arrays != le64toh(f->header->n_entry_arrays)) {
+                log_error("Entry array number mismatch");
+                r = -EBADMSG;
+                goto fail;
+        }
+
         if (n_data_hash_tables != 1) {
                 log_error("Missing data hash table");
                 r = -EBADMSG;



More information about the systemd-commits mailing list