Date: Tue, 24 Jan 2017 22:00:16 +0000 (UTC) From: Mateusz Guzik <mjg@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r312724 - in head/sys: sys vm Message-ID: <201701242200.v0OM0GRO042084@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: mjg Date: Tue Jan 24 22:00:16 2017 New Revision: 312724 URL: https://svnweb.freebsd.org/changeset/base/312724 Log: hwpmc: partially depessimize munmap handling if the module is not loaded HWPMC_HOOKS is enabled in GENERIC and triggers some work avoidable in the common (module not loaded) case. In particular this avoids permission checks + lock downgrade singlethreaded and in cases were an executable mapping is found the pmc sx lock is no longer bounced. Note this is a band aid. MFC after: 1 week Modified: head/sys/sys/pmckern.h head/sys/vm/vm_mmap.c Modified: head/sys/sys/pmckern.h ============================================================================== --- head/sys/sys/pmckern.h Tue Jan 24 21:48:57 2017 (r312723) +++ head/sys/sys/pmckern.h Tue Jan 24 22:00:16 2017 (r312724) @@ -174,6 +174,9 @@ extern const int pmc_kernel_version; /* PMC soft per cpu trapframe */ extern struct trapframe pmc_tf[MAXCPU]; +/* Quick check if preparatory work is necessary */ +#define PMC_HOOK_INSTALLED(cmd) __predict_false(pmc_hook != NULL) + /* Hook invocation; for use within the kernel */ #define PMC_CALL_HOOK(t, cmd, arg) \ do { \ Modified: head/sys/vm/vm_mmap.c ============================================================================== --- head/sys/vm/vm_mmap.c Tue Jan 24 21:48:57 2017 (r312723) +++ head/sys/vm/vm_mmap.c Tue Jan 24 22:00:16 2017 (r312724) @@ -526,6 +526,7 @@ sys_munmap(td, uap) #ifdef HWPMC_HOOKS struct pmckern_map_out pkm; vm_map_entry_t entry; + bool pmc_handled; #endif vm_offset_t addr; vm_size_t size, pageoff; @@ -551,20 +552,24 @@ sys_munmap(td, uap) return (EINVAL); vm_map_lock(map); #ifdef HWPMC_HOOKS - /* - * Inform hwpmc if the address range being unmapped contains - * an executable region. - */ - pkm.pm_address = (uintptr_t) NULL; - if (vm_map_lookup_entry(map, addr, &entry)) { - for (; - entry != &map->header && entry->start < addr + size; - entry = entry->next) { - if (vm_map_check_protection(map, entry->start, - entry->end, VM_PROT_EXECUTE) == TRUE) { - pkm.pm_address = (uintptr_t) addr; - pkm.pm_size = (size_t) size; - break; + pmc_handled = false; + if (PMC_HOOK_INSTALLED(PMC_FN_MUNMAP)) { + pmc_handled = true; + /* + * Inform hwpmc if the address range being unmapped contains + * an executable region. + */ + pkm.pm_address = (uintptr_t) NULL; + if (vm_map_lookup_entry(map, addr, &entry)) { + for (; + entry != &map->header && entry->start < addr + size; + entry = entry->next) { + if (vm_map_check_protection(map, entry->start, + entry->end, VM_PROT_EXECUTE) == TRUE) { + pkm.pm_address = (uintptr_t) addr; + pkm.pm_size = (size_t) size; + break; + } } } } @@ -572,14 +577,16 @@ sys_munmap(td, uap) vm_map_delete(map, addr, addr + size); #ifdef HWPMC_HOOKS - /* downgrade the lock to prevent a LOR with the pmc-sx lock */ - vm_map_lock_downgrade(map); - if (pkm.pm_address != (uintptr_t) NULL) - PMC_CALL_HOOK(td, PMC_FN_MUNMAP, (void *) &pkm); - vm_map_unlock_read(map); -#else - vm_map_unlock(map); + if (__predict_false(pmc_handled)) { + /* downgrade the lock to prevent a LOR with the pmc-sx lock */ + vm_map_lock_downgrade(map); + if (pkm.pm_address != (uintptr_t) NULL) + PMC_CALL_HOOK(td, PMC_FN_MUNMAP, (void *) &pkm); + vm_map_unlock_read(map); + } else #endif + vm_map_unlock(map); + /* vm_map_delete returns nothing but KERN_SUCCESS anyway */ return (0); }
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201701242200.v0OM0GRO042084>