summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormec <none@none>2008-02-19 13:14:17 -0800
committermec <none@none>2008-02-19 13:14:17 -0800
commit60946fe0e0cab23f683e9de92451aa45b7913135 (patch)
tree66ca7e367ff1029f93715ef6334293d405c64f89
parentc0889d7a91fa87e1cb7ef4457629b0cb51d47b50 (diff)
downloadillumos-gate-60946fe0e0cab23f683e9de92451aa45b7913135.tar.gz
PSARC 2006/123 Mmap compatibility
5003415 Provide a MAP_NOOVERMAP option for mmap()
-rw-r--r--usr/src/uts/common/exec/elf/elf.c4
-rw-r--r--usr/src/uts/common/fs/cachefs/cachefs_vnops.c18
-rw-r--r--usr/src/uts/common/fs/gfs.c14
-rw-r--r--usr/src/uts/common/fs/hsfs/hsfs_vnops.c18
-rw-r--r--usr/src/uts/common/fs/mntfs/mntvnops.c12
-rw-r--r--usr/src/uts/common/fs/nfs/nfs3_vnops.c18
-rw-r--r--usr/src/uts/common/fs/nfs/nfs4_vnops.c16
-rw-r--r--usr/src/uts/common/fs/nfs/nfs_vnops.c18
-rw-r--r--usr/src/uts/common/fs/pcfs/pc_vnops.c17
-rw-r--r--usr/src/uts/common/fs/specfs/specvnops.c38
-rw-r--r--usr/src/uts/common/fs/tmpfs/tmp_vnops.c15
-rw-r--r--usr/src/uts/common/fs/udfs/udf_vnops.c18
-rw-r--r--usr/src/uts/common/fs/ufs/ufs_vnops.c26
-rw-r--r--usr/src/uts/common/fs/zfs/zfs_vnops.c17
-rw-r--r--usr/src/uts/common/io/ksyms.c13
-rw-r--r--usr/src/uts/common/io/mem.c29
-rw-r--r--usr/src/uts/common/io/smbios.c9
-rw-r--r--usr/src/uts/common/os/grow.c60
-rw-r--r--usr/src/uts/common/os/schedctl.c2
-rw-r--r--usr/src/uts/common/sys/vmsystm.h10
-rw-r--r--usr/src/uts/common/vm/seg_dev.c22
21 files changed, 159 insertions, 235 deletions
diff --git a/usr/src/uts/common/exec/elf/elf.c b/usr/src/uts/common/exec/elf/elf.c
index 7813bf00df..ab19c025af 100644
--- a/usr/src/uts/common/exec/elf/elf.c
+++ b/usr/src/uts/common/exec/elf/elf.c
@@ -20,7 +20,7 @@
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -1106,7 +1106,7 @@ mapelfexec(
{
Phdr *phdr;
int i, prot, error;
- caddr_t addr;
+ caddr_t addr = NULL;
size_t zfodsz;
int ptload = 0;
int page;
diff --git a/usr/src/uts/common/fs/cachefs/cachefs_vnops.c b/usr/src/uts/common/fs/cachefs/cachefs_vnops.c
index 795c70dc3d..6150b51381 100644
--- a/usr/src/uts/common/fs/cachefs/cachefs_vnops.c
+++ b/usr/src/uts/common/fs/cachefs/cachefs_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -8194,18 +8194,10 @@ cachefs_map(struct vnode *vp, offset_t off, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto out;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto out;
}
/*
diff --git a/usr/src/uts/common/fs/gfs.c b/usr/src/uts/common/fs/gfs.c
index c56fb004f0..54aaa6854e 100644
--- a/usr/src/uts/common/fs/gfs.c
+++ b/usr/src/uts/common/fs/gfs.c
@@ -20,7 +20,7 @@
*/
/* Portions Copyright 2007 Shivakumar GN */
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -1022,14 +1022,10 @@ gfs_vop_map(vnode_t *vp, offset_t off, struct as *as, caddr_t *addrp,
* Find appropriate address if needed, otherwise clear address range.
*/
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, (offset_t)off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- (void) as_unmap(as, *addrp, len);
+ rv = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (rv != 0) {
+ as_rangeunlock(as);
+ return (rv);
}
/*
diff --git a/usr/src/uts/common/fs/hsfs/hsfs_vnops.c b/usr/src/uts/common/fs/hsfs/hsfs_vnops.c
index 7394b3e1ee..8651b88ee9 100644
--- a/usr/src/uts/common/fs/hsfs/hsfs_vnops.c
+++ b/usr/src/uts/common/fs/hsfs/hsfs_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -1814,18 +1814,10 @@ hsfs_map(
return (EAGAIN);
as_rangelock(as);
-
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/mntfs/mntvnops.c b/usr/src/uts/common/fs/mntfs/mntvnops.c
index 9e519167cf..dcfce13ab5 100644
--- a/usr/src/uts/common/fs/mntfs/mntvnops.c
+++ b/usr/src/uts/common/fs/mntfs/mntvnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -158,13 +158,13 @@ mntfs_optprint(struct vfs *vfsp, char *buf)
else
optinbuf = 1;
buf += snprintf(buf, MAX_MNTOPT_STR,
- "%s", mop->mo_name);
+ "%s", mop->mo_name);
/*
* print option value if there is one
*/
if (mop->mo_arg != NULL) {
buf += snprintf(buf, MAX_MNTOPT_STR, "=%s",
- mop->mo_arg);
+ mop->mo_arg);
}
}
}
@@ -445,7 +445,7 @@ mntfs_mapin(char *base, size_t size)
{
size_t rlen = roundup(size, PAGESIZE);
struct as *as = curproc->p_as;
- char *addr;
+ char *addr = NULL;
as_rangelock(as);
map_addr(&addr, rlen, 0, 1, 0);
@@ -466,11 +466,11 @@ mntfs_freesnap(mntsnap_t *snap)
{
if (snap->mnts_text != NULL)
(void) as_unmap(curproc->p_as, snap->mnts_text,
- roundup(snap->mnts_textsize, PAGESIZE));
+ roundup(snap->mnts_textsize, PAGESIZE));
snap->mnts_textsize = snap->mnts_count = 0;
if (snap->mnts_metadata != NULL)
(void) as_unmap(curproc->p_as, snap->mnts_metadata,
- roundup(snap->mnts_metasize, PAGESIZE));
+ roundup(snap->mnts_metasize, PAGESIZE));
snap->mnts_metasize = 0;
}
diff --git a/usr/src/uts/common/fs/nfs/nfs3_vnops.c b/usr/src/uts/common/fs/nfs/nfs3_vnops.c
index fed70c1106..54a0a40b5f 100644
--- a/usr/src/uts/common/fs/nfs/nfs3_vnops.c
+++ b/usr/src/uts/common/fs/nfs/nfs3_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -5218,18 +5218,10 @@ nfs3_map(vnode_t *vp, offset_t off, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if (!(flags & MAP_FIXED)) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto done;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto done;
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/nfs/nfs4_vnops.c b/usr/src/uts/common/fs/nfs/nfs4_vnops.c
index 1186d591af..a9c27d8502 100644
--- a/usr/src/uts/common/fs/nfs/nfs4_vnops.c
+++ b/usr/src/uts/common/fs/nfs/nfs4_vnops.c
@@ -10416,18 +10416,10 @@ nfs4_map(vnode_t *vp, offset_t off, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if (!(flags & MAP_FIXED)) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto done;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto done;
}
if (vp->v_type == VREG) {
diff --git a/usr/src/uts/common/fs/nfs/nfs_vnops.c b/usr/src/uts/common/fs/nfs/nfs_vnops.c
index 1dfda0dded..ea8b2fb974 100644
--- a/usr/src/uts/common/fs/nfs/nfs_vnops.c
+++ b/usr/src/uts/common/fs/nfs/nfs_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*
* Copyright (c) 1983,1984,1985,1986,1987,1988,1989 AT&T.
@@ -4314,18 +4314,10 @@ nfs_map(vnode_t *vp, offset_t off, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if (!(flags & MAP_FIXED)) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto done;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto done;
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/pcfs/pc_vnops.c b/usr/src/uts/common/fs/pcfs/pc_vnops.c
index 9f77542636..3fa7e8d143 100644
--- a/usr/src/uts/common/fs/pcfs/pc_vnops.c
+++ b/usr/src/uts/common/fs/pcfs/pc_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -1865,17 +1865,10 @@ pcfs_map(
return (ENXIO);
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/specfs/specvnops.c b/usr/src/uts/common/fs/specfs/specvnops.c
index d452246135..bda8d893f9 100644
--- a/usr/src/uts/common/fs/specfs/specvnops.c
+++ b/usr/src/uts/common/fs/specfs/specvnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -2255,21 +2255,11 @@ spec_segmap(
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- /*
- * Pick an address w/o worrying about
- * any vac alignment constraints.
- */
- map_addr(addrp, len, (offset_t)off, 0, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User-specified address; blow away any previous mappings.
- */
- (void) as_unmap(as, *addrp, len);
+ /* Pick an address w/o worrying about any vac alignment constraints. */
+ error = choose_addr(as, addrp, len, off, ADDR_NOVACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
dev_a.mapfunc = mapfunc;
@@ -2407,18 +2397,10 @@ spec_map(
return (ENXIO);
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User-specified address; blow away any
- * previous mappings.
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
vn_a.vp = cvp;
diff --git a/usr/src/uts/common/fs/tmpfs/tmp_vnops.c b/usr/src/uts/common/fs/tmpfs/tmp_vnops.c
index c6fee2b1dd..3248df1b26 100644
--- a/usr/src/uts/common/fs/tmpfs/tmp_vnops.c
+++ b/usr/src/uts/common/fs/tmpfs/tmp_vnops.c
@@ -2174,17 +2174,10 @@ tmp_map(
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, (offset_t)off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/udfs/udf_vnops.c b/usr/src/uts/common/fs/udfs/udf_vnops.c
index 2a2822eb3f..9496e9a86d 100644
--- a/usr/src/uts/common/fs/udfs/udf_vnops.c
+++ b/usr/src/uts/common/fs/udfs/udf_vnops.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -2048,18 +2048,10 @@ udf_map(
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto end;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto end;
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/fs/ufs/ufs_vnops.c b/usr/src/uts/common/fs/ufs/ufs_vnops.c
index 2bbd577bf2..827ef4c81a 100644
--- a/usr/src/uts/common/fs/ufs/ufs_vnops.c
+++ b/usr/src/uts/common/fs/ufs/ufs_vnops.c
@@ -5601,22 +5601,16 @@ retry_map:
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- error = ENOMEM;
- goto out;
- }
- } else {
- /*
- * User specified address - blow away any previous mappings.
- * If we are retrying (because ufs_lockfs_trybegin failed in
- * the previous attempt), some other thread could have grabbed
- * the same VA range. In that case, we would unmap the valid
- * VA range, that is ok.
- */
- (void) as_unmap(as, *addrp, len);
+ /*
+ * Note that if we are retrying (because ufs_lockfs_trybegin failed in
+ * the previous attempt), some other thread could have grabbed
+ * the same VA range if MAP_FIXED is set. In that case, choose_addr
+ * would unmap the valid VA range, that is ok.
+ */
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ goto out;
}
/*
diff --git a/usr/src/uts/common/fs/zfs/zfs_vnops.c b/usr/src/uts/common/fs/zfs/zfs_vnops.c
index 267b4de114..811115fd00 100644
--- a/usr/src/uts/common/fs/zfs/zfs_vnops.c
+++ b/usr/src/uts/common/fs/zfs/zfs_vnops.c
@@ -4108,18 +4108,11 @@ zfs_map(vnode_t *vp, offset_t off, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- map_addr(addrp, len, off, 1, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- ZFS_EXIT(zfsvfs);
- return (ENOMEM);
- }
- } else {
- /*
- * User specified address - blow away any previous mappings
- */
- (void) as_unmap(as, *addrp, len);
+ error = choose_addr(as, addrp, len, off, ADDR_VACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ ZFS_EXIT(zfsvfs);
+ return (error);
}
vn_a.vp = vp;
diff --git a/usr/src/uts/common/io/ksyms.c b/usr/src/uts/common/io/ksyms.c
index 2a8bc0bc30..92bb96ab83 100644
--- a/usr/src/uts/common/io/ksyms.c
+++ b/usr/src/uts/common/io/ksyms.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -167,7 +166,7 @@ ksyms_buflist_alloc(ksyms_buflist_hdr_t *hdr, size_t size)
static char *
ksyms_asmap(struct as *as, size_t rlen)
{
- char *addr;
+ char *addr = NULL;
as_rangelock(as);
map_addr(&addr, rlen, 0, 1, 0);
@@ -223,7 +222,7 @@ ksyms_open(dev_t *devp, int flag, int otyp, struct cred *cred)
ksyms_buflist_hdr_t hdr;
bzero(&hdr, sizeof (struct ksyms_buflist_hdr));
list_create(&hdr.blist, PAGESIZE,
- offsetof(ksyms_buflist_t, buflist_node));
+ offsetof(ksyms_buflist_t, buflist_node));
ASSERT(getminor(*devp) == 0);
@@ -345,7 +344,7 @@ ksyms_segmap(dev_t dev, off_t off, struct as *as, caddr_t *addrp, off_t len,
return (ENOTSUP);
if (off < 0 || len <= 0 || off > kip->ksyms_size ||
- len > kip->ksyms_size - off)
+ len > kip->ksyms_size - off)
return (EINVAL);
rlen = roundup(len, PAGESIZE);
diff --git a/usr/src/uts/common/io/mem.c b/usr/src/uts/common/io/mem.c
index 1be161f8f9..36bf6819d7 100644
--- a/usr/src/uts/common/io/mem.c
+++ b/usr/src/uts/common/io/mem.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -826,24 +826,15 @@ mmsegmap(dev_t dev, off_t off, struct as *as, caddr_t *addrp, off_t len,
minor = getminor(dev);
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- /*
- * No need to worry about vac alignment on /dev/zero
- * since this is a "clone" object that doesn't yet exist.
- */
- map_addr(addrp, len, (offset_t)off,
- (minor == M_MEM) || (minor == M_KMEM), flags);
-
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User specified address -
- * Blow away any previous mappings.
- */
- (void) as_unmap(as, *addrp, len);
+ /*
+ * No need to worry about vac alignment on /dev/zero
+ * since this is a "clone" object that doesn't yet exist.
+ */
+ error = choose_addr(as, addrp, len, off,
+ (minor == M_MEM) || (minor == M_KMEM), flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
switch (minor) {
diff --git a/usr/src/uts/common/io/smbios.c b/usr/src/uts/common/io/smbios.c
index 533975e418..e7e68f3532 100644
--- a/usr/src/uts/common/io/smbios.c
+++ b/usr/src/uts/common/io/smbios.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -21,7 +20,7 @@
*/
/*
- * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -171,7 +170,7 @@ smb_segmap(dev_t dev, off_t off, struct as *as, caddr_t *addrp, off_t len,
smb_clone_t *cp = &smb_clones[getminor(dev)];
size_t alen = P2ROUNDUP(len, PAGESIZE);
- caddr_t addr;
+ caddr_t addr = NULL;
iovec_t iov;
uio_t uio;
diff --git a/usr/src/uts/common/os/grow.c b/usr/src/uts/common/os/grow.c
index 0033b11ff4..2b82aaba0d 100644
--- a/usr/src/uts/common/os/grow.c
+++ b/usr/src/uts/common/os/grow.c
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -230,7 +230,7 @@ brk_internal(caddr_t nva, uint_t brkszc)
*/
nva = (caddr_t)P2ROUNDUP((uintptr_t)nva, pgsz);
ova = (caddr_t)P2ROUNDUP((uintptr_t)(p->p_brkbase + p->p_brksize),
- PAGESIZE);
+ PAGESIZE);
if ((nva < p->p_brkbase) || (size > p->p_brksize &&
size > as_rctl)) {
@@ -490,6 +490,40 @@ grow_internal(caddr_t sp, uint_t growszc)
}
/*
+ * Find address for user to map.
+ * If MAP_FIXED is not specified, we can pick any address we want, but we will
+ * first try the value in *addrp if it is non-NULL. Thus this is implementing
+ * a way to try and get a preferred address.
+ */
+int
+choose_addr(struct as *as, caddr_t *addrp, size_t len, offset_t off,
+ int vacalign, uint_t flags)
+{
+ caddr_t basep = (caddr_t)(uintptr_t)((uintptr_t)*addrp & PAGEMASK);
+ size_t lenp = len;
+
+ ASSERT(AS_ISCLAIMGAP(as)); /* searches should be serialized */
+ if (flags & MAP_FIXED) {
+ (void) as_unmap(as, *addrp, len);
+ return (0);
+ } else if (basep != NULL && ((flags & MAP_ALIGN) == 0) &&
+ !as_gap(as, len, &basep, &lenp, 0, *addrp)) {
+ /* User supplied address was available */
+ *addrp = basep;
+ } else {
+ /*
+ * No user supplied address or the address supplied was not
+ * available.
+ */
+ map_addr(addrp, len, off, vacalign, flags);
+ }
+ if (*addrp == NULL)
+ return (ENOMEM);
+ return (0);
+}
+
+
+/*
* Used for MAP_ANON - fast way to get anonymous pages
*/
static int
@@ -497,6 +531,7 @@ zmap(struct as *as, caddr_t *addrp, size_t len, uint_t uprot, int flags,
offset_t pos)
{
struct segvn_crargs vn_a;
+ int error;
if (((PROT_ALL & uprot) != uprot))
return (EACCES);
@@ -523,16 +558,15 @@ zmap(struct as *as, caddr_t *addrp, size_t len, uint_t uprot, int flags,
default:
return (ENOMEM);
}
- (void) as_unmap(as, *addrp, len);
- } else {
- /*
- * No need to worry about vac alignment for anonymous
- * pages since this is a "clone" object that doesn't
- * yet exist.
- */
- map_addr(addrp, len, pos, 0, flags);
- if (*addrp == NULL)
- return (ENOMEM);
+ }
+ /*
+ * No need to worry about vac alignment for anonymous
+ * pages since this is a "clone" object that doesn't
+ * yet exist.
+ */
+ error = choose_addr(as, addrp, len, pos, ADDR_NOVACALIGN, flags);
+ if (error != 0) {
+ return (error);
}
/*
@@ -602,7 +636,7 @@ smmap_common(caddr_t *addrp, size_t len,
/* alignment needs to be a power of 2 >= page size */
if (((uintptr_t)*addrp < PAGESIZE && (uintptr_t)*addrp != 0) ||
- !ISP2((uintptr_t)*addrp))
+ !ISP2((uintptr_t)*addrp))
return (EINVAL);
}
/*
diff --git a/usr/src/uts/common/os/schedctl.c b/usr/src/uts/common/os/schedctl.c
index db6ee0e86e..98c8457523 100644
--- a/usr/src/uts/common/os/schedctl.c
+++ b/usr/src/uts/common/os/schedctl.c
@@ -556,7 +556,7 @@ schedctl_page_lookup(sc_shared_t *ssp)
static int
schedctl_map(struct anon_map *amp, caddr_t *uaddrp, caddr_t kaddr)
{
- caddr_t addr;
+ caddr_t addr = NULL;
struct as *as = curproc->p_as;
struct segvn_crargs vn_a;
int error;
diff --git a/usr/src/uts/common/sys/vmsystm.h b/usr/src/uts/common/sys/vmsystm.h
index 0561ecf03a..a23d468f5a 100644
--- a/usr/src/uts/common/sys/vmsystm.h
+++ b/usr/src/uts/common/sys/vmsystm.h
@@ -19,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -113,6 +113,12 @@ extern pgcnt_t pages_before_pager; /* XXX */
#define MAPPGSZC_STACK 0x04
#define MAPPGSZC_HEAP 0x08
+/*
+ * vacalign values for choose_addr
+ */
+#define ADDR_NOVACALIGN 0
+#define ADDR_VACALIGN 1
+
struct as;
struct page;
struct anon;
@@ -133,6 +139,8 @@ extern size_t map_pgsz(int maptype, struct proc *p, caddr_t addr, size_t len,
int memcntl);
extern uint_t map_pgszcvec(caddr_t addr, size_t size, uintptr_t off, int flags,
int type, int memcntl);
+extern int choose_addr(struct as *as, caddr_t *addrp, size_t len, offset_t off,
+ int vacalign, uint_t flags);
extern void map_addr(caddr_t *addrp, size_t len, offset_t off, int vacalign,
uint_t flags);
extern int map_addr_vacalign_check(caddr_t, u_offset_t);
diff --git a/usr/src/uts/common/vm/seg_dev.c b/usr/src/uts/common/vm/seg_dev.c
index 2b24768e05..e3ea694c05 100644
--- a/usr/src/uts/common/vm/seg_dev.c
+++ b/usr/src/uts/common/vm/seg_dev.c
@@ -20,7 +20,7 @@
*/
/*
- * Copyright 2007 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -2439,21 +2439,11 @@ ddi_segmap_setup(dev_t dev, off_t offset, struct as *as, caddr_t *addrp,
}
as_rangelock(as);
- if ((flags & MAP_FIXED) == 0) {
- /*
- * Pick an address w/o worrying about
- * any vac alignment constraints.
- */
- map_addr(addrp, len, ptob(pfn), 0, flags);
- if (*addrp == NULL) {
- as_rangeunlock(as);
- return (ENOMEM);
- }
- } else {
- /*
- * User-specified address; blow away any previous mappings.
- */
- (void) as_unmap(as, *addrp, len);
+ /* Pick an address w/o worrying about any vac alignment constraints. */
+ error = choose_addr(as, addrp, len, ptob(pfn), ADDR_NOVACALIGN, flags);
+ if (error != 0) {
+ as_rangeunlock(as);
+ return (error);
}
dev_a.mapfunc = mapfunc;