vm_unix.c revision 1542
1336809Sdim/* 2336809Sdim * Copyright (c) 1988 University of Utah. 3353358Sdim * Copyright (c) 1991, 1993 4353358Sdim * The Regents of the University of California. All rights reserved. 5353358Sdim * 6336809Sdim * This code is derived from software contributed to Berkeley by 7336809Sdim * the Systems Programming Group of the University of Utah Computer 8336809Sdim * Science Department. 9336809Sdim * 10336809Sdim * Redistribution and use in source and binary forms, with or without 11336809Sdim * modification, are permitted provided that the following conditions 12336809Sdim * are met: 13336809Sdim * 1. Redistributions of source code must retain the above copyright 14336809Sdim * notice, this list of conditions and the following disclaimer. 15336809Sdim * 2. Redistributions in binary form must reproduce the above copyright 16336809Sdim * notice, this list of conditions and the following disclaimer in the 17336809Sdim * documentation and/or other materials provided with the distribution. 18336809Sdim * 3. All advertising materials mentioning features or use of this software 19336809Sdim * must display the following acknowledgement: 20336809Sdim * This product includes software developed by the University of 21336809Sdim * California, Berkeley and its contributors. 22336809Sdim * 4. Neither the name of the University nor the names of its contributors 23336809Sdim * may be used to endorse or promote products derived from this software 24336809Sdim * without specific prior written permission. 25336809Sdim * 26336809Sdim * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 27336809Sdim * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 28336809Sdim * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 29336809Sdim * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 30336809Sdim * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 31336809Sdim * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 32336809Sdim * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 33336809Sdim * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 34336809Sdim * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 35336809Sdim * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 36336809Sdim * SUCH DAMAGE. 37336809Sdim * 38336809Sdim * from: Utah $Hdr: vm_unix.c 1.1 89/11/07$ 39336809Sdim * 40336809Sdim * @(#)vm_unix.c 8.1 (Berkeley) 6/11/93 41336809Sdim */ 42336809Sdim 43336809Sdim/* 44336809Sdim * Traditional sbrk/grow interface to VM 45336809Sdim */ 46336809Sdim#include <sys/param.h> 47336809Sdim#include <sys/systm.h> 48336809Sdim#include <sys/proc.h> 49336809Sdim#include <sys/resourcevar.h> 50336809Sdim 51336809Sdim#include <vm/vm.h> 52336809Sdim 53336809Sdimstruct obreak_args { 54336809Sdim char *nsiz; 55336809Sdim}; 56336809Sdim/* ARGSUSED */ 57336809Sdimint 58336809Sdimobreak(p, uap, retval) 59336809Sdim struct proc *p; 60336809Sdim struct obreak_args *uap; 61336809Sdim int *retval; 62336809Sdim{ 63336809Sdim register struct vmspace *vm = p->p_vmspace; 64336809Sdim vm_offset_t new, old; 65336809Sdim int rv; 66336809Sdim register int diff; 67336809Sdim 68336809Sdim old = (vm_offset_t)vm->vm_daddr; 69336809Sdim new = round_page(uap->nsiz); 70336809Sdim if ((int)(new - old) > p->p_rlimit[RLIMIT_DATA].rlim_cur) 71336809Sdim return(ENOMEM); 72336809Sdim old = round_page(old + ctob(vm->vm_dsize)); 73336809Sdim diff = new - old; 74336809Sdim if (diff > 0) { 75336809Sdim rv = vm_allocate(&vm->vm_map, &old, diff, FALSE); 76336809Sdim if (rv != KERN_SUCCESS) { 77336809Sdim uprintf("sbrk: grow failed, return = %d\n", rv); 78336809Sdim return(ENOMEM); 79336809Sdim } 80336809Sdim vm->vm_dsize += btoc(diff); 81336809Sdim } else if (diff < 0) { 82336809Sdim diff = -diff; 83336809Sdim rv = vm_deallocate(&vm->vm_map, new, diff); 84336809Sdim if (rv != KERN_SUCCESS) { 85336809Sdim uprintf("sbrk: shrink failed, return = %d\n", rv); 86336809Sdim return(ENOMEM); 87336809Sdim } 88336809Sdim vm->vm_dsize -= btoc(diff); 89336809Sdim } 90336809Sdim return(0); 91336809Sdim} 92336809Sdim 93336809Sdim/* 94336809Sdim * Enlarge the "stack segment" to include the specified 95336809Sdim * stack pointer for the process. 96336809Sdim */ 97336809Sdimint 98336809Sdimgrow(p, sp) 99336809Sdim struct proc *p; 100336809Sdim unsigned sp; 101336809Sdim{ 102336809Sdim register struct vmspace *vm = p->p_vmspace; 103336809Sdim register int si; 104336809Sdim 105336809Sdim /* 106336809Sdim * For user defined stacks (from sendsig). 107336809Sdim */ 108336809Sdim if (sp < (unsigned)vm->vm_maxsaddr) 109336809Sdim return (0); 110336809Sdim /* 111336809Sdim * For common case of already allocated (from trap). 112336809Sdim */ 113336809Sdim if (sp >= USRSTACK - ctob(vm->vm_ssize)) 114336809Sdim return (1); 115336809Sdim /* 116336809Sdim * Really need to check vs limit and increment stack size if ok. 117336809Sdim */ 118336809Sdim si = clrnd(btoc(USRSTACK-sp) - vm->vm_ssize); 119336809Sdim if (vm->vm_ssize + si > btoc(p->p_rlimit[RLIMIT_STACK].rlim_cur)) 120336809Sdim return (0); 121336809Sdim vm->vm_ssize += si; 122336809Sdim return (1); 123336809Sdim} 124336809Sdim 125336809Sdimstruct ovadvise_args { 126336809Sdim int anom; 127336809Sdim}; 128336809Sdim/* ARGSUSED */ 129336809Sdimint 130336809Sdimovadvise(p, uap, retval) 131336809Sdim struct proc *p; 132336809Sdim struct ovadvise_args *uap; 133336809Sdim int *retval; 134336809Sdim{ 135336809Sdim 136336809Sdim return (EINVAL); 137336809Sdim} 138336809Sdim