summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorOtto Moerbeek <otto@cvs.openbsd.org>2008-09-12 08:55:42 +0000
committerOtto Moerbeek <otto@cvs.openbsd.org>2008-09-12 08:55:42 +0000
commit6599fc3960fb183cf2af3b1f512b5b77e153b008 (patch)
tree6655c511ff41a6bf9c0cb11a066257c8dbe80f53
parentb06901ab0daa22bceb1a0045e159acd9583b7547 (diff)
less waste for amaps in the common case:
allocate a single malloc chunk instead of three and allocate a single slot for a single page instead of four slots. ok miod@ tedu@ @deraadt
-rw-r--r--sys/uvm/uvm_amap.c53
1 files changed, 17 insertions, 36 deletions
diff --git a/sys/uvm/uvm_amap.c b/sys/uvm/uvm_amap.c
index 81e315831e5..c939baf29cf 100644
--- a/sys/uvm/uvm_amap.c
+++ b/sys/uvm/uvm_amap.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: uvm_amap.c,v 1.41 2008/08/26 15:39:27 kettenis Exp $ */
+/* $OpenBSD: uvm_amap.c,v 1.42 2008/09/12 08:55:41 otto Exp $ */
/* $NetBSD: uvm_amap.c,v 1.27 2000/11/25 06:27:59 chs Exp $ */
/*
@@ -67,6 +67,8 @@ struct pool uvm_amap_pool;
LIST_HEAD(, vm_amap) amap_list;
+#define MALLOC_SLOT_UNIT (2 * sizeof(int) + sizeof(struct vm_anon *))
+
/*
* local functions
*/
@@ -190,8 +192,8 @@ amap_alloc1(int slots, int padslots, int waitf)
if (amap == NULL)
return(NULL);
- totalslots = malloc_roundup((slots + padslots) * sizeof(int)) /
- sizeof(int);
+ totalslots = malloc_roundup((slots + padslots) * MALLOC_SLOT_UNIT) /
+ MALLOC_SLOT_UNIT;
amap->am_ref = 1;
amap->am_flags = 0;
#ifdef UVM_AMAP_PPREF
@@ -201,26 +203,18 @@ amap_alloc1(int slots, int padslots, int waitf)
amap->am_nslot = slots;
amap->am_nused = 0;
- amap->am_slots = malloc(totalslots * sizeof(int), M_UVMAMAP,
+ amap->am_slots = malloc(totalslots * MALLOC_SLOT_UNIT, M_UVMAMAP,
waitf);
if (amap->am_slots == NULL)
goto fail1;
- amap->am_bckptr = malloc(totalslots * sizeof(int), M_UVMAMAP, waitf);
- if (amap->am_bckptr == NULL)
- goto fail2;
-
- amap->am_anon = malloc(totalslots * sizeof(struct vm_anon *),
- M_UVMAMAP, waitf);
- if (amap->am_anon == NULL)
- goto fail3;
+ amap->am_bckptr = (int *)(((char *)amap->am_slots) + totalslots *
+ sizeof(int));
+ amap->am_anon = (struct vm_anon **)(((char *)amap->am_bckptr) +
+ totalslots * sizeof(int));
return(amap);
-fail3:
- free(amap->am_bckptr, M_UVMAMAP);
-fail2:
- free(amap->am_slots, M_UVMAMAP);
fail1:
pool_put(&uvm_amap_pool, amap);
return (NULL);
@@ -271,8 +265,6 @@ amap_free(struct vm_amap *amap)
KASSERT((amap->am_flags & AMAP_SWAPOFF) == 0);
free(amap->am_slots, M_UVMAMAP);
- free(amap->am_bckptr, M_UVMAMAP);
- free(amap->am_anon, M_UVMAMAP);
#ifdef UVM_AMAP_PPREF
if (amap->am_ppref && amap->am_ppref != PPREF_NONE)
free(amap->am_ppref, M_UVMAMAP);
@@ -369,7 +361,8 @@ amap_extend(struct vm_map_entry *entry, vsize_t addsize)
* XXXCDC: could we take advantage of a kernel realloc()?
*/
- slotalloc = malloc_roundup(slotneed * sizeof(int)) / sizeof(int);
+ slotalloc = malloc_roundup(slotneed * MALLOC_SLOT_UNIT) /
+ MALLOC_SLOT_UNIT;
#ifdef UVM_AMAP_PPREF
newppref = NULL;
if (amap->am_ppref && amap->am_ppref != PPREF_NONE) {
@@ -382,22 +375,9 @@ amap_extend(struct vm_map_entry *entry, vsize_t addsize)
}
}
#endif
- newsl = malloc(slotalloc * sizeof(int), M_UVMAMAP,
- M_WAITOK | M_CANFAIL);
- newbck = malloc(slotalloc * sizeof(int), M_UVMAMAP,
+ newsl = malloc(slotalloc * MALLOC_SLOT_UNIT, M_UVMAMAP,
M_WAITOK | M_CANFAIL);
- newover = malloc(slotalloc * sizeof(struct vm_anon *), M_UVMAMAP,
- M_WAITOK | M_CANFAIL);
- if (newsl == NULL || newbck == NULL || newover == NULL) {
- if (newsl != NULL) {
- free(newsl, M_UVMAMAP);
- }
- if (newbck != NULL) {
- free(newbck, M_UVMAMAP);
- }
- if (newover != NULL) {
- free(newover, M_UVMAMAP);
- }
+ if (newsl == NULL) {
#ifdef UVM_AMAP_PPREF
if (newppref != NULL) {
free(newppref, M_UVMAMAP);
@@ -405,6 +385,9 @@ amap_extend(struct vm_map_entry *entry, vsize_t addsize)
#endif
return (ENOMEM);
}
+ newbck = (int *)(((char *)newsl) + slotalloc * sizeof(int));
+ newover = (struct vm_anon **)(((char *)newbck) + slotalloc *
+ sizeof(int));
KASSERT(amap->am_maxslot < slotneed);
/*
@@ -452,8 +435,6 @@ amap_extend(struct vm_map_entry *entry, vsize_t addsize)
/* and free */
free(oldsl, M_UVMAMAP);
- free(oldbck, M_UVMAMAP);
- free(oldover, M_UVMAMAP);
#ifdef UVM_AMAP_PPREF
if (oldppref && oldppref != PPREF_NONE)
free(oldppref, M_UVMAMAP);