From e9fddbaad81de8afbffe3f8ff626a18a551619df Mon Sep 17 00:00:00 2001 From: cinap_lenrek Date: Sun, 14 Sep 2014 16:04:22 +0200 Subject: kernel: fix segattach() rounding of va+len (thanks kenji arisawa) from segattach(2): Va and len specify the position of the segment in the process's address space. Va is rounded down to the nearest page boundary and va+len is rounded up. The system does not permit segments to overlap. If va is zero, the system will choose a suitable address. just rounding up len isnt enougth. we have to round up va+len instead of just len so that the span [va, va+len) is covered even if va is not page aligned. kenjis example: print("%p\n",ap); // 206cb0 ap = segattach(0, "shared", ap, 1024); print("%p\n",ap); // 206000 term% cat /proc/612768/segment Stack defff000 dffff000 1 Text R 1000 6000 1 Data 6000 7000 1 Bss 7000 7000 1 Shared 206000 207000 1 term% note that 0x206cb0 + 0x400 > 0x20700. --- sys/src/9/port/segment.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/sys/src/9/port/segment.c b/sys/src/9/port/segment.c index 17efff622..2b45af88d 100644 --- a/sys/src/9/port/segment.c +++ b/sys/src/9/port/segment.c @@ -610,7 +610,10 @@ segattach(Proc *p, ulong attr, char *name, uintptr va, uintptr len) } } + /* round up va+len */ + len += va & (BY2PG-1); len = PGROUND(len); + if(len == 0) error(Ebadarg); -- cgit v1.2.3