root/compat/osf1/osf1_mmap.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. osf1_sys_madvise
  2. osf1_sys_mmap
  3. osf1_sys_mprotect

    1 /* $OpenBSD: osf1_mmap.c,v 1.6 2006/03/04 19:33:21 miod Exp $ */
    2 /* $NetBSD: osf1_mmap.c,v 1.5 2000/04/11 05:26:27 chs Exp $ */
    3 
    4 /*
    5  * Copyright (c) 1999 Christopher G. Demetriou.  All rights reserved.
    6  *
    7  * Redistribution and use in source and binary forms, with or without
    8  * modification, are permitted provided that the following conditions
    9  * are met:
   10  * 1. Redistributions of source code must retain the above copyright
   11  *    notice, this list of conditions and the following disclaimer.
   12  * 2. Redistributions in binary form must reproduce the above copyright
   13  *    notice, this list of conditions and the following disclaimer in the
   14  *    documentation and/or other materials provided with the distribution.
   15  * 3. All advertising materials mentioning features or use of this software
   16  *    must display the following acknowledgement:
   17  *      This product includes software developed by Christopher G. Demetriou
   18  *      for the NetBSD Project.
   19  * 4. The name of the author may not be used to endorse or promote products
   20  *    derived from this software without specific prior written permission
   21  *
   22  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
   23  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   24  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
   25  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
   26  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
   27  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
   28  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
   29  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
   30  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
   31  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
   32  */
   33 
   34 #include <sys/param.h>
   35 #include <sys/systm.h>
   36 #include <sys/proc.h>
   37 #include <sys/mman.h>
   38 #include <sys/mount.h>
   39 #include <sys/syscallargs.h>
   40 #include <uvm/uvm.h>
   41 
   42 #include <compat/osf1/osf1.h>
   43 #include <compat/osf1/osf1_syscallargs.h>
   44 #include <compat/osf1/osf1_cvt.h>
   45 
   46 int
   47 osf1_sys_madvise(p, v, retval)
   48         struct proc *p;
   49         void *v;
   50         register_t *retval;
   51 {
   52         struct osf1_sys_madvise_args *uap = v;
   53         struct sys_madvise_args a;
   54         int error;
   55 
   56         SCARG(&a, addr) = SCARG(uap, addr);
   57         SCARG(&a, len) = SCARG(uap, len);
   58 
   59         error = 0;
   60         switch (SCARG(uap, behav)) {
   61         case OSF1_MADV_NORMAL:
   62                 SCARG(&a, behav) = MADV_NORMAL;
   63                 break;
   64 
   65         case OSF1_MADV_RANDOM:
   66                 SCARG(&a, behav) = MADV_RANDOM;
   67                 break;
   68 
   69         case OSF1_MADV_SEQUENTIAL:
   70                 SCARG(&a, behav) = MADV_SEQUENTIAL;
   71                 break;
   72 
   73         case OSF1_MADV_WILLNEED:
   74                 SCARG(&a, behav) = MADV_WILLNEED;
   75                 break;
   76 
   77         case OSF1_MADV_DONTNEED_COMPAT:
   78                 SCARG(&a, behav) = MADV_DONTNEED;
   79                 break;
   80 #if 0
   81         case OSF1_MADV_SPACEAVAIL:
   82                 SCARG(&a, behav) = MADV_SPACEAVAIL;
   83                 break;
   84 #endif
   85         case OSF1_MADV_DONTNEED:
   86                 /*
   87                  * XXX not supported.  In Digital UNIX, this flushes all
   88                  * XXX data in the region and replaces it with ZFOD pages.
   89                  */
   90                 error = EINVAL;
   91                 break;
   92 
   93         default:
   94                 error = EINVAL;
   95                 break;
   96         }
   97 
   98         if (error == 0) {
   99                 error = sys_madvise(p, &a, retval);
  100 
  101                 /*
  102                  * NetBSD madvise() currently always returns ENOSYS.
  103                  * Digital UNIX says that non-operational requests (i.e.
  104                  * valid, but unimplemented 'behav') will return success.
  105                  */
  106                 if (error == ENOSYS)
  107                         error = 0;
  108         }
  109         return (error);
  110 }
  111 
  112 int
  113 osf1_sys_mmap(p, v, retval)
  114         struct proc *p;
  115         void *v;
  116         register_t *retval;
  117 {
  118         struct osf1_sys_mmap_args *uap = v;
  119         struct sys_mmap_args a;
  120         unsigned long leftovers;
  121 
  122         SCARG(&a, addr) = SCARG(uap, addr);
  123         SCARG(&a, len) = SCARG(uap, len);
  124         SCARG(&a, fd) = SCARG(uap, fd);
  125         SCARG(&a, pad) = 0;
  126         SCARG(&a, pos) = SCARG(uap, pos);
  127 
  128         /* translate prot */
  129         SCARG(&a, prot) = emul_flags_translate(osf1_mmap_prot_xtab,
  130             SCARG(uap, prot), &leftovers);
  131         if (leftovers != 0)
  132                 return (EINVAL);
  133 
  134         /* translate flags */
  135         SCARG(&a, flags) = emul_flags_translate(osf1_mmap_flags_xtab,
  136             SCARG(uap, flags), &leftovers);
  137         if (leftovers != 0)
  138                 return (EINVAL);
  139 
  140         /*
  141          * XXX The following code is evil.
  142          *
  143          * The OSF/1 mmap() function attempts to map non-fixed entries
  144          * near the address that the user specified.  Therefore, for
  145          * non-fixed entries we try to find space in the address space
  146          * starting at that address.  If the user specified zero, we
  147          * start looking at at least NBPG, so that programs can't
  148          * accidentally live through deferencing NULL.
  149          *
  150          * The need for this kludgery is increased by the fact that
  151          * the loader data segment is mapped at
  152          * (end of user address space) - 1G, MAXDSIZ is 1G, and
  153          * the VM system tries allocate non-fixed mappings _AFTER_
  154          * (start of data) + MAXDSIZ.  With the loader, of course,
  155          * that means that it'll start trying at
  156          * (end of user address space), and will never succeed!
  157          *
  158          * Notes:
  159          *
  160          * * Though we find space here, if something else (e.g. a second
  161          *   thread) were mucking with the address space the mapping
  162          *   we found might be used by another mmap(), and this call
  163          *   would clobber that region.
  164          *
  165          * * In general, tricks like this only work for MAP_ANON mappings,
  166          *   because of sharing/cache issues.  That's not a problem on
  167          *   the Alpha, and though it's not good style to abuse that fact,
  168          *   there's little choice.
  169          *
  170          * * In order for this to be done right, the VM system should
  171          *   really try to use the requested 'addr' passed in to mmap()
  172          *   as a hint, even if non-fixed.  If it's passed as zero,
  173          *   _maybe_ then try (start of data) + MAXDSIZ, or maybe
  174          *   provide a better way to avoid the data region altogether.
  175          */
  176         if ((SCARG(&a, flags) & MAP_FIXED) == 0) {
  177                 vaddr_t addr = round_page((vaddr_t)SCARG(&a, addr));
  178                 vsize_t size = round_page((vsize_t)SCARG(&a, len));
  179                 int fixed = 0;
  180 
  181                 vm_map_lock(&p->p_vmspace->vm_map);
  182 
  183                 /* if non-NULL address given, start looking there */
  184                 /* XXX - UVM */
  185                 if (addr != 0 && uvm_map_findspace(&p->p_vmspace->vm_map,
  186                     addr, size, &addr, NULL, 0, 0, 0) != NULL) {
  187                         fixed = 1;
  188                         goto done;
  189                 }
  190 
  191                 /* didn't find anything.  take it again from the top. */
  192                 if (uvm_map_findspace(&p->p_vmspace->vm_map, NBPG, size, &addr,
  193                     NULL, 0, 0, 0) != NULL) {
  194                         fixed = 1;
  195                         goto done;
  196                 }
  197 
  198 done:
  199                 vm_map_unlock(&p->p_vmspace->vm_map);
  200                 if (fixed) {
  201                         SCARG(&a, flags) |= MAP_FIXED;
  202                         SCARG(&a, addr) = (void *)addr;
  203                 }
  204         }
  205 
  206         return sys_mmap(p, &a, retval);
  207 }
  208 
  209 int
  210 osf1_sys_mprotect(p, v, retval)
  211         struct proc *p;
  212         void *v;
  213         register_t *retval;
  214 {
  215         struct osf1_sys_mprotect_args *uap = v;
  216         struct sys_mprotect_args a;
  217         unsigned long leftovers;
  218 
  219         SCARG(&a, addr) = SCARG(uap, addr);
  220         SCARG(&a, len) = SCARG(uap, len);
  221 
  222         /* translate prot */
  223         SCARG(&a, prot) = emul_flags_translate(osf1_mmap_prot_xtab,
  224             SCARG(uap, prot), &leftovers);
  225         if (leftovers != 0)
  226                 return (EINVAL);
  227 
  228         return sys_mprotect(p, &a, retval);
  229 }

/* [<][>][^][v][top][bottom][index][help] */