From 44f8bf7d26bf21cc66d2fc8c14a924ed2e1b4f0f Mon Sep 17 00:00:00 2001 From: Richard Braun Date: Sat, 15 Jun 2013 17:16:26 +0200 Subject: vm/vm_map: rework flags Add vm/vm_adv.h for VM_ADV_xxx advice macros, and directly use VM_{ADV,INHERIT,PROT}_xxx macros in the "packed" format used for mapping requests and in map entries. This allows simpler comparisons between stored flags and user provided values. --- Makefrag.am | 1 + vm/vm_adv.h | 31 ++++++++++++++++++++++++++ vm/vm_inherit.h | 10 ++++----- vm/vm_kmem.c | 11 ++++++---- vm/vm_map.c | 32 ++++++++------------------- vm/vm_map.h | 67 +++++++++++++++++++++------------------------------------ 6 files changed, 77 insertions(+), 75 deletions(-) create mode 100644 vm/vm_adv.h diff --git a/Makefrag.am b/Makefrag.am index 67086d5c..d32c02a3 100644 --- a/Makefrag.am +++ b/Makefrag.am @@ -54,6 +54,7 @@ x15_SOURCES += \ kern/work.h x15_SOURCES += \ + vm/vm_adv.h \ vm/vm_inherit.h \ vm/vm_kmem.c \ vm/vm_kmem.h \ diff --git a/vm/vm_adv.h b/vm/vm_adv.h new file mode 100644 index 00000000..1138f0c8 --- /dev/null +++ b/vm/vm_adv.h @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2013 Richard Braun. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef _VM_VM_ADV_H +#define _VM_VM_ADV_H + +/* + * Advice values. + */ +#define VM_ADV_NORMAL 0 +#define VM_ADV_RANDOM 1 +#define VM_ADV_SEQUENTIAL 2 +#define VM_ADV_WILLNEED 3 +#define VM_ADV_DONTNEED 4 +#define VM_ADV_DEFAULT VM_ADV_NORMAL + +#endif /* _VM_VM_ADV_H */ diff --git a/vm/vm_inherit.h b/vm/vm_inherit.h index b50d490d..0ef4616c 100644 --- a/vm/vm_inherit.h +++ b/vm/vm_inherit.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011, 2012 Richard Braun. + * Copyright (c) 2011, 2012, 2013 Richard Braun. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -19,11 +19,11 @@ #define _VM_VM_INHERIT_H /* - * Inheritance flags. + * Inheritance values. */ -#define VM_INHERIT_SHARE 0 -#define VM_INHERIT_COPY 1 -#define VM_INHERIT_NONE 2 +#define VM_INHERIT_NONE 0 +#define VM_INHERIT_SHARE 1 +#define VM_INHERIT_COPY 2 #define VM_INHERIT_DEFAULT VM_INHERIT_COPY #endif /* _VM_VM_INHERIT_H */ diff --git a/vm/vm_kmem.c b/vm/vm_kmem.c index 9f6088de..24a23525 100644 --- a/vm/vm_kmem.c +++ b/vm/vm_kmem.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011, 2012 Richard Braun. + * Copyright (c) 2011, 2012, 2013 Richard Braun. * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -22,10 +22,13 @@ #include #include #include -#include +#include +#include #include +#include #include #include +#include /* * Kernel map and storage. @@ -123,8 +126,8 @@ vm_kmem_alloc_va(size_t size) size = vm_page_round(size); va = 0; - flags = VM_MAP_PROT_ALL | VM_MAP_MAX_PROT_ALL | VM_MAP_INHERIT_NONE - | VM_MAP_ADV_NORMAL; + flags = VM_MAP_FLAGS(VM_PROT_ALL, VM_PROT_ALL, VM_INHERIT_NONE, + VM_ADV_DEFAULT, 0); error = vm_map_enter(kernel_map, NULL, 0, &va, size, 0, flags); if (error) diff --git a/vm/vm_map.c b/vm/vm_map.c index 83091c0e..33c95183 100644 --- a/vm/vm_map.c +++ b/vm/vm_map.c @@ -44,10 +44,13 @@ #include #include #include +#include +#include #include #include #include #include +#include /* * Special threshold which disables the use of the free area cache address. @@ -262,8 +265,8 @@ vm_map_kentry_setup(void) assert(nr_pages > 0); assert(vm_page_aligned(VM_MAP_KENTRY_SIZE)); - flags = VM_MAP_PROT_ALL | VM_MAP_MAX_PROT_ALL | VM_MAP_INHERIT_NONE - | VM_MAP_ADV_NORMAL | VM_MAP_NOMERGE; + flags = VM_MAP_FLAGS(VM_PROT_ALL, VM_PROT_ALL, VM_INHERIT_NONE, + VM_ADV_DEFAULT, VM_MAP_NOMERGE); error = vm_map_prepare(kernel_map, NULL, 0, 0, VM_MAP_KENTRY_SIZE + size, 0, flags, &request); @@ -348,24 +351,10 @@ vm_map_entry_cmp_insert(const struct rbtree_node *a, return vm_map_entry_cmp_lookup(entry->start, b); } -static inline int -vm_map_get_protection(int flags) -{ - return flags & VM_MAP_PROT_MASK; -} - -static inline int -vm_map_get_max_protection(int flags) -{ - return (flags & VM_MAP_MAX_PROT_MASK) >> 4; -} - #ifndef NDEBUG static void vm_map_request_assert_valid(const struct vm_map_request *request) { - int prot, max_prot; - assert((request->object != NULL) || (request->offset == 0)); assert(vm_page_aligned(request->offset)); assert(vm_page_aligned(request->start)); @@ -375,11 +364,8 @@ vm_map_request_assert_valid(const struct vm_map_request *request) assert((request->align == 0) || (request->align >= PAGE_SIZE)); assert(ISP2(request->align)); - prot = vm_map_get_protection(request->flags); - max_prot = vm_map_get_max_protection(request->flags); - assert((prot & max_prot) == prot); - assert(__builtin_popcount(request->flags & VM_MAP_INHERIT_MASK) == 1); - assert(__builtin_popcount(request->flags & VM_MAP_ADV_MASK) == 1); + assert((VM_MAP_PROT(request->flags) & VM_MAP_MAXPROT(request->flags)) + == VM_MAP_PROT(request->flags)); assert(!(request->flags & VM_MAP_FIXED) || (request->align == 0) || P2ALIGNED(request->start, request->align)); @@ -946,8 +932,8 @@ vm_map_setup(void) * the physical page table. */ vm_kmem_boot_space(&start, &end); - flags = VM_MAP_PROT_ALL | VM_MAP_MAX_PROT_ALL | VM_MAP_INHERIT_NONE - | VM_MAP_ADV_NORMAL | VM_MAP_NOMERGE | VM_MAP_FIXED; + flags = VM_MAP_FLAGS(VM_PROT_ALL, VM_PROT_ALL, VM_INHERIT_NONE, + VM_ADV_DEFAULT, VM_MAP_NOMERGE | VM_MAP_FIXED); error = vm_map_prepare(kernel_map, NULL, 0, start, end - start, 0, flags, &request); diff --git a/vm/vm_map.h b/vm/vm_map.h index 3847001c..c68072d7 100644 --- a/vm/vm_map.h +++ b/vm/vm_map.h @@ -26,58 +26,39 @@ #include #include #include +#include +#include +#include /* - * Mapping flags and masks. + * Mapping flags. * - * All these flags can be used when creating a mapping. Most of them are - * also used as map entry flags. + * Unless otherwise mentioned, these can also be used as map entry flags. */ -#define VM_MAP_PROT_READ 0x00001 -#define VM_MAP_PROT_WRITE 0x00002 -#define VM_MAP_PROT_EXEC 0x00004 -#define VM_MAP_PROT_ALL (VM_MAP_PROT_READ \ - | VM_MAP_PROT_WRITE \ - | VM_MAP_PROT_EXEC) -#define VM_MAP_PROT_MASK VM_MAP_PROT_ALL +#define VM_MAP_NOMERGE 0x10000 +#define VM_MAP_FIXED 0x20000 /* Not an entry flag */ -#define VM_MAP_MAX_PROT_READ (VM_MAP_PROT_READ << 4) -#define VM_MAP_MAX_PROT_WRITE (VM_MAP_PROT_WRITE << 4) -#define VM_MAP_MAX_PROT_EXEC (VM_MAP_PROT_EXEC << 4) -#define VM_MAP_MAX_PROT_ALL (VM_MAP_MAX_PROT_READ \ - | VM_MAP_MAX_PROT_WRITE \ - | VM_MAP_MAX_PROT_EXEC) -#define VM_MAP_MAX_PROT_MASK VM_MAP_MAX_PROT_ALL - -#define VM_MAP_INHERIT_SHARE 0x00100 -#define VM_MAP_INHERIT_COPY 0x00200 -#define VM_MAP_INHERIT_NONE 0x00400 -#define VM_MAP_INHERIT_MASK (VM_MAP_INHERIT_SHARE \ - | VM_MAP_INHERIT_COPY \ - | VM_MAP_INHERIT_NONE) - -#define VM_MAP_ADV_NORMAL 0x01000 -#define VM_MAP_ADV_RAND 0x02000 -#define VM_MAP_ADV_SEQUENTIAL 0x04000 -#define VM_MAP_ADV_WILLNEED 0x08000 -#define VM_MAP_ADV_DONTNEED 0x10000 -#define VM_MAP_ADV_MASK (VM_MAP_ADV_NORMAL \ - | VM_MAP_ADV_RAND \ - | VM_MAP_ADV_SEQUENTIAL \ - | VM_MAP_ADV_WILLNEED \ - | VM_MAP_ADV_DONTNEED) +/* + * Macro used to forge "packed" flags. + */ +#define VM_MAP_FLAGS(prot, maxprot, inherit, advice, mapflags) \ + ((prot) | ((maxprot) << 4) | ((inherit) << 8) | ((advice) << 12) \ + | (mapflags)) -#define VM_MAP_NOMERGE 0x20000 -#define VM_MAP_FIXED 0x40000 /* Not an entry flag */ +/* + * Flags usable as map entry flags. + * + * Map entry flags also use the packed format. + */ +#define VM_MAP_ENTRY_MASK (VM_MAP_NOMERGE | 0xffff) /* - * Flags that can be used as map entry flags. + * Macros used to extract specific properties out of packed flags. */ -#define VM_MAP_ENTRY_MASK (VM_MAP_PROT_MASK \ - | VM_MAP_MAX_PROT_MASK \ - | VM_MAP_INHERIT_MASK \ - | VM_MAP_ADV_MASK \ - | VM_MAP_NOMERGE) +#define VM_MAP_PROT(flags) ((flags) & 0xf) +#define VM_MAP_MAXPROT(flags) (((flags) & 0xf0) >> 4) +#define VM_MAP_INHERIT(flags) (((flags) & 0xf00) >> 8) +#define VM_MAP_ADVICE(flags) (((flags) & 0xf000) >> 12) /* * Memory range descriptor. -- cgit v1.2.3