From 152c0307ad2aeefb4f4f1fd43a23f309babbdb7a Mon Sep 17 00:00:00 2001 From: deraadt Date: Wed, 21 Feb 2024 03:28:29 +0000 Subject: [PATCH] Only return EPERM for immutable regions for the nasty operations of madvise() and msync() which damaged the region. The sync ones are allowed to proceed (even if most of them are nops...) based on issues noted by anton and semarie --- sys/uvm/uvm_map.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/sys/uvm/uvm_map.c b/sys/uvm/uvm_map.c index dd2135181e6..0e84e2a1e3f 100644 --- a/sys/uvm/uvm_map.c +++ b/sys/uvm/uvm_map.c @@ -1,4 +1,4 @@ -/* $OpenBSD: uvm_map.c,v 1.326 2024/01/21 17:21:55 deraadt Exp $ */ +/* $OpenBSD: uvm_map.c,v 1.327 2024/02/21 03:28:29 deraadt Exp $ */ /* $NetBSD: uvm_map.c,v 1.86 2000/11/27 08:40:03 chs Exp $ */ /* @@ -4556,7 +4556,7 @@ uvm_map_clean(struct vm_map *map, vaddr_t start, vaddr_t end, int flags) struct vm_page *pg; struct uvm_object *uobj; vaddr_t cp_start, cp_end; - int refs; + int refs, imut = 0; int error; boolean_t rv; @@ -4572,10 +4572,8 @@ uvm_map_clean(struct vm_map *map, vaddr_t start, vaddr_t end, int flags) /* Make a first pass to check for various conditions. */ for (entry = first; entry != NULL && entry->start < end; entry = RBT_NEXT(uvm_map_addr, entry)) { - if (entry->etype & UVM_ET_IMMUTABLE) { - vm_map_unlock(map); - return EPERM; - } + if (entry->etype & UVM_ET_IMMUTABLE) + imut = 1; if (UVM_ET_ISSUBMAP(entry)) { vm_map_unlock(map); return EINVAL; @@ -4608,6 +4606,11 @@ uvm_map_clean(struct vm_map *map, vaddr_t start, vaddr_t end, int flags) if (amap == NULL || (flags & (PGO_DEACTIVATE|PGO_FREE)) == 0) goto flush_object; + if (imut) { + vm_map_unbusy(map); + return EPERM; + } + cp_start = MAX(entry->start, start); cp_end = MIN(entry->end, end); -- 2.20.1