[systemd-commits] 12 commits - configure.ac src/journal src/shared

Michal Schmidt michich at kemper.freedesktop.org
Fri Dec 12 15:48:41 PST 2014


 configure.ac                       |   38 ++++++++--
 src/journal/journal-authenticate.c |    4 -
 src/journal/journal-authenticate.h |    2 
 src/journal/journal-def.h          |    6 -
 src/journal/journal-file.c         |   26 ++++---
 src/journal/journal-file.h         |   22 ------
 src/journal/journal-verify.c       |   10 +-
 src/journal/mmap-cache.c           |  134 +++++++++++--------------------------
 src/journal/mmap-cache.h           |   10 --
 src/journal/sd-journal.c           |   15 ----
 src/journal/test-mmap-cache.c      |   10 +-
 src/shared/hashmap.c               |   24 +++---
 src/shared/hashmap.h               |    8 +-
 13 files changed, 130 insertions(+), 179 deletions(-)

New commits:
commit 69adae5168da231c6cf319f708860954701b25ed
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Wed Dec 3 18:25:44 2014 +0100

    journal: replace contexts hashmap with a plain array
    
    try_context() is such a hot path that the hashmap lookup is expensive.
    
    The number of contexts is small - it is the number of object types.
    Using a hashmap is overkill. A plain array will do.
    
    Before:
    $ time ./journalctl --since=2014-06-01 --until=2014-07-01 > /dev/null
    
    real    0m9.445s
    user    0m9.228s
    sys     0m0.213s
    
    After:
    $ time ./journalctl --since=2014-06-01 --until=2014-07-01 > /dev/null
    real    0m5.438s
    user    0m5.266s
    sys     0m0.170s

diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 82e50fc..7cdaf29 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -376,6 +376,7 @@ static int journal_file_allocate(JournalFile *f, uint64_t offset, uint64_t size)
 
 static unsigned type_to_context(ObjectType type) {
         /* One context for each type, plus one catch-all for the rest */
+        assert_cc(_OBJECT_TYPE_MAX <= MMAP_CACHE_MAX_CONTEXTS);
         return type > OBJECT_UNUSED && type < _OBJECT_TYPE_MAX ? type : 0;
 }
 
