From e828398c8b0a45f41c4d0f4823732f3859781d2a Mon Sep 17 00:00:00 2001 From: Masamichi Takagi Date: Thu, 7 Feb 2019 10:42:27 +0900 Subject: [PATCH] do_mmap: don't pre-populate the whole file when asked for smaller segment The linker maps parts of libs with different access flags, so we cannot prepopulate the whole file. [dominique.martinet@cea.fr: moved min and friends in compiler.h] Change-Id: Ifbeddc0908699099cfae5ce9cc2adc578221db31 --- kernel/include/lwk/compiler.h | 36 ++++++++++++++++++++++++++++++++++ kernel/include/xpmem_private.h | 36 ---------------------------------- kernel/syscall.c | 3 +-- 3 files changed, 37 insertions(+), 38 deletions(-) diff --git a/kernel/include/lwk/compiler.h b/kernel/include/lwk/compiler.h index ee987f2c..4c110978 100644 --- a/kernel/include/lwk/compiler.h +++ b/kernel/include/lwk/compiler.h @@ -545,4 +545,40 @@ static __always_inline void __write_once_size(volatile void *p, void *res, int s #define WRITE_ONCE(x, val) \ ({ typeof(x) __val = (val); __write_once_size(&(x), &__val, sizeof(__val)); __val; }) +#define min(x, y) ({ \ + __typeof__(x) _min1 = (x); \ + __typeof__(y) _min2 = (y); \ + (void) (&_min1 == &_min2); \ + _min1 < _min2 ? _min1 : _min2; }) + +#define max(x, y) ({ \ + __typeof__(x) _max1 = (x); \ + __typeof__(y) _max2 = (y); \ + (void) (&_max1 == &_max2); \ + _max1 > _max2 ? _max1 : _max2; }) + +#define MAX_ERRNO 4095 + +#define IS_ERR_VALUE(x) ((x) >= (unsigned long)-MAX_ERRNO) + +static inline void *ERR_PTR(long error) +{ + return (void *)error; +} + +static inline long PTR_ERR(const void *ptr) +{ + return (long)ptr; +} + +static inline long IS_ERR(const void *ptr) +{ + return IS_ERR_VALUE((unsigned long)ptr); +} + +static inline long IS_ERR_OR_NULL(const void *ptr) +{ + return !ptr || IS_ERR_VALUE((unsigned long)ptr); +} + #endif /* __LWK_COMPILER_H */ diff --git a/kernel/include/xpmem_private.h b/kernel/include/xpmem_private.h index 48d2b6e3..0d9acb70 100644 --- a/kernel/include/xpmem_private.h +++ b/kernel/include/xpmem_private.h @@ -48,42 +48,6 @@ #define offset_in_page(p) ((unsigned long)(p) & ~PAGE_MASK) -#define min(x, y) ({ \ - __typeof__(x) _min1 = (x); \ - __typeof__(y) _min2 = (y); \ - (void) (&_min1 == &_min2); \ - _min1 < _min2 ? _min1 : _min2;}) - -#define max(x, y) ({ \ - __typeof__(x) _max1 = (x); \ - __typeof__(y) _max2 = (y); \ - (void) (&_max1 == &_max2); \ - _max1 > _max2 ? _max1 : _max2;}) - -#define MAX_ERRNO 4095 - -#define IS_ERR_VALUE(x) ((x) >= (unsigned long)-MAX_ERRNO) - -static inline void * ERR_PTR(long error) -{ - return (void *)error; -} - -static inline long PTR_ERR(const void *ptr) -{ - return (long)ptr; -} - -static inline long IS_ERR(const void *ptr) -{ - return IS_ERR_VALUE((unsigned long)ptr); -} - -static inline long IS_ERR_OR_NULL(const void *ptr) -{ - return !ptr || IS_ERR_VALUE((unsigned long)ptr); -} - /* * Both the xpmem_segid_t and xpmem_apid_t are of type __s64 and designed * to be opaque to the user. Both consist of the same underlying fields. diff --git a/kernel/syscall.c b/kernel/syscall.c index 6286d8d5..90da5f11 100644 --- a/kernel/syscall.c +++ b/kernel/syscall.c @@ -1925,13 +1925,12 @@ do_mmap(const uintptr_t addr0, const size_t len0, const int prot, } /* Determine pre-populated size */ - populate_len = len; + populate_len = memobj ? min(len, memobj->size) : len; if (!(flags & MAP_ANONYMOUS)) { if (atomic_cmpxchg4(&memobj->status, MEMOBJ_TO_BE_PREFETCHED, MEMOBJ_READY)) { populated_mapping = 1; - populate_len = memobj->size; } /* Update PTEs for pre-mapped memory object */