Jinoh Kang (@iamahuman) commented about server/mapping.c:
shared->object_capacity = (mapping->size - offsetof(session_shm_t, objects[0])) / sizeof(session_obj_t);
- }
- SHARED_WRITE_END;
+}
+static int grow_session_mapping(void) +{
- unsigned int capacity;
- mem_size_t size;
- int unix_fd;
- void *tmp;
- capacity = session.shared->object_capacity * 3 / 2;
- size = offsetof(session_shm_t, objects[capacity]);
- size = (size + page_mask) & ~((mem_size_t)page_mask);
The growth rate is not kept in sync with initial capacity, so it's possible that `grow_session_mapping` ends up doing nothing (0% increment) since the initial capacity is too small (e.g. capacity = 31, growth = 33/32). However, `alloc_shared_object` does not check for this condition, resulting in OOB.
So I think either `grow_session_mapping` or `alloc_shared_object` should have an assert for size growth (see the other thread). Note that decrement is not possible—I got this part wrong, sorry.