diff --git a/include/haproxy/ring-t.h b/include/haproxy/ring-t.h index 55867b54b..ac3e1e1d9 100644 --- a/include/haproxy/ring-t.h +++ b/include/haproxy/ring-t.h @@ -96,6 +96,9 @@ #define RING_WF_WAIT_MODE 0x00000001 /* wait for new contents */ #define RING_WF_SEEK_NEW 0x00000002 /* seek to new contents */ +/* ring flags */ +#define RING_FL_MAPPED 0x00000001 /* mmapped area, must not free() */ + /* keep values below in decimal, they may be dumped in error messages */ #define RING_WRITING_SIZE 255 /* the next message's size is being written */ #define RING_MAX_READERS 254 /* highest supported value for RC */ @@ -105,6 +108,7 @@ struct ring { struct list waiters; // list of waiters, for now, CLI "show event" __decl_thread(HA_RWLOCK_T lock); int readers_count; + uint flags; // RING_FL_* }; #endif /* _HAPROXY_RING_T_H */ diff --git a/src/ring.c b/src/ring.c index 8d0b704bb..52df2a5cc 100644 --- a/src/ring.c +++ b/src/ring.c @@ -43,6 +43,8 @@ void ring_init(struct ring *ring, void *area, size_t size) LIST_INIT(&ring->waiters); ring->readers_count = 0; ring->buf = b_make(area, size, 0, 0); + ring->flags = 0; + /* write the initial RC byte */ b_putchr(&ring->buf, 0); } @@ -83,18 +85,23 @@ struct ring *ring_new(size_t size) struct ring *ring_make_from_area(void *area, size_t size) { struct ring *ring = NULL; + uint flags = 0; if (size < sizeof(*ring)) return NULL; if (!area) area = malloc(size); + else + flags |= RING_FL_MAPPED; + if (!area) return NULL; ring = area; area += sizeof(*ring); ring_init(ring, area, size - sizeof(*ring)); + ring->flags |= flags; return ring; } @@ -113,6 +120,7 @@ struct ring *ring_cast_from_area(void *area) HA_RWLOCK_INIT(&ring->lock); LIST_INIT(&ring->waiters); ring->readers_count = 0; + ring->flags = RING_FL_MAPPED; return ring; } @@ -156,7 +164,7 @@ void ring_free(struct ring *ring) return; /* make sure it was not allocated by ring_make_from_area */ - if (ring->buf.area == (void *)ring + sizeof(*ring)) + if (ring->flags & RING_FL_MAPPED) return; free(ring_area(ring));