diff options
author | Ludovic Courtès <ludo@gnu.org> | 2010-07-17 16:24:39 +0200 |
---|---|---|
committer | Samuel Thibault <samuel.thibault@ens-lyon.org> | 2011-04-03 15:47:34 +0000 |
commit | a8744157214a302d84c8959b1ae99abe3ae2d7d2 (patch) | |
tree | 1cfebbd27e311beee3a6a1660ff7d08624ca20d8 /mach-defpager/wiring.c | |
parent | bebc64a9a0f064a0e5f8a3549aa01aa9ac79a2e9 (diff) | |
download | hurd-a8744157214a302d84c8959b1ae99abe3ae2d7d2.tar.gz hurd-a8744157214a302d84c8959b1ae99abe3ae2d7d2.tar.bz2 hurd-a8744157214a302d84c8959b1ae99abe3ae2d7d2.zip |
Remove `serverboot'; fix "make dist" in `mach-defpager'.
* serverboot/default_pager.c, serverboot/kalloc.c, serverboot/queue.h,
serverboot/wiring.c, serverboot/wiring.h: Move to `mach-defpager/'.
* serverboot/Makefile, serverboot/assert.h, serverboot/bootstrap.c,
serverboot/bunzip2.c, serverboot/def_pager_setup.c, serverboot/defs.h,
serverboot/dir.h, serverboot/disk_inode.h,
serverboot/disk_inode_ffs.h, serverboot/elf-load.c, serverboot/exec.c,
serverboot/ext2_file_io.c, serverboot/ffs_compat.c,
serverboot/ffs_compat.h, serverboot/ffs_file_io.c,
serverboot/file_io.c, serverboot/file_io.h, serverboot/fs.h,
serverboot/gets.c, serverboot/gunzip.c, serverboot/load.c,
serverboot/mach-exec.h, serverboot/minix_ffs_compat.c,
serverboot/minix_ffs_compat.h, serverboot/minix_file_io.c,
serverboot/minix_fs.h, serverboot/minix_super.h, serverboot/panic.c,
serverboot/strfcns.c: Remove.
* mach-defpager/Makefile (LCLHDRS): New variable.
(vpath): Remove.
(CPPFLAGS): Remove `-I$(srcdir)/../serverboot'.
* mach-defpager/setup.c (page_aligned): Make public.
Diffstat (limited to 'mach-defpager/wiring.c')
-rw-r--r-- | mach-defpager/wiring.c | 175 |
1 files changed, 175 insertions, 0 deletions
diff --git a/mach-defpager/wiring.c b/mach-defpager/wiring.c new file mode 100644 index 00000000..585a3075 --- /dev/null +++ b/mach-defpager/wiring.c @@ -0,0 +1,175 @@ +/* + * Mach Operating System + * Copyright (c) 1991 Carnegie Mellon University + * All Rights Reserved. + * + * Permission to use, copy, modify and distribute this software and its + * documentation is hereby granted, provided that both the copyright + * notice and this permission notice appear in all copies of the + * software, derivative works or modified versions, and any portions + * thereof, and that both notices appear in supporting documentation. + * + * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" + * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR + * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. + * + * Carnegie Mellon requests users of this software to return to + * + * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU + * School of Computer Science + * Carnegie Mellon University + * Pittsburgh PA 15213-3890 + * + * any improvements or extensions that they make and grant Carnegie Mellon + * the rights to redistribute these changes. + */ +/* + * Package to wire current task's memory. + */ +#include <mach.h> +#include <mach_init.h> +#include <mach/machine/vm_param.h> + +mach_port_t this_task; /* our task */ +mach_port_t priv_host_port = MACH_PORT_NULL; + /* the privileged host port */ + +void +wire_setup(host_priv) + mach_port_t host_priv; +{ + priv_host_port = host_priv; + this_task = mach_task_self(); +} + +void +wire_memory(start, size, prot) + vm_address_t start; + vm_size_t size; + vm_prot_t prot; +{ + kern_return_t kr; + + if (priv_host_port == MACH_PORT_NULL) + return; + + kr = vm_wire(priv_host_port, + this_task, + start, size, prot); + if (kr != KERN_SUCCESS) + panic("mem_wire: %d", kr); +} + +void +wire_thread() +{ + kern_return_t kr; + + if (priv_host_port == MACH_PORT_NULL) + return; + + kr = thread_wire(priv_host_port, + mach_thread_self(), + TRUE); + if (kr != KERN_SUCCESS) + panic("wire_thread: %d", kr); +} + +void +wire_all_memory() +{ + register kern_return_t kr; + vm_offset_t address; + vm_size_t size; + vm_prot_t protection; + vm_prot_t max_protection; + vm_inherit_t inheritance; + boolean_t is_shared; + memory_object_name_t object; + vm_offset_t offset; + + if (priv_host_port == MACH_PORT_NULL) + return; + + /* iterate thru all regions, wiring */ + address = 0; + while ( + (kr = vm_region(this_task, &address, + &size, + &protection, + &max_protection, + &inheritance, + &is_shared, + &object, + &offset)) + == KERN_SUCCESS) + { + if (MACH_PORT_VALID(object)) + (void) mach_port_deallocate(this_task, object); + if (protection != VM_PROT_NONE) + { + /* The VM system cannot cope with a COW fault on another + unrelated virtual copy happening later when we have + wired down the original page. So we must touch all our + pages before wiring to make sure that only we will ever + use them. */ + void *page; + if (!(protection & VM_PROT_WRITE)) + { + kr = vm_protect(this_task, address, size, + 0, max_protection); + } + for (page = (void *) address; + page < (void *) (address + size); + page += vm_page_size) + *(volatile int *) page = *(int *) page; + + wire_memory(address, size, protection); + + if (!(protection & VM_PROT_WRITE)) + { + kr = vm_protect(this_task, address, size, + 0, protection); + } + } + address += size; + } +} + +/* + * Alias for vm_allocate to return wired memory. + */ +kern_return_t +vm_allocate(task, address, size, anywhere) + task_t task; + vm_address_t *address; + vm_size_t size; + boolean_t anywhere; +{ + kern_return_t kr; + + if (anywhere) + *address = VM_MIN_ADDRESS; + kr = vm_map(task, + address, size, (vm_offset_t) 0, anywhere, + MEMORY_OBJECT_NULL, (vm_offset_t)0, FALSE, + VM_PROT_DEFAULT, VM_PROT_ALL, VM_INHERIT_DEFAULT); + if (kr != KERN_SUCCESS) + return kr; + + if (task == this_task) + (void) vm_wire(priv_host_port, task, *address, size, + VM_PROT_DEFAULT); + return KERN_SUCCESS; +} + +/* Other versions of this function in libc... */ +kern_return_t +__vm_allocate (task, address, size, anywhere) + task_t task; + vm_address_t *address; + vm_size_t size; + boolean_t anywhere; +{ + return vm_allocate (task, address, size, anywhere); +} |