diff --git a/src/journal/mmap-cache.c b/src/journal/mmap-cache.c
index 949f978..4c940aa 100644
--- a/src/journal/mmap-cache.c
+++ b/src/journal/mmap-cache.c
@@ -76,7 +76,7 @@ struct MMapCache {
 
 
         Hashmap *fds;
-        Hashmap *contexts;
+        Context *contexts[MMAP_CACHE_MAX_CONTEXTS];
 
         LIST_HEAD(Window, unused);
         Window *last_unused;
@@ -231,18 +231,13 @@ static void context_attach_window(Context *c, Window *w) {
 
 static Context *context_add(MMapCache *m, unsigned id) {
         Context *c;
-        int r;
 
         assert(m);
 
-        c = hashmap_get(m->contexts, UINT_TO_PTR(id + 1));
+        c = m->contexts[id];
         if (c)
                 return c;
 
-        r = hashmap_ensure_allocated(&m->contexts, NULL);
-        if (r < 0)
-                return NULL;
-
         c = new0(Context, 1);
         if (!c)
                 return NULL;
@@ -250,11 +245,8 @@ static Context *context_add(MMapCache *m, unsigned id) {
         c->cache = m;
         c->id = id;
 
-        r = hashmap_put(m->contexts, UINT_TO_PTR(id + 1), c);
-        if (r < 0) {
-                free(c);
-                return NULL;
-        }
+        assert(!m->contexts[id]);
+        m->contexts[id] = c;
 
         return c;
 }
@@ -264,8 +256,10 @@ static void context_free(Context *c) {
 
         context_detach_window(c);
 
-        if (c->cache)
-                assert_se(hashmap_remove(c->cache->contexts, UINT_TO_PTR(c->id + 1)));
+        if (c->cache) {
+                assert(c->cache->contexts[c->id] == c);
+                c->cache->contexts[c->id] = NULL;
+        }
 
         free(c);
 }
@@ -314,15 +308,14 @@ static FileDescriptor* fd_add(MMapCache *m, int fd) {
 }
 
 static void mmap_cache_free(MMapCache *m) {
-        Context *c;
         FileDescriptor *f;
+        int i;
 
         assert(m);
 
-        while ((c = hashmap_first(m->contexts)))
-                context_free(c);
-
-        hashmap_free(m->contexts);
+        for (i = 0; i < MMAP_CACHE_MAX_CONTEXTS; i++)
+                if (m->contexts[i])
+                        context_free(m->contexts[i]);
 
         while ((f = hashmap_first(m->fds)))
                 fd_free(f);
@@ -374,7 +367,7 @@ static int try_context(
         assert(size > 0);
         assert(ret);
 
-        c = hashmap_get(m->contexts, UINT_TO_PTR(context+1));
+        c = m->contexts[context];
         if (!c)
                 return 0;
 
@@ -557,6 +550,7 @@ int mmap_cache_get(
         assert(fd >= 0);
         assert(size > 0);
         assert(ret);
+        assert(context < MMAP_CACHE_MAX_CONTEXTS);
 
         /* Check whether the current context is the right one already */
         r = try_context(m, fd, prot, context, keep_always, offset, size, ret);
diff --git a/src/journal/mmap-cache.h b/src/journal/mmap-cache.h
index 543a2bf..fe2c83d 100644
--- a/src/journal/mmap-cache.h
+++ b/src/journal/mmap-cache.h
@@ -25,6 +25,8 @@
 #include <stdbool.h>
 #include <sys/stat.h>
 
+#define MMAP_CACHE_MAX_CONTEXTS 8
+
 typedef struct MMapCache MMapCache;
 
 MMapCache* mmap_cache_new(void);

commit 634ed0ee3466e5e5f78d3acbe9782650ff456288
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Wed Dec 3 18:23:23 2014 +0100

    journal: delete unused function mmap_cache_close_context
    
    This never had any callers. Contexts are freed when the MMapCache is
    freed.

diff --git a/src/journal/mmap-cache.c b/src/journal/mmap-cache.c
index f34d260..949f978 100644
--- a/src/journal/mmap-cache.c
+++ b/src/journal/mmap-cache.c
@@ -591,18 +591,6 @@ void mmap_cache_close_fd(MMapCache *m, int fd) {
         fd_free(f);
 }
 
-void mmap_cache_close_context(MMapCache *m, unsigned context) {
-        Context *c;
-
-        assert(m);
-
-        c = hashmap_get(m->contexts, UINT_TO_PTR(context + 1));
-        if (!c)
-                return;
-
-        context_free(c);
-}
-
 unsigned mmap_cache_get_hit(MMapCache *m) {
         assert(m);
 
diff --git a/src/journal/mmap-cache.h b/src/journal/mmap-cache.h
index 3e2ffbb..543a2bf 100644
--- a/src/journal/mmap-cache.h
+++ b/src/journal/mmap-cache.h
@@ -42,7 +42,6 @@ int mmap_cache_get(
         struct stat *st,
         void **ret);
 void mmap_cache_close_fd(MMapCache *m, int fd);
-void mmap_cache_close_context(MMapCache *m, unsigned context);
 
 unsigned mmap_cache_get_hit(MMapCache *m);
 unsigned mmap_cache_get_missed(MMapCache *m);

commit 7a9dabea7eabd4dd87f8774234265590d34761da
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 23:20:05 2014 +0100

    journal: push type_to_context conversion down to journal_file_move_to()

diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 1d73be1..82e50fc 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -379,7 +379,7 @@ static unsigned type_to_context(ObjectType type) {
         return type > OBJECT_UNUSED && type < _OBJECT_TYPE_MAX ? type : 0;
 }
 
-static int journal_file_move_to(JournalFile *f, int context, bool keep_always, uint64_t offset, uint64_t size, void **ret) {
+static int journal_file_move_to(JournalFile *f, ObjectType type, bool keep_always, uint64_t offset, uint64_t size, void **ret) {
         assert(f);
         assert(ret);
 
@@ -396,7 +396,7 @@ static int journal_file_move_to(JournalFile *f, int context, bool keep_always, u
                         return -EADDRNOTAVAIL;
         }
 
-        return mmap_cache_get(f->mmap, f->fd, f->prot, context, keep_always, offset, size, &f->last_stat, ret);
+        return mmap_cache_get(f->mmap, f->fd, f->prot, type_to_context(type), keep_always, offset, size, &f->last_stat, ret);
 }
 
 static uint64_t minimum_header_size(Object *o) {
@@ -430,7 +430,7 @@ int journal_file_move_to_object(JournalFile *f, ObjectType type, uint64_t offset
         if (!VALID64(offset))
                 return -EFAULT;
 
-        r = journal_file_move_to(f, type_to_context(type), false, offset, sizeof(ObjectHeader), &t);
+        r = journal_file_move_to(f, type, false, offset, sizeof(ObjectHeader), &t);
         if (r < 0)
                 return r;
 
@@ -450,7 +450,7 @@ int journal_file_move_to_object(JournalFile *f, ObjectType type, uint64_t offset
                 return -EBADMSG;
 
         if (s > sizeof(ObjectHeader)) {
-                r = journal_file_move_to(f, type_to_context(type), false, offset, s, &t);
+                r = journal_file_move_to(f, type, false, offset, s, &t);
                 if (r < 0)
                         return r;
 

commit 7851983162ef851d5b9ce12bd88de86fc402f88a
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Wed Dec 10 15:18:49 2014 +0100

    journal: have a named enum ObjectType

diff --git a/src/journal/journal-authenticate.c b/src/journal/journal-authenticate.c
index 0e31c8d..b3e2601 100644
--- a/src/journal/journal-authenticate.c
+++ b/src/journal/journal-authenticate.c
@@ -229,7 +229,7 @@ int journal_file_maybe_append_tag(JournalFile *f, uint64_t realtime) {
         return 0;
 }
 
-int journal_file_hmac_put_object(JournalFile *f, int type, Object *o, uint64_t p) {
+int journal_file_hmac_put_object(JournalFile *f, ObjectType type, Object *o, uint64_t p) {
         int r;
 
         assert(f);
diff --git a/src/journal/journal-authenticate.h b/src/journal/journal-authenticate.h
index 0aaf836..565fe84 100644
--- a/src/journal/journal-authenticate.h
+++ b/src/journal/journal-authenticate.h
@@ -33,7 +33,7 @@ int journal_file_append_first_tag(JournalFile *f);
 int journal_file_hmac_setup(JournalFile *f);
 int journal_file_hmac_start(JournalFile *f);
 int journal_file_hmac_put_header(JournalFile *f);
-int journal_file_hmac_put_object(JournalFile *f, int type, Object *o, uint64_t p);
+int journal_file_hmac_put_object(JournalFile *f, ObjectType type, Object *o, uint64_t p);
 
 int journal_file_fss_load(JournalFile *f);
 int journal_file_parse_verification_key(JournalFile *f, const char *key);
diff --git a/src/journal/journal-def.h b/src/journal/journal-def.h
index 005e5fa..ab089cb 100644
--- a/src/journal/journal-def.h
+++ b/src/journal/journal-def.h
@@ -52,7 +52,7 @@ typedef struct HashItem HashItem;
 typedef struct FSSHeader FSSHeader;
 
 /* Object types */
-enum {
+typedef enum ObjectType {
         OBJECT_UNUSED, /* also serves as "any type" or "additional context" */
         OBJECT_DATA,
         OBJECT_FIELD,
@@ -62,7 +62,7 @@ enum {
         OBJECT_ENTRY_ARRAY,
         OBJECT_TAG,
         _OBJECT_TYPE_MAX
-};
+} ObjectType;
 
 /* Object flags */
 enum {
diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 6ee0fff..1d73be1 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -374,7 +374,7 @@ static int journal_file_allocate(JournalFile *f, uint64_t offset, uint64_t size)
         return 0;
 }
 
-static unsigned type_to_context(int type) {
+static unsigned type_to_context(ObjectType type) {
         /* One context for each type, plus one catch-all for the rest */
         return type > OBJECT_UNUSED && type < _OBJECT_TYPE_MAX ? type : 0;
 }
@@ -417,7 +417,7 @@ static uint64_t minimum_header_size(Object *o) {
         return table[o->object.type];
 }
 
-int journal_file_move_to_object(JournalFile *f, int type, uint64_t offset, Object **ret) {
+int journal_file_move_to_object(JournalFile *f, ObjectType type, uint64_t offset, Object **ret) {
         int r;
         void *t;
         Object *o;
@@ -487,7 +487,7 @@ static uint64_t journal_file_entry_seqnum(JournalFile *f, uint64_t *seqnum) {
         return r;
 }
 
-int journal_file_append_object(JournalFile *f, int type, uint64_t size, Object **ret, uint64_t *offset) {
+int journal_file_append_object(JournalFile *f, ObjectType type, uint64_t size, Object **ret, uint64_t *offset) {
         int r;
         uint64_t p;
         Object *tail, *o;
diff --git a/src/journal/journal-file.h b/src/journal/journal-file.h
index 5e8065c..a4a172b 100644
--- a/src/journal/journal-file.h
+++ b/src/journal/journal-file.h
@@ -160,13 +160,13 @@ static inline bool VALID_EPOCH(uint64_t u) {
 #define JOURNAL_HEADER_COMPRESSED_LZ4(h) \
         (!!(le32toh((h)->incompatible_flags) & HEADER_INCOMPATIBLE_COMPRESSED_LZ4))
 
-int journal_file_move_to_object(JournalFile *f, int type, uint64_t offset, Object **ret);
+int journal_file_move_to_object(JournalFile *f, ObjectType type, uint64_t offset, Object **ret);
 
 uint64_t journal_file_entry_n_items(Object *o) _pure_;
 uint64_t journal_file_entry_array_n_items(Object *o) _pure_;
 uint64_t journal_file_hash_table_n_items(Object *o) _pure_;
 
-int journal_file_append_object(JournalFile *f, int type, uint64_t size, Object **ret, uint64_t *offset);
+int journal_file_append_object(JournalFile *f, ObjectType type, uint64_t size, Object **ret, uint64_t *offset);
 int journal_file_append_entry(JournalFile *f, const dual_timestamp *ts, const struct iovec iovec[], unsigned n_iovec, uint64_t *seqno, Object **ret, uint64_t *offset);
 
 int journal_file_find_data_object(JournalFile *f, const void *data, uint64_t size, Object **ret, uint64_t *offset);

commit d05089d86ef032b245c7f928e623b88c82998ab0
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 22:51:24 2014 +0100

    journal: consistently use OBJECT_<type> names instead of numbers
    
    Note that numbers 0 and -1 are both replaced with OBJECT_UNUSED,
    because they are treated the same everywhere (e.g. type_to_context()
    translates them both to 0).

diff --git a/src/journal/journal-authenticate.c b/src/journal/journal-authenticate.c
index fd3b821..0e31c8d 100644
--- a/src/journal/journal-authenticate.c
+++ b/src/journal/journal-authenticate.c
@@ -246,7 +246,7 @@ int journal_file_hmac_put_object(JournalFile *f, int type, Object *o, uint64_t p
                 if (r < 0)
                         return r;
         } else {
-                if (type > 0 && o->object.type != type)
+                if (type > OBJECT_UNUSED && o->object.type != type)
                         return -EBADMSG;
         }
 
diff --git a/src/journal/journal-def.h b/src/journal/journal-def.h
index e55fa19..005e5fa 100644
--- a/src/journal/journal-def.h
+++ b/src/journal/journal-def.h
@@ -53,7 +53,7 @@ typedef struct FSSHeader FSSHeader;
 
 /* Object types */
 enum {
-        OBJECT_UNUSED,
+        OBJECT_UNUSED, /* also serves as "any type" or "additional context" */
         OBJECT_DATA,
         OBJECT_FIELD,
         OBJECT_ENTRY,
diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 4632326..6ee0fff 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -376,7 +376,7 @@ static int journal_file_allocate(JournalFile *f, uint64_t offset, uint64_t size)
 
 static unsigned type_to_context(int type) {
         /* One context for each type, plus one catch-all for the rest */
-        return type > 0 && type < _OBJECT_TYPE_MAX ? type : 0;
+        return type > OBJECT_UNUSED && type < _OBJECT_TYPE_MAX ? type : 0;
 }
 
 static int journal_file_move_to(JournalFile *f, int context, bool keep_always, uint64_t offset, uint64_t size, void **ret) {
@@ -446,7 +446,7 @@ int journal_file_move_to_object(JournalFile *f, int type, uint64_t offset, Objec
         if (s < minimum_header_size(o))
                 return -EBADMSG;
 
-        if (type > 0 && o->object.type != type)
+        if (type > OBJECT_UNUSED && o->object.type != type)
                 return -EBADMSG;
 
         if (s > sizeof(ObjectHeader)) {
@@ -494,7 +494,7 @@ int journal_file_append_object(JournalFile *f, int type, uint64_t size, Object *
         void *t;
 
         assert(f);
-        assert(type > 0 && type < _OBJECT_TYPE_MAX);
+        assert(type > OBJECT_UNUSED && type < _OBJECT_TYPE_MAX);
         assert(size >= sizeof(ObjectHeader));
         assert(offset);
         assert(ret);
@@ -507,7 +507,7 @@ int journal_file_append_object(JournalFile *f, int type, uint64_t size, Object *
         if (p == 0)
                 p = le64toh(f->header->header_size);
         else {
-                r = journal_file_move_to_object(f, -1, p, &tail);
+                r = journal_file_move_to_object(f, OBJECT_UNUSED, p, &tail);
                 if (r < 0)
                         return r;
 
@@ -2294,7 +2294,7 @@ void journal_file_dump(JournalFile *f) {
 
         p = le64toh(f->header->header_size);
         while (p != 0) {
-                r = journal_file_move_to_object(f, -1, p, &o);
+                r = journal_file_move_to_object(f, OBJECT_UNUSED, p, &o);
                 if (r < 0)
                         goto fail;
 
diff --git a/src/journal/journal-verify.c b/src/journal/journal-verify.c
index 75792a5..b03335e 100644
--- a/src/journal/journal-verify.c
+++ b/src/journal/journal-verify.c
@@ -865,7 +865,7 @@ int journal_file_verify(
                 if (show_progress)
                         draw_progress(0x7FFF * p / le64toh(f->header->tail_object_offset), &last_usec);
 
-                r = journal_file_move_to_object(f, -1, p, &o);
+                r = journal_file_move_to_object(f, OBJECT_UNUSED, p, &o);
                 if (r < 0) {
                         error(p, "invalid object");
                         goto fail;
@@ -1085,11 +1085,11 @@ int journal_file_verify(
                                         q = last_tag;
 
                                 while (q <= p) {
-                                        r = journal_file_move_to_object(f, -1, q, &o);
+                                        r = journal_file_move_to_object(f, OBJECT_UNUSED, q, &o);
                                         if (r < 0)
                                                 goto fail;
 
-                                        r = journal_file_hmac_put_object(f, -1, o, q);
+                                        r = journal_file_hmac_put_object(f, OBJECT_UNUSED, o, q);
                                         if (r < 0)
                                                 goto fail;
 
@@ -1097,7 +1097,7 @@ int journal_file_verify(
                                 }
 
                                 /* Position might have changed, let's reposition things */
-                                r = journal_file_move_to_object(f, -1, p, &o);
+                                r = journal_file_move_to_object(f, OBJECT_UNUSED, p, &o);
                                 if (r < 0)
                                         goto fail;
 
diff --git a/src/journal/sd-journal.c b/src/journal/sd-journal.c
index 028060d..be08a92 100644
--- a/src/journal/sd-journal.c
+++ b/src/journal/sd-journal.c
@@ -2588,10 +2588,10 @@ _public_ int sd_journal_enumerate_unique(sd_journal *j, const void **data, size_
                         continue;
                 }
 
-                /* We do not use the type context here, but 0 instead,
-                 * so that we can look at this data object at the same
+                /* We do not use OBJECT_DATA context here, but OBJECT_UNUSED
+                 * instead, so that we can look at this data object at the same
                  * time as one on another file */
-                r = journal_file_move_to_object(j->unique_file, 0, j->unique_offset, &o);
+                r = journal_file_move_to_object(j->unique_file, OBJECT_UNUSED, j->unique_offset, &o);
                 if (r < 0)
                         return r;
 

commit 2df65e7d964295f2763fae3b8bc3ade5d4e0fbe3
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Wed Dec 10 16:37:29 2014 +0100

    journal: consistently allow type==0 to mean "any type"
    
    If type==0 and a non-NULL object were given as arguments to
    journal_file_hmac_put_object(), its object type check would fail and it
    would return -EBADMSG.
    
    All existing callers use either a positive type or -1. Still, for
    behavior consistency with journal_file_move_to_object() let's allow
    type 0 to pass.

diff --git a/src/journal/journal-authenticate.c b/src/journal/journal-authenticate.c
index f9bd686..fd3b821 100644
--- a/src/journal/journal-authenticate.c
+++ b/src/journal/journal-authenticate.c
@@ -246,7 +246,7 @@ int journal_file_hmac_put_object(JournalFile *f, int type, Object *o, uint64_t p
                 if (r < 0)
                         return r;
         } else {
-                if (type >= 0 && o->object.type != type)
+                if (type > 0 && o->object.type != type)
                         return -EBADMSG;
         }
 

commit d3d3208f607693b8fde5226efa0cc15ec17670a0
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 18:06:22 2014 +0100

    journal: move type_to_context() to journal-file.c
    
    It has no other callers. It does not need to be in the header file.

diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index f706990..4632326 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -374,6 +374,11 @@ static int journal_file_allocate(JournalFile *f, uint64_t offset, uint64_t size)
         return 0;
 }
 
+static unsigned type_to_context(int type) {
+        /* One context for each type, plus one catch-all for the rest */
+        return type > 0 && type < _OBJECT_TYPE_MAX ? type : 0;
+}
+
 static int journal_file_move_to(JournalFile *f, int context, bool keep_always, uint64_t offset, uint64_t size, void **ret) {
         assert(f);
         assert(ret);
diff --git a/src/journal/journal-file.h b/src/journal/journal-file.h
index c5a92bc..5e8065c 100644
--- a/src/journal/journal-file.h
+++ b/src/journal/journal-file.h
@@ -205,9 +205,3 @@ int journal_file_get_cutoff_realtime_usec(JournalFile *f, usec_t *from, usec_t *
 int journal_file_get_cutoff_monotonic_usec(JournalFile *f, sd_id128_t boot, usec_t *from, usec_t *to);
 
 bool journal_file_rotate_suggested(JournalFile *f, usec_t max_file_usec);
-
-
-static unsigned type_to_context(int type) {
-        /* One context for each type, plus one catch-all for the rest */
-        return type > 0 && type < _OBJECT_TYPE_MAX ? type : 0;
-}

commit 1b8951e5bd9b2bf1722098a861055cae0bb52088
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 21:52:18 2014 +0100

    journal: remove journal_file_object_keep/release functions
    
    The only user is sd_journal_enumerate_unique() and, as explained in
    the previous commit (fed67c38e3 "journal: map objects to context set by
    caller, not by actual object type"), the use of them there is now
    superfluous. Let's remove them.
    
    This reverts major parts of commits:
      ae97089d49 journal: fix access to munmapped memory in
                 sd_journal_enumerate_unique
      06cc69d44c sd-journal: fix sd_journal_enumerate_unique skipping values
    
    Tested with an "--enable-debug" build and "journalctl --list-boots".
    It gives the expected number of results. Additionally, if I then revert
    the previous commit ("journal: map objects to context set by caller, not
    to actual object type"), it crashes with SIGSEGV, as expected.

diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 01b7f89..f706990 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -391,7 +391,7 @@ static int journal_file_move_to(JournalFile *f, int context, bool keep_always, u
                         return -EADDRNOTAVAIL;
         }
 
-        return mmap_cache_get(f->mmap, f->fd, f->prot, context, keep_always, offset, size, &f->last_stat, ret, NULL);
+        return mmap_cache_get(f->mmap, f->fd, f->prot, context, keep_always, offset, size, &f->last_stat, ret);
 }
 
 static uint64_t minimum_header_size(Object *o) {
diff --git a/src/journal/journal-file.h b/src/journal/journal-file.h
index 211e121..c5a92bc 100644
--- a/src/journal/journal-file.h
+++ b/src/journal/journal-file.h
@@ -211,15 +211,3 @@ static unsigned type_to_context(int type) {
         /* One context for each type, plus one catch-all for the rest */
         return type > 0 && type < _OBJECT_TYPE_MAX ? type : 0;
 }
-
-static inline int journal_file_object_keep(JournalFile *f, Object *o, uint64_t offset, void **release_cookie) {
-        unsigned context = type_to_context(o->object.type);
-        uint64_t s = le64toh(o->object.size);
-
-        return mmap_cache_get(f->mmap, f->fd, f->prot, context, true,
-                              offset, s, &f->last_stat, NULL, release_cookie);
-}
-
-static inline int journal_file_object_release(JournalFile *f, void *release_cookie) {
-        return mmap_cache_release(f->mmap, f->fd, release_cookie);
-}
diff --git a/src/journal/journal-verify.c b/src/journal/journal-verify.c
index 91de45f..75792a5 100644
--- a/src/journal/journal-verify.c
+++ b/src/journal/journal-verify.c
@@ -368,7 +368,7 @@ static int contains_uint64(MMapCache *m, int fd, uint64_t n, uint64_t p) {
 
                 c = (a + b) / 2;
 
-                r = mmap_cache_get(m, fd, PROT_READ|PROT_WRITE, 0, false, c * sizeof(uint64_t), sizeof(uint64_t), NULL, (void **) &z, NULL);
+                r = mmap_cache_get(m, fd, PROT_READ|PROT_WRITE, 0, false, c * sizeof(uint64_t), sizeof(uint64_t), NULL, (void **) &z);
                 if (r < 0)
                         return r;
 
diff --git a/src/journal/mmap-cache.c b/src/journal/mmap-cache.c
index c57c162..f34d260 100644
--- a/src/journal/mmap-cache.c
+++ b/src/journal/mmap-cache.c
@@ -38,7 +38,7 @@ typedef struct FileDescriptor FileDescriptor;
 struct Window {
         MMapCache *cache;
 
-        unsigned keep_always;
+        bool keep_always;
         bool in_unused;
 
         int prot;
@@ -191,7 +191,7 @@ static void context_detach_window(Context *c) {
         c->window = NULL;
         LIST_REMOVE(by_window, w->contexts, c);
 
-        if (!w->contexts && w->keep_always == 0) {
+        if (!w->contexts && !w->keep_always) {
                 /* Not used anymore? */
 #ifdef ENABLE_DEBUG_MMAP_CACHE
                 /* Unmap unused windows immediately to expose use-after-unmap
@@ -364,8 +364,7 @@ static int try_context(
                 bool keep_always,
                 uint64_t offset,
                 size_t size,
-                void **ret,
-                void **release_cookie) {
+                void **ret) {
 
         Context *c;
 
@@ -373,6 +372,7 @@ static int try_context(
         assert(m->n_ref > 0);
         assert(fd >= 0);
         assert(size > 0);
+        assert(ret);
 
         c = hashmap_get(m->contexts, UINT_TO_PTR(context+1));
         if (!c)
@@ -390,12 +390,9 @@ static int try_context(
                 return 0;
         }
 
-        c->window->keep_always += keep_always;
+        c->window->keep_always |= keep_always;
 
-        if (ret)
-                *ret = (uint8_t*) c->window->ptr + (offset - c->window->offset);
-        if (keep_always && release_cookie)
-                *release_cookie = c->window;
+        *ret = (uint8_t*) c->window->ptr + (offset - c->window->offset);
         return 1;
 }
 
@@ -407,8 +404,7 @@ static int find_mmap(
                 bool keep_always,
                 uint64_t offset,
                 size_t size,
-                void **ret,
-                void **release_cookie) {
+                void **ret) {
 
         FileDescriptor *f;
         Window *w;
@@ -439,10 +435,7 @@ static int find_mmap(
         context_attach_window(c, w);
         w->keep_always += keep_always;
 
-        if (ret)
-                *ret = (uint8_t*) w->ptr + (offset - w->offset);
-        if (keep_always && release_cookie)
-                *release_cookie = c->window;
+        *ret = (uint8_t*) w->ptr + (offset - w->offset);
         return 1;
 }
 
@@ -455,8 +448,7 @@ static int add_mmap(
                 uint64_t offset,
                 size_t size,
                 struct stat *st,
-                void **ret,
-                void **release_cookie) {
+                void **ret) {
 
         uint64_t woffset, wsize;
         Context *c;
@@ -469,6 +461,7 @@ static int add_mmap(
         assert(m->n_ref > 0);
         assert(fd >= 0);
         assert(size > 0);
+        assert(ret);
 
         woffset = offset & ~((uint64_t) page_size() - 1ULL);
         wsize = size + (offset - woffset);
@@ -538,10 +531,7 @@ static int add_mmap(
         c->window = w;
         LIST_PREPEND(by_window, w->contexts, c);
 
-        if (ret)
-                *ret = (uint8_t*) w->ptr + (offset - w->offset);
-        if (keep_always && release_cookie)
-                *release_cookie = c->window;
+        *ret = (uint8_t*) w->ptr + (offset - w->offset);
         return 1;
 
 outofmem:
@@ -558,8 +548,7 @@ int mmap_cache_get(
                 uint64_t offset,
                 size_t size,
                 struct stat *st,
-                void **ret,
-                void **release_cookie) {
+                void **ret) {
 
         int r;
 
@@ -567,16 +556,17 @@ int mmap_cache_get(
         assert(m->n_ref > 0);
         assert(fd >= 0);
         assert(size > 0);
+        assert(ret);
 
         /* Check whether the current context is the right one already */
-        r = try_context(m, fd, prot, context, keep_always, offset, size, ret, release_cookie);
+        r = try_context(m, fd, prot, context, keep_always, offset, size, ret);
         if (r != 0) {
                 m->n_hit ++;
                 return r;
         }
 
         /* Search for a matching mmap */
-        r = find_mmap(m, fd, prot, context, keep_always, offset, size, ret, release_cookie);
+        r = find_mmap(m, fd, prot, context, keep_always, offset, size, ret);
         if (r != 0) {
                 m->n_hit ++;
                 return r;
@@ -585,39 +575,7 @@ int mmap_cache_get(
         m->n_missed++;
 
         /* Create a new mmap */
-        return add_mmap(m, fd, prot, context, keep_always, offset, size, st, ret, release_cookie);
-}
-
-int mmap_cache_release(
-                MMapCache *m,
-                int fd,
-                void *release_cookie) {
-
-        FileDescriptor *f;
-        Window *w;
-
-        assert(m);
-        assert(m->n_ref > 0);
-        assert(fd >= 0);
-
-        f = hashmap_get(m->fds, INT_TO_PTR(fd + 1));
-        if (!f)
-                return -EBADF;
-
-        assert(f->fd == fd);
-
-        LIST_FOREACH(by_fd, w, f->windows)
-                if (w == release_cookie)
-                        break;
-
-        if (!w)
-                return -ENOENT;
-
-        if (w->keep_always == 0)
-                return -ENOLCK;
-
-        w->keep_always -= 1;
-        return 0;
+        return add_mmap(m, fd, prot, context, keep_always, offset, size, st, ret);
 }
 
 void mmap_cache_close_fd(MMapCache *m, int fd) {
diff --git a/src/journal/mmap-cache.h b/src/journal/mmap-cache.h
index 76e5316..3e2ffbb 100644
--- a/src/journal/mmap-cache.h
+++ b/src/journal/mmap-cache.h
@@ -40,12 +40,7 @@ int mmap_cache_get(
         uint64_t offset,
         size_t size,
         struct stat *st,
-        void **ret,
-        void **release_cookie);
-int mmap_cache_release(
-        MMapCache *m,
-        int fd,
-        void *release_cookie);
+        void **ret);
 void mmap_cache_close_fd(MMapCache *m, int fd);
 void mmap_cache_close_context(MMapCache *m, unsigned context);
 
diff --git a/src/journal/sd-journal.c b/src/journal/sd-journal.c
index 23aad74..028060d 100644
--- a/src/journal/sd-journal.c
+++ b/src/journal/sd-journal.c
@@ -2563,7 +2563,6 @@ _public_ int sd_journal_enumerate_unique(sd_journal *j, const void **data, size_
                 size_t ol;
                 bool found;
                 int r;
-                void *release_cookie;
 
                 /* Proceed to next data object in the field's linked list */
                 if (j->unique_offset == 0) {
@@ -2604,10 +2603,6 @@ _public_ int sd_journal_enumerate_unique(sd_journal *j, const void **data, size_
                         return -EBADMSG;
                 }
 
-                r = journal_file_object_keep(j->unique_file, o, j->unique_offset, &release_cookie);
-                if (r < 0)
-                        return r;
-
                 r = return_data(j, j->unique_file, o, &odata, &ol);
                 if (r < 0)
                         return r;
@@ -2652,10 +2647,6 @@ _public_ int sd_journal_enumerate_unique(sd_journal *j, const void **data, size_
                                 found = true;
                 }
 
-                r = journal_file_object_release(j->unique_file, release_cookie);
-                if (r < 0)
-                        return r;
-
                 if (found)
                         continue;
 
diff --git a/src/journal/test-mmap-cache.c b/src/journal/test-mmap-cache.c
index 1227b62..3fcd774 100644
--- a/src/journal/test-mmap-cache.c
+++ b/src/journal/test-mmap-cache.c
@@ -49,23 +49,23 @@ int main(int argc, char *argv[]) {
         assert_se(z >= 0);
         unlink(pz);
 
-        r = mmap_cache_get(m, x, PROT_READ, 0, false, 1, 2, NULL, &p, NULL);
+        r = mmap_cache_get(m, x, PROT_READ, 0, false, 1, 2, NULL, &p);
         assert_se(r >= 0);
 
-        r = mmap_cache_get(m, x, PROT_READ, 0, false, 2, 2, NULL, &q, NULL);
+        r = mmap_cache_get(m, x, PROT_READ, 0, false, 2, 2, NULL, &q);
         assert_se(r >= 0);
 
         assert_se((uint8_t*) p + 1 == (uint8_t*) q);
 
-        r = mmap_cache_get(m, x, PROT_READ, 1, false, 3, 2, NULL, &q, NULL);
+        r = mmap_cache_get(m, x, PROT_READ, 1, false, 3, 2, NULL, &q);
         assert_se(r >= 0);
 
         assert_se((uint8_t*) p + 2 == (uint8_t*) q);
 
-        r = mmap_cache_get(m, x, PROT_READ, 0, false, 16ULL*1024ULL*1024ULL, 2, NULL, &p, NULL);
+        r = mmap_cache_get(m, x, PROT_READ, 0, false, 16ULL*1024ULL*1024ULL, 2, NULL, &p);
         assert_se(r >= 0);
 
-        r = mmap_cache_get(m, x, PROT_READ, 1, false, 16ULL*1024ULL*1024ULL+1, 2, NULL, &q, NULL);
+        r = mmap_cache_get(m, x, PROT_READ, 1, false, 16ULL*1024ULL*1024ULL+1, 2, NULL, &q);
         assert_se(r >= 0);
 
         assert_se((uint8_t*) p + 1 == (uint8_t*) q);

commit fed67c38e3f1cecf4c0571f5603d47b35bff6576
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 18:21:55 2014 +0100

    journal: map objects to context set by caller, not by actual object type
    
    When the caller of journal_file_move_to_object() specifies type==0,
    the object header is at first mapped in context 0. Then after the header
    is checked, the whole object is mapped in a context determined by
    the actual object type (which is not even range-checked using
    type_to_context()). This looks wrong. It should map in the
    caller-specified context.
    
    An old comment in sd_journal_enumerate_unique() supports this view:
        /* We do not use the type context here, but 0 instead,
         * so that we can look at this data object at the same
         * time as one on another file */
    Clearly the expectation was that the data object will remain mapped
    in context 0 without being pushed away by mapping other objects in
    context OBJECT_DATA.
    
    I suspect that this was the real bug that got fixed by ae97089d49
    "journal: fix access to munmapped memory in sd_journal_enumerate_unique".
    In other words, journal_file_object_keep/release are superfluous after
    applying this patch.

diff --git a/src/journal/journal-file.c b/src/journal/journal-file.c
index 622eb16..01b7f89 100644
--- a/src/journal/journal-file.c
+++ b/src/journal/journal-file.c
@@ -445,7 +445,7 @@ int journal_file_move_to_object(JournalFile *f, int type, uint64_t offset, Objec
                 return -EBADMSG;
 
         if (s > sizeof(ObjectHeader)) {
-                r = journal_file_move_to(f, o->object.type, false, offset, s, &t);
+                r = journal_file_move_to(f, type_to_context(type), false, offset, s, &t);
                 if (r < 0)
                         return r;
 

commit fad5a6c66e73d3df20846906121d52159e1f6bf4
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 17:57:22 2014 +0100

    journal: add debug mode for mmap-cache (--enable-debug=mmap-cache)
    
    This is useful for exposing unsafe access to mmapped objects after
    the context that they were mapped in was already moved.
    
    For example:
    journal_file_move_to_object(f1, OBJECT_DATA, p1, &o1);
    journal_file_move_to_object(f2, OBJECT_DATA, p2, &o2);
    t = o1->object.type; /* this usually works, but is unsafe */

diff --git a/configure.ac b/configure.ac
index ea74fcd..e14f3cf 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1328,9 +1328,9 @@ AC_ARG_ENABLE(tests,
 AM_CONDITIONAL(ENABLE_TESTS, [test x$enable_tests = xyes])
 
 AC_ARG_ENABLE(debug,
-        [AC_HELP_STRING([--enable-debug@<:@=LIST@:>@], [enable extra debugging (hashmap)])],
+        [AC_HELP_STRING([--enable-debug@<:@=LIST@:>@], [enable extra debugging (hashmap,mmap-cache)])],
         [if test "x$enableval" = "xyes"; then
-                enableval="hashmap"
+                enableval="hashmap,mmap-cache"
         fi
         saved_ifs="$IFS"
         IFS="$IFS$PATH_SEPARATOR,"
@@ -1339,6 +1339,9 @@ AC_ARG_ENABLE(debug,
                 hashmap)
                         enable_debug_hashmap=yes
                         ;;
+                mmap-cache)
+                        enable_debug_mmap_cache=yes
+                        ;;
                 esac
         done
         IFS="$saved_ifs"],[])
@@ -1348,6 +1351,9 @@ AS_IF([test x$enable_debug_hashmap = xyes], [
         AC_DEFINE(ENABLE_DEBUG_HASHMAP, 1, [Define if hashmap debugging is to be enabled])
         enable_debug="hashmap $enable_debug"
 ])
+AS_IF([test x$enable_debug_mmap_cache = xyes], [
+        AC_DEFINE(ENABLE_DEBUG_MMAP_CACHE, 1, [Define if mmap cache debugging is to be enabled])
+        enable_debug="mmap-cache $enable_debug"
 ])
 test -z "$enable_debug" && enable_debug="none"
 
diff --git a/src/journal/mmap-cache.c b/src/journal/mmap-cache.c
index b7db6f1..c57c162 100644
--- a/src/journal/mmap-cache.c
+++ b/src/journal/mmap-cache.c
@@ -83,7 +83,13 @@ struct MMapCache {
 };
 
 #define WINDOWS_MIN 64
-#define WINDOW_SIZE (8ULL*1024ULL*1024ULL)
+
+#ifdef ENABLE_DEBUG_MMAP_CACHE
+/* Tiny windows increase mmap activity and the chance of exposing unsafe use. */
+# define WINDOW_SIZE (page_size())
+#else
+# define WINDOW_SIZE (8ULL*1024ULL*1024ULL)
+#endif
 
 MMapCache* mmap_cache_new(void) {
         MMapCache *m;
@@ -187,11 +193,17 @@ static void context_detach_window(Context *c) {
 
         if (!w->contexts && w->keep_always == 0) {
                 /* Not used anymore? */
+#ifdef ENABLE_DEBUG_MMAP_CACHE
+                /* Unmap unused windows immediately to expose use-after-unmap
+                 * by SIGSEGV. */
+                window_free(w);
+#else
                 LIST_PREPEND(unused, c->cache->unused, w);
                 if (!c->cache->last_unused)
                         c->cache->last_unused = w;
 
                 w->in_unused = true;
+#endif
         }
 }
 

commit fc86aa0ed204922dcafa85353cb10e1aa7d91a76
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 17:48:13 2014 +0100

    configure.ac: add a generic --enable-debug, replace --enable-hashmap-debug
    
    There will be more debugging options later.
     --enable-debug will enable them all.
     --enable-debug=hashmap will enable only hashmap debugging.
    
    Also rename the C #define to ENABLE_DEBUG_* pattern.

diff --git a/configure.ac b/configure.ac
index 9218ed3..ea74fcd 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1323,16 +1323,33 @@ AS_IF([test "x$0" != "x./configure"], [
 ])
 
 AC_ARG_ENABLE(tests,
-       [AC_HELP_STRING([--disable-tests], [disable tests])],
-       enable_tests=$enableval, enable_tests=yes)
+        [AC_HELP_STRING([--disable-tests], [disable tests])],
+        enable_tests=$enableval, enable_tests=yes)
 AM_CONDITIONAL(ENABLE_TESTS, [test x$enable_tests = xyes])
 
-AC_ARG_ENABLE(hashmap-debug,
-       [AC_HELP_STRING([--enable-hashmap-debug], [enable hashmap debugging])],
-       enable_hashmap_debug=$enableval, enable_hashmap_debug=no)
-AS_IF([test x$enable_hashmap_debug = xyes], [
-        AC_DEFINE(ENABLE_HASHMAP_DEBUG, 1, [Define if hashmap debugging is to be enabled])
+AC_ARG_ENABLE(debug,
+        [AC_HELP_STRING([--enable-debug@<:@=LIST@:>@], [enable extra debugging (hashmap)])],
+        [if test "x$enableval" = "xyes"; then
+                enableval="hashmap"
+        fi
+        saved_ifs="$IFS"
+        IFS="$IFS$PATH_SEPARATOR,"
+        for name in $enableval; do
+                case $name in
+                hashmap)
+                        enable_debug_hashmap=yes
+                        ;;
+                esac
+        done
+        IFS="$saved_ifs"],[])
+
+enable_debug=""
+AS_IF([test x$enable_debug_hashmap = xyes], [
+        AC_DEFINE(ENABLE_DEBUG_HASHMAP, 1, [Define if hashmap debugging is to be enabled])
+        enable_debug="hashmap $enable_debug"
+])
 ])
+test -z "$enable_debug" && enable_debug="none"
 
 AC_SUBST([dbuspolicydir], [$with_dbuspolicydir])
 AC_SUBST([dbussessionservicedir], [$with_dbussessionservicedir])
@@ -1419,6 +1436,7 @@ AC_MSG_RESULT([
         SysV compatibility:      ${SYSTEM_SYSV_COMPAT}
         compatibility libraries: ${have_compat_libs}
         utmp/wtmp support:       ${have_utmp}
+        extra debugging:         ${enable_debug}
 
         prefix:                  ${prefix}
         rootprefix:              ${with_rootprefix}
diff --git a/src/shared/hashmap.c b/src/shared/hashmap.c
index 18c2c0e..f2a8a77 100644
--- a/src/shared/hashmap.c
+++ b/src/shared/hashmap.c
@@ -137,7 +137,7 @@ typedef uint8_t dib_raw_t;
 
 #define DIB_FREE UINT_MAX
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
 struct hashmap_debug_info {
         LIST_FIELDS(struct hashmap_debug_info, debug_list);
         unsigned max_entries;  /* high watermark of n_entries */
@@ -158,9 +158,9 @@ static LIST_HEAD(struct hashmap_debug_info, hashmap_debug_list);
 
 #define HASHMAP_DEBUG_FIELDS struct hashmap_debug_info debug;
 
-#else /* !ENABLE_HASHMAP_DEBUG */
+#else /* !ENABLE_DEBUG_HASHMAP */
 #define HASHMAP_DEBUG_FIELDS
-#endif /* ENABLE_HASHMAP_DEBUG */
+#endif /* ENABLE_DEBUG_HASHMAP */
 
 enum HashmapType {
         HASHMAP_TYPE_PLAIN,
@@ -552,7 +552,7 @@ static void base_remove_entry(HashmapBase *h, unsigned idx) {
         dibs = dib_raw_ptr(h);
         assert(dibs[idx] != DIB_RAW_FREE);
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         h->debug.rem_count++;
         h->debug.last_rem_idx = idx;
 #endif
@@ -631,7 +631,7 @@ static unsigned hashmap_iterate_in_insertion_order(OrderedHashmap *h, Iterator *
                 assert(e->p.b.key == i->next_key);
         }
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         i->prev_idx = idx;
 #endif
 
@@ -688,7 +688,7 @@ static unsigned hashmap_iterate_in_internal_order(HashmapBase *h, Iterator *i) {
         }
 
         idx = i->idx;
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         i->prev_idx = idx;
 #endif
 
@@ -711,7 +711,7 @@ static unsigned hashmap_iterate_entry(HashmapBase *h, Iterator *i) {
                 return IDX_NIL;
         }
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         if (i->idx == IDX_FIRST) {
                 i->put_count = h->debug.put_count;
                 i->rem_count = h->debug.rem_count;
@@ -799,7 +799,7 @@ static struct HashmapBase *hashmap_base_new(const struct hash_ops *hash_ops, enu
                 shared_hash_key_initialized= true;
         }
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         LIST_PREPEND(debug_list, hashmap_debug_list, &h->debug);
         h->debug.func = func;
         h->debug.file = file;
@@ -854,7 +854,7 @@ static void hashmap_free_no_clear(HashmapBase *h) {
         assert(!h->has_indirect);
         assert(!h->n_direct_entries);
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         LIST_REMOVE(debug_list, hashmap_debug_list, &h->debug);
 #endif
 
@@ -961,7 +961,7 @@ static bool hashmap_put_robin_hood(HashmapBase *h, unsigned idx,
         dib_raw_t raw_dib, *dibs;
         unsigned dib, distance;
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         h->debug.put_count++;
 #endif
 
@@ -1055,7 +1055,7 @@ static int hashmap_base_put_boldly(HashmapBase *h, unsigned idx,
         assert_se(hashmap_put_robin_hood(h, idx, swap) == false);
 
         n_entries_inc(h);
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         h->debug.max_entries = MAX(h->debug.max_entries, n_entries(h));
 #endif
 
@@ -1283,7 +1283,7 @@ int hashmap_replace(Hashmap *h, const void *key, void *value) {
         idx = bucket_scan(h, hash, key);
         if (idx != IDX_NIL) {
                 e = plain_bucket_at(h, idx);
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
                 /* Although the key is equal, the key pointer may have changed,
                  * and this would break our assumption for iterating. So count
                  * this operation as incompatible with iteration. */
diff --git a/src/shared/hashmap.h b/src/shared/hashmap.h
index 72c4adc..894f679 100644
--- a/src/shared/hashmap.h
+++ b/src/shared/hashmap.h
@@ -32,7 +32,7 @@
  * will be treated as empty hashmap for all read operations. That way it is not
  * necessary to instantiate an object for each Hashmap use.
  *
- * If ENABLE_HASHMAP_DEBUG is defined (by configuring with --enable-hashmap-debug),
+ * If ENABLE_DEBUG_HASHMAP is defined (by configuring with --enable-debug=hashmap),
  * the implemention will:
  * - store extra data for debugging and statistics (see tools/gdb-sd_dump_hashmaps.py)
  * - perform extra checks for invalid use of iterators
@@ -57,7 +57,7 @@ typedef struct Set Set;                       /* Stores just keys */
 typedef struct {
         unsigned idx;         /* index of an entry to be iterated next */
         const void *next_key; /* expected value of that entry's key pointer */
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
         unsigned put_count;   /* hashmap's put_count recorded at start of iteration */
         unsigned rem_count;   /* hashmap's rem_count in previous iteration */
         unsigned prev_idx;    /* idx in previous iteration */
@@ -129,7 +129,7 @@ extern const struct hash_ops devt_hash_ops = {
                 (Hashmap*)(h), \
                 (void)0)
 
-#ifdef ENABLE_HASHMAP_DEBUG
+#ifdef ENABLE_DEBUG_HASHMAP
 # define HASHMAP_DEBUG_PARAMS , const char *func, const char *file, int line
 # define HASHMAP_DEBUG_SRC_ARGS   , __func__, __FILE__, __LINE__
 # define HASHMAP_DEBUG_PASS_ARGS   , func, file, line

commit 90df619ef505145a62b25bbe8d95ae595a6a9511
Author: Michal Schmidt <mschmidt at redhat.com>
Date:   Fri Dec 12 17:42:28 2014 +0100

    shared/hashmap.h: fix comment
    
    An early version used underscore prefixes for internal functions, but
    the current version uses the prefix "internal_".

diff --git a/src/shared/hashmap.h b/src/shared/hashmap.h
index 9c6e0ca..72c4adc 100644
--- a/src/shared/hashmap.h
+++ b/src/shared/hashmap.h
@@ -43,7 +43,7 @@
 /* The base type for all hashmap and set types. Many functions in the
  * implementation take (HashmapBase*) parameters and are run-time polymorphic,
  * though the API is not meant to be polymorphic (do not call functions
- * prefixed with two underscores directly). */
+ * internal_*() directly). */
 typedef struct HashmapBase HashmapBase;
 
 /* Specific hashmap/set types */



More information about the systemd-commits mailing list