Message ID | 20221111092642.2333724-4-houtao@huaweicloud.com (mailing list archive) |
---|---|
State | Superseded |
Delegated to: | BPF |
Headers | show |
Series | libbpf: Fixes for ring buffer | expand |
On Fri, Nov 11, 2022 at 1:01 AM Hou Tao <houtao@huaweicloud.com> wrote: > > From: Hou Tao <houtao1@huawei.com> > > Similar with the overflow problem on ringbuf mmap, in user_ringbuf_map() > 2 * max_entries may overflow u32 when mapping writeable region. > > Fixing it by casting the size of writable mmap region into a __u64 and > checking whether or not there will be overflow during mmap. > > Fixes: b66ccae01f1d ("bpf: Add libbpf logic for user-space ring buffer") > Signed-off-by: Hou Tao <houtao1@huawei.com> > --- > tools/lib/bpf/ringbuf.c | 11 +++++++++-- > 1 file changed, 9 insertions(+), 2 deletions(-) > > diff --git a/tools/lib/bpf/ringbuf.c b/tools/lib/bpf/ringbuf.c > index c4bdc88af672..b34e61c538d7 100644 > --- a/tools/lib/bpf/ringbuf.c > +++ b/tools/lib/bpf/ringbuf.c > @@ -355,6 +355,7 @@ static int user_ringbuf_map(struct user_ring_buffer *rb, int map_fd) > { > struct bpf_map_info info; > __u32 len = sizeof(info); > + __u64 wr_size; > void *tmp; > struct epoll_event *rb_epoll; > int err; > @@ -391,8 +392,14 @@ static int user_ringbuf_map(struct user_ring_buffer *rb, int map_fd) > * simple reading and writing of samples that wrap around the end of > * the buffer. See the kernel implementation for details. > */ > - tmp = mmap(NULL, rb->page_size + 2 * info.max_entries, > - PROT_READ | PROT_WRITE, MAP_SHARED, map_fd, rb->page_size); > + wr_size = rb->page_size + 2 * (__u64)info.max_entries; > + if (wr_size != (__u64)(size_t)wr_size) { > + pr_warn("user ringbuf: ring buf size (%u) is too big\n", > + info.max_entries); > + return -E2BIG; > + } > + tmp = mmap(NULL, (size_t)wr_size, PROT_READ | PROT_WRITE, MAP_SHARED, > + map_fd, rb->page_size); same suggestions as in precious patch: s/wr_size/mmap_sz/ and let's discuss if we should split one mmap into two? cc'ed David as well > if (tmp == MAP_FAILED) { > err = -errno; > pr_warn("user ringbuf: failed to mmap data pages for map fd=%d: %d\n", > -- > 2.29.2 >
diff --git a/tools/lib/bpf/ringbuf.c b/tools/lib/bpf/ringbuf.c index c4bdc88af672..b34e61c538d7 100644 --- a/tools/lib/bpf/ringbuf.c +++ b/tools/lib/bpf/ringbuf.c @@ -355,6 +355,7 @@ static int user_ringbuf_map(struct user_ring_buffer *rb, int map_fd) { struct bpf_map_info info; __u32 len = sizeof(info); + __u64 wr_size; void *tmp; struct epoll_event *rb_epoll; int err; @@ -391,8 +392,14 @@ static int user_ringbuf_map(struct user_ring_buffer *rb, int map_fd) * simple reading and writing of samples that wrap around the end of * the buffer. See the kernel implementation for details. */ - tmp = mmap(NULL, rb->page_size + 2 * info.max_entries, - PROT_READ | PROT_WRITE, MAP_SHARED, map_fd, rb->page_size); + wr_size = rb->page_size + 2 * (__u64)info.max_entries; + if (wr_size != (__u64)(size_t)wr_size) { + pr_warn("user ringbuf: ring buf size (%u) is too big\n", + info.max_entries); + return -E2BIG; + } + tmp = mmap(NULL, (size_t)wr_size, PROT_READ | PROT_WRITE, MAP_SHARED, + map_fd, rb->page_size); if (tmp == MAP_FAILED) { err = -errno; pr_warn("user ringbuf: failed to mmap data pages for map fd=%d: %d\n",